本站为非官方 Pylon 文档站,大量内容均为 AI 生成·前往官方文档站● ● ●This is an unofficial Pylon documentation site, most content is AI-generated·Visit Official Docs● ● ●中文开发者交流·加入 QQ 群● ● ●本站为非官方 Pylon 文档站,大量内容均为 AI 生成·前往官方文档站● ● ●This is an unofficial Pylon documentation site, most content is AI-generated·Visit Official Docs● ● ●中文开发者交流·加入 QQ 群● ● ●
Pylon 中文文档
创建附属

物品与配置

介绍 Rebar 物品与配置系统的基础知识。

最后更新时间

概览

这节讲怎么给物品加自定义行为。我们用法棍喷火器来演示——右键点击实体时点燃它。


法棍喷火器

创建一个"普通"物品

像上一节一样,先做一个"普通"物品。

MyAddonKeys.java
public final class ExampleAddonKeys {
    public static final NamespacedKey baguetteFlamethrowerKey = new NamespacedKey(this, "baguette_flamethrower");
}
MyAddonitems.java
public final class ExampleAddonItems {

    // ...

    public static final ItemStack baguetteFlamethrower = ItemStackBuilder.rebar(Material.BREAD, baguetteFlamethrowerKey)
            .build();

    // ...

    public static void initialize() {

        // ...

        RebarItem.register(RebarItem.class, baguette);
        PylonPages.FOOD.addItem(baguetteKey);
    }
}
resources/en.yml
item:
  baguette:
    name: Baguette Flamethrower
    lore: |-
      <arrow> Use the power of baguettes to vanquish your enemies
      <arrow> <insn>Right click</insn> an entity to ignite it

创建自定义物品类

接下来加点火逻辑。

需要新建一个 BaguetteFlamethrower 类。所有 Rebar 物品类都必须继承 RebarItem

新建 BaguetteFlamethrower.java

BaguetteFlamethrower.java
public class BaguetteFlamethrower extends RebarItem {
    public BaguetteFlamethrower(@NotNull ItemStack stack) {
        super(stack);
    }
}

想让玩家拿法棍喷火器右键实体时触发代码。为此需要实现一个 Rebar 物品接口。

Rebar 物品接口就是让你的物品能做更多事的接口——比如在物品被使用时执行代码。

这里要实现 RebarItemEntityInteractor 接口,它有一个方法:onUsedToRightClickEntity

物品接口完整列表在这里

BaguetteFlamethrower
public class BaguetteFlamethrower extends RebarItem implements RebarItemEntityInteractor {
    public BaguetteFlamethrower(@NotNull ItemStack stack) {
        super(stack);
    }

    @Override
    public void onUsedToRightClickEntity(@NotNull PlayerInteractEntityEvent event, @NotNull EventPriority priority) {
        event.getRightClicked().setFireTicks(40);
    }
}

使用自定义物品类

让法棍喷火器用这个自定义类,代替默认的 RebarItem

RebarItem.register(...) 那行改成这样:

RebarItem.register(BaguetteFlamethrower.class, baguetteFlamethrower);

跑一下服务器试试。用法棍喷火器右键一个实体,应该能让它着火 40 tick!


让物品可配置

物品可以绑定配置文件。看看服务器的 Pylon 设置目录(run/plugins/Rebar/settings/pylon),很多 Pylon 物品和方块都有自己的配置文件。

比如 bandage.yml

bandage.yml
consume-seconds: 1.25
heal-amount: 4.0

创建配置文件

假如想加个配置文件,让你自己设置法棍喷火器的点燃时长。

新建 resources/settings/baguette_flamethrower.yml

baguette_flamethrower.yml
burn-time-ticks: 40

最佳实践

配置选项是数量的话,名称里带上单位。如果只叫 burn-time,用户可能不知道单位是 tick,会误以为是秒或其他单位。

Rebar 在配置文件首次使用时,会自动把所有设置复制到 run/plugins/Rebar/settings/<你的附属组件名称> 目录下,方便服主配置。

读取配置文件

读取配置里的 burn-time-ticks 值,用 getSettings().getOrThrow(...) 就行。getSettings() 返回和物品键同名的配置——本例中是 flamethrower_baguette

BaguetteFlamethrower.java
public class BaguetteFlamethrower extends RebarItem implements RebarItemEntityInteractor {
    private final int burnTimeTicks = getSettings().getOrThrow("burn-time-ticks", ConfigAdapter.INT);

    public BaguetteFlamethrower(@NotNull ItemStack stack) {
        super(stack);
    }

    @Override
    public void onUsedToRightClickEntity(@NotNull PlayerInteractEntityEvent event, @NotNull EventPriority priority) {
        event.getRightClicked().setFireTicks(40);
    }
}

Rebar 怎么知道用哪个配置文件?

配置文件是按分配的,不是按物品。访问 settings 时,Rebar 会取物品的键去找对应的设置文件!其实就是 Settings.get(key) 的简写。如果你用 Settings.get(NamespacedKey(MyAddon.getInstance(), "buffoon")),读的就是 buffoon.yml

Settings 也有 get 方法,找不到键就返回 null。用 getOrThrow 的话,找不到键会直接抛异常,告诉你缺了哪个键、在哪。

调用 getgetOrThrow 时要传一个 ConfigAdapter,这个类定义了怎么从配置文件读值。

配置适配器列表在这里

用配置值来点火

现在可以用这个值来点火了!

BaguetteFlamethrower.java
public class BaguetteFlamethrower extends RebarItem implements RebarItemEntityInteractor {
    private final int burnTimeTicks = getSettings().getOrThrow("burn-time-ticks", ConfigAdapter.INT);

    public BaguetteFlamethrower(@NotNull ItemStack stack) {
        super(stack);
    }

    @Override
    public void onUsedToRightClickEntity(@NotNull PlayerInteractEntityEvent event, @NotNull EventPriority priority) {
        event.getRightClicked().setFireTicks(burnTimeTicks);
    }
}

改配置值的话燃烧时间也会跟着变。

测配置的时候注意:每次跑测试服务器任务都会清空 plugins 文件夹,里面的配置改动会被覆盖。所以要么改默认值,要么手动启服务器(不要用测试任务),这样 plugins 文件夹不会被清。


完整代码

MyAddonKeys.java
public final class ExampleAddonKeys {
    public static final NamespacedKey baguetteFlamethrowerKey = new NamespacedKey(this, "baguette_flamethrower");
}
BaguetteFlamethrower.java
public class BaguetteFlamethrower extends RebarItem implements RebarItemEntityInteractor {
    private final int burnTimeTicks = getSettings().getOrThrow("burn-time-ticks", ConfigAdapter.INT);

    public BaguetteFlamethrower(@NotNull ItemStack stack) {
        super(stack);
    }

    @Override
    public void onUsedToRightClickEntity(@NotNull PlayerInteractEntityEvent event, @NotNull EventPriority priority) {
        event.getRightClicked().setFireTicks(burnTimeTicks);
    }
}
MyAddonitems.java
public final class ExampleAddonItems {

    // ...

    public static final ItemStack baguetteFlamethrower = ItemStackBuilder.rebar(Material.BREAD, baguetteFlamethrowerKey)
            .build();

    // ...

    public static void initialize() {

        // ...

        RebarItem.register(RebarItem.class, baguette);
        PylonPages.FOOD.addItem(baguetteKey);
    }
}
resources/en.yml
item:
  baguette:
    name: Baguette Flamethrower
    lore: |-
      <arrow> Use the power of baguettes to vanquish your enemies
      <arrow> <insn>Right click</insn> an entity to ignite it
baguette_flamethrower.yml
burn-time-ticks: 40

目录