Hi, I'm quite new to NMS/Protocol API and giving it my best shot to learn, but am having some difficulty with Entitymeta. I do not have much knowledge of the API yet and don't know what I'm doing too well yet, so try to give me a bit of patience (I've watched a tutorial and read through the introduction, it just hasn't entirely "clicked" per-say.) What I'm trying to do: The goal here is to set a player to glowing through packets, for X amount of time, visible to any player I specify With some googling and a bit of mental power, I was able to get a player to glow, but as soon as the player sprinted, they stopped glowing. I believe this might be because the metadata of the player is changing? I did so with this code (Pretty much copy pasted from https://www.spigotmc.org/threads/simulating-potion-effect-glowing-with-protocollib.218828/): Spoiler: Copy pasted code from other source Code (Java): private void setGlowing() { pm.addPacketListener(new PacketAdapter(this, ListenerPriority.NORMAL, PacketType.Play.Server.UPDATE_HEALTH) { @Override public void onPacketSending(PacketEvent event) { Player player = event.getPlayer(); PacketContainer packet = pm.createPacket(PacketType.Play.Server.ENTITY_METADATA); packet.getIntegers().write(0, player.getEntityId()); // Set packet's entity id WrappedDataWatcher watcher = new WrappedDataWatcher(); // Create data watcher, the Entity Metadata // packet requires this Serializer serializer = Registry.get(Byte.class); // Found this through google, needed for some stupid // reason watcher.setEntity(player); // Set the new data watcher's target watcher.setObject(0, serializer, (byte) (0x40)); // Set status to glowing, found on protocol page packet.getWatchableCollectionModifier().write(0, watcher.getWatchableObjects()); // Make the packet's // // one we created watcher.getWatchableObject(0); try { for (Player p : Bukkit.getOnlinePlayers()) { pm.sendServerPacket(p, packet); } } catch (InvocationTargetException e) { e.printStackTrace(); } } }); } I tried changing the packet listener to PacketType.Play.Server.ENTITY_METADATA... big mistake as it must be looking for the metadata of every entity on this server. Aka it lags the server, and it doesn't even fully fix the problem! Sprinting will cause it to flicker, and it actually pretty much makes sprinting unusable as it cancels the player sprint or something. I'm not looking to be spoon fed--I just need some guidance on how I SHOULD be doing this correctly so that no action the player does causes the packet's effect to go away. Thanks in advance
bump. really could use some help. Spent several hours trying to figure this out with no satisfactory solution
Your code seems a bit off, why are you adding the glow inside a listener for an update health packet? Why do you have a listener at all?
You don't need a packet listener, just send the right packet. And why using ProtocolLib at first place? Absraction and raw NMS is much faster than ProtocolLib and in fact you won't depend on it on every plugin you do.
Thanks for the feedback guys! I took a look at my code and realized how garbage it was lol, and scrapped it, ditched the ProtocolLib, gave NMS a shot and came up with this: Spoiler: Code Code (Text): package io.github.lukeeff; import java.lang.reflect.Field; import org.bukkit.Bukkit; import org.bukkit.ChatColor; import org.bukkit.craftbukkit.v1_15_R1.entity.CraftPlayer; import com.mojang.authlib.GameProfile; import net.minecraft.server.v1_15_R1.DataWatcherObject; import net.minecraft.server.v1_15_R1.EntityHuman; import net.minecraft.server.v1_15_R1.World; public class PlayerGlow extends EntityHuman { public PlayerGlow(World world, GameProfile gameprofile, CraftPlayer player) throws NoSuchFieldException, SecurityException, IllegalArgumentException, IllegalAccessException { super(world, gameprofile); Field field = EntityHuman.class.getDeclaredField("bq"); field.setAccessible(true); final DataWatcherObject<Byte> bq = (DataWatcherObject<Byte>) field.get(0); this.getDataWatcher().set(bq, (byte) 0x40); Bukkit.getConsoleSender().sendMessage(ChatColor.GREEN+"Finished PlayerGlow block."); } @Override public boolean isCreative() { // TODO Auto-generated method stub return false; } @Override public boolean isSpectator() { // TODO Auto-generated method stub return false; } } The good is the entirety of the code will run without any errors in console. Unfortunately, I'm missing something and I'm not sure what that is. Should I be sending packets or something? Is there a certain packet I'm supposed to be sending? Edit: Really doubt this is the culprit, but just in case, here's my main class: Spoiler: *Probably* Functional Code Code (Text): package io.github.lukeeff; import org.bukkit.Bukkit; import org.bukkit.ChatColor; import org.bukkit.craftbukkit.v1_15_R1.entity.CraftPlayer; import org.bukkit.event.EventHandler; import org.bukkit.event.Listener; import org.bukkit.event.player.PlayerJoinEvent; import org.bukkit.plugin.java.JavaPlugin; import net.minecraft.server.v1_15_R1.EntityHuman; public class NMSPractice extends JavaPlugin implements Listener { @Override public void onEnable() { this.getServer().getPluginManager().registerEvents(this, this); } @Override public void onDisable() { } @EventHandler public void onJoin(PlayerJoinEvent e) throws NoSuchFieldException, SecurityException, IllegalArgumentException, IllegalAccessException { CraftPlayer player = (CraftPlayer) e.getPlayer(); EntityHuman p = (EntityHuman) player.getHandle(); Bukkit.getConsoleSender().sendMessage(ChatColor.GREEN+"onJoin event called!"); new PlayerGlow(p.getWorld(),p.getProfile()); } } **** Okay, did some more editing. I updated the code above with my new stuff. Thanks