lulu2002/DatouNms

playDeathAnimation 存在的問題

Closed this issue · 4 comments

me.lulu.datounms.v1_8_R3 的 CraftCommonNMS 有一點小錯誤
在 1 Ticks 之後運行的 Runnable, 應該需要把真正的玩家加回來, 不然的話玩家會在Tablist上消失

這個是修改後的代碼: (我有把整個method改過一點點, 不過運作原理大致上相同)

//Credit: https://github.com/lulu2002/DatouNms/blob/master/src/main/java/me/lulu/datounms/v1_8_R3/CraftCommonNMS.java
    public static void playDeathAnimation(Player player, List<Player> viewers) {
        MinecraftServer nmsServer = ((CraftServer) Bukkit.getServer()).getServer();
        WorldServer nmsWorld = (( CraftWorld ) player.getWorld()).getHandle();
        CraftPlayer cp = (CraftPlayer) player;
        EntityPlayer npc = new EntityPlayer(nmsServer, nmsWorld, cp.getProfile(), new PlayerInteractManager(nmsWorld));
        npc.setLocation(player.getLocation().getX(), player.getLocation().getY(), player.getLocation().getZ(), player.getLocation().getYaw(), player.getLocation().getPitch());
        PacketPlayOutPlayerInfo removeRealPlayer = new PacketPlayOutPlayerInfo(PacketPlayOutPlayerInfo.EnumPlayerInfoAction.REMOVE_PLAYER, cp.getHandle());
        PacketPlayOutPlayerInfo addPlayer = new PacketPlayOutPlayerInfo(PacketPlayOutPlayerInfo.EnumPlayerInfoAction.ADD_PLAYER, npc);
        PacketPlayOutPlayerInfo removePlayer = new PacketPlayOutPlayerInfo(PacketPlayOutPlayerInfo.EnumPlayerInfoAction.REMOVE_PLAYER, npc);
        PacketPlayOutPlayerInfo addRealPlayer = new PacketPlayOutPlayerInfo(PacketPlayOutPlayerInfo.EnumPlayerInfoAction.ADD_PLAYER, cp.getHandle());
        PacketPlayOutNamedEntitySpawn entitySpawn = new PacketPlayOutNamedEntitySpawn(npc);
        PacketPlayOutEntityStatus entityDeath = new PacketPlayOutEntityStatus(npc, ( byte ) 3);

        for (Player o : viewers) {
            PlayerConnection connection = ((CraftPlayer) o).getHandle().playerConnection;
            connection.sendPacket(removeRealPlayer);
            connection.sendPacket(addPlayer);
            connection.sendPacket(entitySpawn);
            connection.sendPacket(entityDeath);
        }
        Tasks.runLater(()-> {
            for (Player o : viewers) {
                if (o.isOnline()) {
                    PlayerConnection connection = ((CraftPlayer) o).getHandle().playerConnection;
                    connection.sendPacket(removePlayer);
                    connection.sendPacket(addRealPlayer);
                }
            }
        }, 1L);
    }

對了, 在 connection.sendPacket(addRealPlayer); 運行之前應該要先檢查 if (cp.isOnline()), 不然的話 tablist 就會有一個已離線的玩家

感謝你~~ 有意願幫忙做個 PR 嗎?這個 credit 留給你完成它

開啟了 :D #3

Done,感謝啦!