本帖最后由 602723113 于 2018-12-15 19:34 编辑


如何给你的实体增加NBT数据

目录:
  • 导读
  • 代码示例

导读

本教程使用的是 Spigot1.10.2-R0.1-SNAPSHOT 核心
在阅读之前请确保你具有Java基础知识

在上次的NBT教程中,我们是对物品的NBT进行的操作,那么实体可不可以操作它的NBT呢?答案是可以的

跟物品不同的是,你可以直接通过BukkitAPI操作实体的NBT,而不是通过NMS来进行操作

在BukkitAPI中,这个包就是为我们的实体的NBT进行的操作的包


特别感谢ChineseBukkitAPI汉化组

此包提供了开发者对实体进行的NBT操作,但此包不能用于物品!

代码示例

既然我们是对一个实体进行修改NBT的操作,那么我们就需要先有一个LivingEntity的实例
  1. Player player = (Player) sender;
  2. Zombie zombie = (Zombie) player.getWorld().spawnEntity(player.getLocation(), EntityType.ZOMBIE);
复制代码
在上方的代码中我们生成了一个僵尸,它是LivingEntity的一个子接口,然后我们获取其NBT
  1. AttributeInstance healthInstance = zombie.getAttribute(Attribute.GENERIC_MAX_HEALTH);
复制代码

在上方的代码中,我们调用了zombie.getAttribute()方法,里面需要填入一个Attribute枚举的示例,这里我们用最大生命值做演示
之后我们给这个僵尸增加一个AttributeModifier修改它的最大生命值
  1. healthInstance.addModifier(new AttributeModifier("最大生命值", 20D, AttributeModifier.Operation.ADD_NUMBER));
复制代码
上面的内容有点多,我们来一一介绍
我们调用的AttributeInstance类下的一个方法addModifier,里面需要填入的是一个AttributeModifier的示例,那么我们可以通过实例化就可以

之后我们再来看实例化的这些操作
AttributeModifier有两个构造方法可以供我们使用它们分别是
  1. AttributeModifier(String name, double amount, AttributeModifier.Operation operation)
  2. AttributeModifier(UUID uuid, String name, double amount, AttributeModifier.Operation operation)
复制代码
我们通过上方的两个构造方法可以发现两者只是一个UUID的不同,我们翻其实现可以发现,
  • UUID
没有UUID的构造方**自动给我们生成一个UUID,这个UUID用于AttributeModifier的区分,既然我们这里只修改了一个属性,所以我们直接使用上者即可

  • name
这里的name是AttributeModifier只要和其他的AttributeModifier不重复即可amount

  • amount
此处的amount是修改的数值

  • operation
operation用于表示当前AttributeModifier的数值是以什么进行作用
  • ADD_NUMBER (增加数值#会受到正负值的影响)
  • ADD_SCALAR (增加数值#不会受到正负值的影响,表示为标量)
  • MULTIPLY_SCALAR_1 (基值 * (该数值+1))   在将基值加1之后乘以该数值)
注释:
  • 基值: 此Attribute的基础值,如最大生命值,默认为20,20就是这里的基值


然后我们通过打印实体的最大血量进行观察
完整代码:
  1. Player player = (Player) sender;
  2. Zombie zombie = (Zombie) player.getWorld().spawnEntity(player.getLocation(), EntityType.ZOMBIE);
  3. player.sendMessage("[修改前]生命值: " + zombie.getMaxHealth());

  4. AttributeInstance healthInstance = zombie.getAttribute(Attribute.GENERIC_MAX_HEALTH);
  5. healthInstance.addModifier(new AttributeModifier("最大生命值", 20D, AttributeModifier.Operation.ADD_NUMBER));
  6. player.sendMessage("[修改后]生命值: " + zombie.getMaxHealth());
复制代码
测试结果:


通过上图,我们可以发现,我们已经成功修改了zombie实体的最大生命值

那么这里就会有人说

呆瓜:为什么不用setMaxHealth()呢?


为什么不用呢?首先这样的操作比较装逼,除此之外我们还可以修改NBT的其他Attribute属性
你可以在这里找到所有可用(不同版本,此枚举会有些不同)的Attribute


再吹一波ChineseBukkitAPI

通过查阅上方的doc,我们就可以看到有很多很多的Attribute可以修改

比如说
GENERIC_ARMOR (护甲值) -> 可以不用给实体穿戴护甲而增加其护甲值了
GENERIC_ATTACK_DAMAGE (当生物攻击其他人时所造成的伤害) -> 就可以不用给实体穿戴佩剑来增加其伤害了

诸如此类的操作...这里我就不再多说了



[groupid=1181]Unknown Domain[/groupid]