From 9ccd0a9c6e892f6b32005b1d800d22bcd496fecc Mon Sep 17 00:00:00 2001 From: SB-Reborn Date: Sat, 10 Aug 2024 00:46:37 +0800 Subject: [PATCH] =?UTF-8?q?=E5=88=A0=E9=99=A4=E4=BA=86=E5=9B=A0=E6=A0=BC?= =?UTF-8?q?=E5=BC=8F=E5=8C=96=E8=80=8C=E6=84=8F=E5=A4=96=E9=87=8D=E5=A4=8D?= =?UTF-8?q?=E7=9A=84=E6=AE=B5=E8=90=BD=20(#217)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 驿站合之前不review,拷打 --- .../plugin/other/Skript/AdvancedTutorials.md | 651 ------------------ 1 file changed, 651 deletions(-) diff --git a/docs-java/process/plugin/other/Skript/AdvancedTutorials.md b/docs-java/process/plugin/other/Skript/AdvancedTutorials.md index 6caea81b2..43fcdd29f 100644 --- a/docs-java/process/plugin/other/Skript/AdvancedTutorials.md +++ b/docs-java/process/plugin/other/Skript/AdvancedTutorials.md @@ -198,654 +198,3 @@ on TPARequestEvent: 这几行和普通的 sk 语法没什么区别,作用是判断然后取消事件。 -### 使用方法 - -如果你需要调用其他的插件或是一些 **skript** 里没有而 [Bukkit API](https://bukkit.windit.net/javadoc/) 有的 API,那么会很棘手。 - -**skript-reflect** 很好的解决了这一点。 - -比如,你正在使用 **Leaves** 服务端,想要用sk来改变Leaves中假人在玩家列表中显示的名字,那么可以遵循以下步骤: - -#### 查询 Javadoc - -修改假人的名字这一行为应该在假人加入服务器时进行,所以我们得监听这一事件。 - -我们需要找到 bot 事件到底是哪个,查询[Leaves 的 Javadoc](https://repo.leavesmc.org/javadoc/snapshots/org/leavesmc/leaves/leaves-api/1.20.6-R0.1-SNAPSHOT): - -![搜索事件](_images/SearchEvent.png) - -这里查询找到了`org.leavesmc.leaves.event.bot.BotEvent`事件。 - -看命名就知道应该会有更详细的**子类**来**继承**它,点进去看看,可以看到: - -![查找子类](_images/QuerySubclasses.png) - -通过看类名可以知道,`BotJoinEvent`就是我们要的事件。 - -看介绍,发现这个事件会“Called when a fakeplayer joins a server” - -接下来让我们看看这个类有哪些**方法**。 - -![查找方法](_images/SearchMethods.png) - -可以看到,最主要的是一个`getBot()`方法,在让我们看看这个方法会返回什么。 - -点击超链接,可以看到这个方法会返回一个`Bot`对象。 - -这个`Bot`接口是继承自`Player`的,也就是说,`Player`有的方法,`Bot`都有。 - -再次查询 [Bukkit API](https://bukkit.windit.net/javadoc/org/bukkit/entity/Player.html) 可以找到`Player`类有的方法,如`Player#setPlayerListName()`,这正是我们需要的方法。 - -#### 编写程序 - -开始编写程序 - -```sk -import: - org.leavesmc.leaves.event.bot.BotJoinEvent #导入类 - -# 监听事件 -on BotJoinEvent: - set {_bot} to event.getBot() # 获取假人 - set {_bot_name} to {_bot}.getName() # 储存假人原本的名字 - {_bot}.setPlayerListName("假的%{_bot_name}%") # 修改假人在tab列表里的名字 -``` - -这一过程也可适用于其他插件,比如[zimzaza4大蛇](https://github.com/zimzaza4)的 [Skript-Floodgate-Api](https://github.com/zimzaza4/Skript-Floodgate-Api) , -就是利用 **skript-reflect** 来调用 [Floodagate API](https://wiki.geysermc.org/floodgate/api/) 的。 - -可以查看下面的教程来详细学习 **skript-reflect** 的基础功能(对,下面这一大坨只是基础) - -### skript-reflect 基础教程 - -:::danger - -此段部分或全部抄自 **skript-reflect** [官方文档](https://tpgamesnl.gitbook.io/skript-reflect/basics) - -::: - -#### 导入 Java 类 - -##### _在解析时导入类(推荐)_ - -在大多数情况下,无需运行脚本即可知道所需类的确切限定名称。如果是这种情况,您应该使用 **skript-reflect** 的`import`块: - -:::info - -为避免冲突,`import`块创建的表达式仅对导入它们的脚本可用。您必须在使用它们的每个脚本中导入 Java 类。 - -::: - -```sk -import: - java.lang.System - -command /example: - trigger: - message "%System%" # java.lang.System - System.out.println("test") -``` - -```sk -import: - java.lang.String as JavaString - -command /example: - trigger: - message JavaString.format("Hello %%s", sender) -``` - -:::info - -别名必须是有效的 Java 标识符! - -```sk -on TPARequestEvent: -``` - -这行代码意为注册监听`TPARequestEvent`事件,与普通 sk 里注册事件的语法没啥区别。 - -```sk - set {_ess_IUser} to event.getTarget() # 获取IUser对象 - set {_player} to {_ess_IUser}.getBase() # 获取Player对象 -``` - -这行代码意为调用这个事件里的`getTarget()`方法,来获取 tpa 的目标,其返回一个`IUser`。 - -这个`IUser`是 EssentialsX 的一个**接口**,`User`类**实现**了它,可以在[essentialsx 的 javadoc](https://jd-v2.essentialsx.net/net/ess3/api/iuser)里查看。 - -```sk - if {_player} is player("lilingfeng"): - send "&cliliangfeng是我的不准tpa到她那里🥵" - cancel event -``` - -这几行和普通的 sk 语法没什么区别,作用是判断然后取消事件。 - -### 使用方法 - -如果你需要调用其他的插件或是一些 **skript** 里没有而 [Bukkit API](https://bukkit.windit.net/javadoc/) 有的 API,那么会很棘手。 - -**skript-reflect** 很好的解决了这一点。 - -比如,你正在使用 **Leaves** 服务端,想要用sk来改变Leaves中假人在玩家列表中显示的名字,那么可以遵循以下步骤: - -#### 查询 Javadoc - -修改假人的名字这一行为应该在假人加入服务器时进行,所以我们得监听这一事件。 - -我们需要找到 bot 事件到底是哪个,查询[Leaves 的 Javadoc](https://repo.leavesmc.org/javadoc/snapshots/org/leavesmc/leaves/leaves-api/1.20.6-R0.1-SNAPSHOT): - -![搜索事件](_images/SearchEvent.png) - -这里查询找到了`org.leavesmc.leaves.event.bot.BotEvent`事件。 - -看命名就知道应该会有更详细的**子类**来**继承**它,点进去看看,可以看到: - -![查找子类](_images/QuerySubclasses.png) - -通过看类名可以知道,`BotJoinEvent`就是我们要的事件。 - -看介绍,发现这个事件会“Called when a fakeplayer joins a server” - -接下来让我们看看这个类有哪些**方法**。 - -![查找方法](_images/SearchMethods.png) - -可以看到,最主要的是一个`getBot()`方法,在让我们看看这个方法会返回什么。 - -点击超链接,可以看到这个方法会返回一个`Bot`对象。 - -这个`Bot`接口是继承自`Player`的,也就是说,`Player`有的方法,`Bot`都有。 - -再次查询 [Bukkit API](https://bukkit.windit.net/javadoc/org/bukkit/entity/Player.html) 可以找到`Player`类有的方法,如`Player#setPlayerListName()`,这正是我们需要的方法。 - -#### 编写程序 - -开始编写程序 - -```sk -import: - org.leavesmc.leaves.event.bot.BotJoinEvent #导入类 - -# 监听事件 -on BotJoinEvent: - set {_bot} to event.getBot() # 获取假人 - set {_bot_name} to {_bot}.getName() # 储存假人原本的名字 - {_bot}.setPlayerListName("假的%{_bot_name}%") # 修改假人在tab列表里的名字 -``` - -这一过程也可适用于其他插件,比如[zimzaza4大蛇](https://github.com/zimzaza4)的 [Skript-Floodgate-Api](https://github.com/zimzaza4/Skript-Floodgate-Api) , -就是利用 **skript-reflect** 来调用 [Floodagate API](https://wiki.geysermc.org/floodgate/api/) 的。 - -可以查看下面的教程来详细学习 **skript-reflect** 的基础功能(对,下面这一大坨只是基础) - -### skript-reflect 基础教程 - -:::danger - -此段部分或全部抄自 **skript-reflect** [官方文档](https://tpgamesnl.gitbook.io/skript-reflect/basics) - -::: - -#### 导入 Java 类 - -##### _在解析时导入类(推荐)_ - -在大多数情况下,无需运行脚本即可知道所需类的确切限定名称。如果是这种情况,您应该使用 **skript-reflect** 的`import`块: - -:::info - -为避免冲突,`import`块创建的表达式仅对导入它们的脚本可用。您必须在使用它们的每个脚本中导入 Java 类。 - -::: - -```sk -import: - java.lang.System - -command /example: - trigger: - message "%System%" # java.lang.System - System.out.println("test") -``` - -```sk -import: - java.lang.String as JavaString - -command /example: - trigger: - message JavaString.format("Hello %%s", sender) -``` - -:::info - -别名必须是有效的 Java 标识符! - -::: - -###### 在低于 1.17 的 Minecraft 版本上导入 NMS 类 - -由于 **Minecraft** 1.17 以下版 - -::: - -###### 在低于 1.17 的 Minecraft 版本上导入 NMS 类 - -由于 **Minecraft** 1.17 以下版 - trigger: - message JavaString.format("Hello %%s", sender) - -``` - -:::info - -别名必须是有效的 Java 标识符! - -::: - -###### 在低于 1.17 的 Minecraft 版本上导入 NMS 类 - -由于 **Minecraft** 1.17 以下版本的 **NMS** 包会随着每个 **Minecraft** 版本而变化,因此您应该动态生成包前缀。有关详细信息,请参阅[计算选项](https://tpgamesnl.gitbook.io/skript-reflect/advanced/computed-options#using-computed-options-for-nms-imports)。 - -##### _在运行时导入类_ - -有时,在执行脚本之前,无法确定所需的类引用。 - -###### 从完全限定的名称 - -语法: - -```sk -[the] [java] class %text% -``` - -示例: - -```sk -on script load: - set {Player} to the class "org.bukkit.entity.Player" - message "%{Player}%" # org.bukkit.entity.Player -``` - -###### _从对象_ - -语法: - -```sk -[the] [java] class[es] of %objects% -%objects%'[s] [java] class[es] -``` - -示例: - -```sk -command /example: - executable by: players - trigger: - set {Player} to player's class - message "%{Player}%" # org.bukkit.entity.Player -``` - -###### 在effect命令中导入 - -由于导入块在 effect 命令中不可用,因此您可以使用 import effect(仅在 effect 命令中可用): - -```sk -import [as ] -``` - -此导入只能在以上效果命令中使用,直到您停止服务器。 - -##### _处理内部类_ - -有时,一个类可能嵌套在另一个类中。当引用类的完全限定名称时,内部类使用一个`$`而不是`.` - -例如,将`org.bukkit.entity.EnderDragon.Phase`变成`org.bukkit.entity.EnderDragon$Phase`。 - -内部类通常比其周围的类具有更通用的名称,因此应在别名下导入这些名称: - -```sk -import: - org.bukkit.entity.EnderDragon$Phase as EnderDragonPhase -``` - -导入这些类的另一种方法是只导入它们的封闭类: - -```sk -import: - org.bukkit.entity.EnderDragon - -on load: - set {phase} to EnderDragon.Phase.LEAVE_PORTAL -``` - -#### 运行 Java 代码 - -##### _调用方法_ - -语法: - -```sk -%object%.(%objects%) -``` - -示例: - -```sk -event-block.breakNaturally() -(last spawned creeper).setPowered(true) -player.giveExpLevels({_levels}) -``` - -方法可以用作 **Effects** 、 **Expressions** 和 **Conditions** 。如果用作**Conditions**,则只要方法的返回值不是 `false` 、`null`或`0` ,这个 **Conditions** 就会通过。 - -###### 调用非公共方法 - -如果尝试调用的方法不是公共的,则可能需要在方法名称前面加上括号中的声明类。由于一个对象在多个父类中可能具有同名的非公共方法,因此必须显式指定在何处查找该方法。 - -语法: - -```sk -{_arraylist}.[ArrayList]fastRemove(1) -``` - -###### 调用重载的方法 - -通常, **skript-reflect** 可以从运行时传递的参数中推断出要调用的正确的重载方法。如果需要使用某个方法的某种实现,可以在方法名称的末尾附加一个逗号分隔的列表,并用括号括起来。 - -语法: - -```sk -System.out.println[Object]({_something}) - -Math.max[int, int](0, {_value}) -``` - -##### _调用字段_ - -语法: - -```sk -%object%. -``` - -###### 调用非公共字段 - -如果您尝试访问的字段不是公共的,则可能需要在字段名称前面加上括号中的声明类。由于一个对象在多个父类中可能具有同名的非公共字段,因此必须显式指定查找该字段的位置。 - -示例: - -```sk -{_hashmap}.[HashMap]modCount -``` - -##### _调用构造函数_ - -语法: - -```sk -[a] new %javatype%(%objects%) -``` - -示例: - -```sk -new Location(player's world, 0, 0, 0) -``` - -#### 处理事件 - -##### 监听事件 - -您可以通过引用导入的类来收听任何基于 Bukkit 的事件(包括其他插件添加的事件)。例如,如果要收听 `org.bukkit.event.entity.EnderDragonChangePhaseEvent`: - -```sk -import: - org.bukkit.event.entity.EnderDragonChangePhaseEvent - -on EnderDragonChangePhaseEvent: - # your code -``` - -:::warning - -一些插件使用自己的事件处理系统,或者不通过 **Bukkit** 的事件执行器传递他们的事件( **Skript** 的一些内部事件就是这种情况)。 - -为了侦听事件,它必须扩展`org.bukkit.event.Event`并由 **Bukkit** 的事件执行器执行。 - -::: - -您还可以使用同一处理程序侦听多个事件。这些事件不必相关,但如果尝试访问在一个事件中可用但在另一个事件中不可用的方法,则应采取适当的预防措施。例如,如果要同时侦听`org.bukkit.event.entity.ProjectileLaunchEvent`和`org.bukkit.event.entity.ProjectileHitEvent`: - -```sk -import: - org.bukkit.event.entity.ProjectileLaunchEvent - org.bukkit.event.entity.ProjectileHitEvent - -on ProjectileLaunchEvent and ProjectileHitEvent: - # your code -``` - -##### 使用`event` **Expressions** - -**skript-reflect** 公开一个叫做`event`的 **Expressions**,允许您使用反射访问事件值。 - -语法: - -```sk -[the] event -``` - -示例: - -```sk -import: - org.bukkit.event.entity.EnderDragonChangePhaseEvent - org.bukkit.entity.EnderDragon$Phase as EnderDragonPhase - -on EnderDragonChangePhaseEvent: - if event.getNewPhase() is EnderDragonPhase.CIRCLING: - event.setNewPhase(EnderDragonPhase.CHARGE_PLAYER) -``` - -:::info - -该 event 表达式也可用于正常的 Skript 事件。 - -::: - -##### 设置优先级 - -可以将事件的优先级设置为控制特定事件处理程序相对于其他事件处理程序的运行时间。 - -示例: - -```sk -import: - org.bukkit.event.entity.EnderDragonChangePhaseEvent - -on EnderDragonChangePhaseEvent with priority highest: - # your code -``` - -可以使用`org.bukkit.event.EventPriority`中定义的任何事件优先级。优先级较低的事件处理程序在优先级较高的事件处理程序之前运行。 - -事件优先级: - -``` -lowest -low -normal -high -highest -monitor -``` - -##### 处理已取消的事件 - -默认情况下,如果事件被优先级较低的处理程序取消,则不会调用事件处理程序。可以通过指定处理程序应处理`all`事件来更改此行为。 - -示例: - -```sk -import: - org.bukkit.event.block.BlockBreakEvent - -on all BlockBreakEvent: - uncancel event -``` - -#### 一些 **skript-reflect** 内置的小工具 - -##### Collect - -```sk -[%objects%] -[%objects% as %javatype%] -``` - -创建包含指定对象的数组。指定类型可确定生成数组的组件类型。 - -:::info - -此语法中的括号是文字,不表示可选组。 - -::: - -##### Spread - -```sk -...%object% -``` - -将Java类型的数组转化为sk可读形式。 - -实例: - -```sk -set {_list::*} to ...{_array} -``` - -##### 创建数组 - -```sk -new %javatype%[%integer%] -``` - -创建给定类型和大小的数组。类型可能是原始类型,不需要导入。 - -:::info - -此语法中的括号是文字,不表示可选组。 - -::: - -##### 通过索引获取数组的值 - -```sk -%array%[%integer%] -``` - -表示数组的某个索引处的值。 - -可以读取和写入此值。 - -:::info - -此语法中的括号是文字,不表示可选组。 - -::: - -##### Null - -```sk -null -``` - -在 **Java** 中表示 `null` 。这与 **Skript** 的``不同 . - -##### Bits - -```sk -[the] (bit %number%|bit(s| range) [from] %number%( to |[ ]-[ ])%number%) of %numbers% -%numbers%'[s] (bit %number%|1¦bit(s| range) [from] %number%( to |[ ]-[ ])%number%) -``` - -表示数字中的位的子集。 - -可以读取和写入此值。 - -##### Raw Expression - -```sk -[the] raw %objects% -``` - -返回表达式的基础对象。 - -:::info - -与 [Expression](https://tpgamesnl.gitbook.io/skript-reflect/advanced/custom-syntax#expression) 一起使用时,可以将其设置为一个值,这将更改该参数的输入值。这可用于将数据存储在调用触发器的变量中。 - -```sk -import: - ch.njol.skript.lang.Variable - -effect put %objects% in %objects%: - parse: - expr-2 is an instance of Variable # to check if the second argument is a variable - continue - trigger: - set raw expr-2 to expr-1 -``` - -::: - -##### 成员 - -```sk -[the] (fields|methods|constructors) of %objects% -%objects%'[s] (fields|methods|constructors) -``` - -返回对象的字段、方法或构造函数的列表,包括其修饰符和参数。 - -如果需要不带修饰符或参数详细信息的字段或方法名称列表,请参阅[成员名称](https://tpgamesnl.gitbook.io/skript-reflect/basics/utilities#member-names)。 - -##### 成员的名字 - -```sk -[the] (field|method) names of %objects% -%objects%'[s] (field|method) names -``` - -返回对象的字段或方法的列表。 - -##### 判断对象是否是某个类的实例 - -```sk -%objects% (is|are) [a[n]] instance[s] of %javatypes% -%objects% (is not|isn't|are not|aren't) [a[n]] instance[s] of %javatypes% -``` - -检查对象是否是给定 **Java** 类型的实例。 - -##### 类引用 - -```sk -%javatype%.class -``` - -从给定的 **Java** 类型返回对类的引用。返回`java.lang.Class`类型的对象。此表达式还支持不需要导入的基元类型。 - -##### 插件实例 - -```sk -[(an|the)] instance of [the] plugin %javatype/string% -``` - -返回给定插件的实例(字符串形式的名称或插件类)。 - -更高级的用法及详细内容请自行查阅[skript-reflect文档](https://tpgamesnl.gitbook.io/skript-reflect)