数据system
  1.                    
  2.                     entity.setname("magicbullet.png");
  3.                     MessagePositionHistory message = new MessagePositionHistory();
  4.                     message.entity=entity;
  5.                     message.nbt = new NBTTagCompound();

  6.                     message.nbt.setString("name","magicbullet.png");
  7.                     NetworkLoader.instance.sendToAll(message);
复制代码
  1. public class MessagePositionHistory implements IMessage
  2. {
  3.     public NBTTagCompound nbt;
  4.         public EntityMagicBullet entity;

  5.     @Override
  6.     public void fromBytes(ByteBuf buf)
  7.     {
  8.         nbt = ByteBufUtils.readTag(buf);
  9.     }

  10.     @Override
  11.     public void toBytes(ByteBuf buf)
  12.     {
  13.         ByteBufUtils.writeTag(buf, nbt);
  14.     }
  15.    
  16.     public static class Handler implements IMessageHandler<MessagePositionHistory, IMessage>
  17.     {
  18.         @Override
  19.         public IMessage onMessage(MessagePositionHistory message, MessageContext ctx)
  20.         {
  21.             if (ctx.side == Side.CLIENT)
  22.             {
  23.                 final String name = message.nbt.getString("name");
  24.                 Minecraft.getMinecraft().addScheduledTask(new Runnable()
  25.                 {
  26.                     @Override
  27.                     public void run()
  28.                     {
  29.                             //EntityPlayer player = Minecraft.getMinecraft().player;
  30.                             EntityMagicBullet e= message.entity;
  31.                             e.setname(name);
  32.                     }
  33.                 });
  34.             }
  35.             return null;
  36.         }
  37.     }
  38. }
复制代码


如题,应该如何将服务端对自定义的数据同步到客户端,这样写似乎没有作用,是实体的数据没传输过去吗?应该如何去客户端同步某一实体的数据。

数据system
没有大佬能来解答一下吗?

3TUSK
  1. Minecraft.getMinecraft().addScheduledTask(new Runnable()
  2.                 {
  3.                     @Override
  4.                     public void run()
  5.                     {
  6.                             //EntityPlayer player = Minecraft.getMinecraft().player;
  7.                             EntityMagicBullet e= message.entity;
  8.                             e.setname(name);
  9.                     }
  10.                 });
复制代码

显然你没有在这个数据包里写明“我要同步的是哪一个实体”。所以没有效果。

sendToAll 方法是“面向玩家”的,也就是说你发送数据包,收数据包的人是你的玩家。玩家的客户端负责处理数据。你不写清楚是哪一个实体的数据需要同步,那玩家的客户端也就不知道哪一个实体的数据需要同步。
具体来说,fromBytes() 方法里你不仅要从 ByteBuf 里读实体信息,还要读“是哪一个实体”。




题外话,这个需求看上去用 DataParameter<?> 更好一点。一次同步一整个 NBT?你在浪费流量。

数据system
本帖最后由 数据system 于 2020-4-2 10:29 编辑
3TUSK 发表于 2020-4-2 03:01
显然你没有在这个数据包里写明“我要同步的是哪一个实体”。所以没有效果。

sendToAll 方法是“面向玩家 ...

大佬这个该怎么去读取实体,ByteBufUtils好像没有读取实体的方法,这方面我实在不会,请问有教程之类的资料吗?

洞穴夜莺
数据system 发表于 2020-4-2 10:28
大佬这个该怎么去读取实体,ByteBufUtils好像没有读取实体的方法,这方面我实在不会,请问有教程之类的资料 ...

读取实体的UUID,在客户端根据UUID找到这个实体

数据system
Billy12345 发表于 2020-4-2 11:06
读取实体的UUID,在客户端根据UUID找到这个实体
  1.     @SubscribeEvent
  2.     public void onUseItem(RightClickItem event) {
  3.             EntityLivingBase player=event.getEntityPlayer();
  4.             World worldIn=player.getEntityWorld();
  5.             ItemStack Mainhand=player.getHeldItemMainhand();
  6.             if(Mainhand.getDisplayName()=="book") {
  7.                     if (!worldIn.isRemote) {
  8.                     EntityMagicBullet entity=new EntityMagicBullet(worldIn, player);
  9.                     entity.setTime(360);
  10.                     worldIn.spawnEntity(entity);
  11.                     entity.setname("magicbullet.png");
  12.                    
  13.                     MessagePositionHistory message = new MessagePositionHistory();
  14.                     UUID uuid=entity.getUniqueID();
  15.                     message.nbt = new NBTTagCompound();
  16.                    
  17.                     message.nbt.setString("name","magicbullet.png");
  18.                     message.nbt.setUniqueId("ID", uuid);
  19.                     NetworkLoader.instance.sendToAll(message);
  20.                     }
  21.             }
  22.            
  23.     }
复制代码
  1.     public static class Handler implements IMessageHandler<MessagePositionHistory, IMessage>
  2.     {
  3.         @Override
  4.         public IMessage onMessage(MessagePositionHistory message, MessageContext ctx)
  5.         {
  6.             if (ctx.side == Side.CLIENT)
  7.             {
  8.                 final String name = message.nbt.getString("name");
  9.                 final UUID uuid = message.nbt.getUniqueId("ID");
  10.                 Minecraft.getMinecraft().addScheduledTask(new Runnable()
  11.                 {
  12.                     @Override
  13.                     public void run()
  14.                     {
  15.                             EntityPlayerSP player=Minecraft.getMinecraft().player;
  16.                             World world =player.world;
  17.                             List<Entity> i=world.loadedEntityList;
  18.                             Entity t=i.get(0);
  19.                             int u=1;
  20.                            
  21.                             while((!uuid.equals(t.getUniqueID()))&&u<i.size()) {
  22.                                     t=i.get(u);
  23.                                     u++;
  24.                             }
  25.                            
  26.                             if(u<=i.size()) {((EntityMagicBullet) t).setname(name);}
  27.                     }
  28.                 });
  29.             }
  30.             return null;
  31.         }
  32.     }
复制代码
请问这样是哪里出问题,实体还是没变化

洞穴夜莺
没必要这么搞,直接用DataParameter<?>

数据system
Billy12345 发表于 2020-4-2 15:27
没必要这么搞,直接用DataParameter
  1. private static final DataParameter<Float> Yaw = EntityDataManager.<Float>createKey(EntityMagicBullet.class, DataSerializers.FLOAT);
  2.         private static final DataParameter<Float> Pitch = EntityDataManager.<Float>createKey(EntityMagicBullet.class, DataSerializers.FLOAT);
  3.         private static final DataParameter<String> Name = EntityDataManager.<String>createKey(Entity.class, DataSerializers.STRING);
  4.        
  5.         protected void entityInit() {
  6.                 this.dataManager.register(Yaw,Float.valueOf(15.0f) );
  7.                 this.dataManager.register(Pitch, Float.valueOf(15.0f) );
  8.                 this.dataManager.register(Name, "");
  9.         }
  10.         public void setrotation(Float t1,Float t2) {
  11.                 this.dataManager.set(Yaw, t1);
  12.                 this.dataManager.set(Pitch, t2);
  13.         }
  14.         public Float getYaw() {
  15.                 return (Float)this.dataManager.get(Yaw);
  16.         }
  17.         public Float getPitch() {
  18.                 return (Float)this.dataManager.get(Pitch);
  19.         }
复制代码
那个大佬,请问一下,Yaw和Pitch的同步似乎都没有问题,但加上this.dataManager.register(Name, "");这条后实体就会无法召唤,这是什么原因?

洞穴夜莺
数据system 发表于 2020-4-9 13:33
那个大佬,请问一下,Yaw和Pitch的同步似乎都没有问题,但加上this.dataManager.register(Name, "");这条 ...

有什么报错吗?
我这样写是没问题的啊

数据system
Billy12345 发表于 2020-4-9 18:24
有什么报错吗?
我这样写是没问题的啊


召唤实体时游戏没有崩溃,控制台输出了这些东西


洞穴夜莺
数据system 发表于 2020-4-9 18:53
召唤实体时游戏没有崩溃,控制台输出了这些东西

private static final DataParameter<String> Name = EntityDataManager.<String>createKey(Entity.class, DataSerializers.STRING);
改成
private static final DataParameter<String> Name = EntityDataManager.<String>createKey(EntityMagicBullet.class, DataSerializers.STRING);

第一页 上一页 下一页 最后一页