Skip to content

API

EmakiItem 提供物品创建、识别和查询能力。对外公开的是静态门面 EmakiItemApi;插件本体在启用时安装 bridge,禁用时卸载 bridge。

EmakiItemApi

方法返回值说明
available()boolean判断 EmakiItem API 是否已安装。
isReady()boolean判断 EmakiItem 是否已完成初始化并可解析物品定义。重载进行中返回 false
exists(String id)boolean检查物品 ID 是否已加载。
create(String id, int amount)ItemStack根据物品 ID 创建 ItemStack。返回 null 表示 ID 不存在或 API 不可用。
identify(ItemStack itemStack)String识别物品的 EmakiItem ID。返回 null 表示不是 EmakiItem 物品。
definitionIds()Set<String>获取所有已加载的物品 ID 集合。
displayName(String id)String获取物品的显示名(纯文本,不含 MiniMessage 标签);未知 ID 或 API 未安装时返回空串。
definition(String id)ConfiguredItemDefinition获取规范化后的共享基础物品定义;未知 ID 或 API 未安装时返回 null
registerLayerPreview(Plugin plugin, ItemLayerPreviewProvider provider)ItemLayerPreviewRegistration注册物品层预览提供器;EmakiItem 不可用时返回可安全关闭的 no-op 句柄。

获取方式

java
if (EmakiItemApi.available()) {
    ItemStack stack = EmakiItemApi.create("example_sword", 1);
}

或者先做可用性检查:

java
if (!EmakiItemApiProvider.available()) {
    return;
}

EmakiItemApiProvider.requireAvailable();
ItemStack stack = EmakiItemApi.create("example_sword", 1);

接入建议

  • 在插件 onEnable 之后再查询可用性,确保 EmakiItem 已加载。
  • 查询不到 API 时降级运行,不要让 softdepend 模块直接崩溃。
  • create 返回的 ItemStack 是全新实例,已包含所有 PDC 数据和展示。
  • identify 通过 PDC 中的 emakiitem:id 标记识别,不依赖 Lore 或名称。
  • definition 返回 CoreLib API 的版本无关 DTO,不暴露 EmakiItem 内部 model 或 Paper experimental 组件 value 类型。
  • definition 是加法式 API;Bridge 默认实现返回 null,旧实现不会因缺少新方法而发生链接失败。
  • available() 只表示 bridge 已安装;需要确保物品定义可解析时应改用 isReady()

物品层预览 SPI

物品层 Preview SPI 位于 EmakiItemApi 模块的 emaki.jiuwu.craft.item.api.preview 包,第三方通过 EmakiItemApi.registerLayerPreview 注册。

类型说明
ItemLayerPreviewProvider提供器接口:id() 返回稳定层 ID,order() 决定顺序(默认 100,小值先应用),preview(request) 生成预览结果。
ItemLayerPreviewRequest不可变请求快照:itemIdbaseItemcurrentItemoptions;物品字段进出都会克隆。
ItemLayerPreviewResult不可变结果:idavailablereasonitemStackdetailsoptionsselected;提供 available(...)unavailable(...) 工厂方法。
ItemLayerPreviewRegistration可关闭注册句柄,实现 AutoCloseablenoop() 返回可重复使用的空实现。

注册表语义(EmakiItemLayerPreviewRegistry,实例级、owner-aware):

  • 层 ID 按 trim + 小写规范化;ID 为空或 provider/owner 为 null 时返回 no-op 句柄。
  • 同一 ID 重复注册会替换旧记录,并按 generation 保护:旧句柄 close() 不会误删新注册。
  • 查询时按 order() 升序、同 order 按 ID 字典序返回稳定顺序。
  • owner 插件被禁用时自动清理其 provider,PluginDisableEvent 也会触发同 owner 清理。
  • provider 抛出异常或返回 null 时降级为该层 unavailable,不影响其余层。
java
ItemLayerPreviewRegistration registration = EmakiItemApi.registerLayerPreview(this, new ItemLayerPreviewProvider() {
    @Override
    public String id() {
        return "my_layer";
    }

    @Override
    public ItemLayerPreviewResult preview(ItemLayerPreviewRequest request) {
        return ItemLayerPreviewResult.unavailable(id(), "not configured", Map.of(), Map.of());
    }
});

插件禁用时调用 registration.close() 释放注册。strengthengem 是内置层 ID,对应模块未加载时会以 unavailable 占位出现。

JavaScript 调用

CoreLib JavaScript 脚本中可通过 emaki.module("item") 调用 EmakiItem 模块门面,emaki.module("items") 是等价别名。注意 emaki.item 是上下文物品工具,emaki.module("item") 才是 EmakiItem 插件 API。

方法说明
available()判断 EmakiItem API 是否可用。
exists(id)判断物品定义是否已加载。
create(id, amount)返回物品摘要快照,不放入背包。
identify(itemKey)识别上下文 attribute 中该 key 对应物品的 EmakiItem ID。
definitionIds()返回所有物品定义 ID。
displayName(id)返回定义显示名纯文本。

完整的脚本方法(含运行时定义与物品工厂注册)见 JavaScript 脚本

js
function main(ctx) {
  const item = emaki.module("item");
  if (!item.available()) {
    return { skipped: true, message: "EmakiItem not installed" };
  }

  const id = item.identify("item_stack");
  const preview = item.create("example_sword", 1);
  emaki.logger.info("current=" + id + ", preview=" + preview.displayName);
  return true;
}