Skip to content

Instantly share code, notes, and snippets.

@vemacs
Created August 19, 2015 02:05
Show Gist options
  • Select an option

  • Save vemacs/9c1d73cb759b96ca5e34 to your computer and use it in GitHub Desktop.

Select an option

Save vemacs/9c1d73cb759b96ca5e34 to your computer and use it in GitHub Desktop.
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
public class ReflPackets {
private String serverVersion;
public ReflPackets() {
String name = Bukkit.getServer().getClass().getName();
String[] parts = name.split("\\.");
serverVersion = parts[3];
TabHFBukkit.instance.getLogger().info("Detected NMS/OBC package version " + serverVersion);
}
public Class<?> getNMSClass(String className) {
String fullName = "net.minecraft.server." + serverVersion + "." + className;
Class<?> clazz = null;
try {
clazz = Class.forName(fullName);
} catch (Exception e) {
e.printStackTrace();
}
return clazz;
}
private Method getHandle;
private Field playerConnection;
private Class<?> chatSerializer;
private Method serialize;
private Method sendPacket;
public void sendTabPacket(Player p) {
try {
if (getHandle == null) {
getHandle = p.getClass().getDeclaredMethod("getHandle");
getHandle.setAccessible(true);
}
Object entityPlayer = getHandle.invoke(p);
if (playerConnection == null) {
playerConnection = entityPlayer.getClass().getDeclaredField("playerConnection");
playerConnection.setAccessible(true);
}
Object conn = playerConnection.get(entityPlayer);
if (chatSerializer == null) {
chatSerializer = getNMSClass("IChatBaseComponent$ChatSerializer");
// still null?
if (chatSerializer == null) {
chatSerializer = getNMSClass("ChatSerializer");
}
}
if (serialize == null) {
serialize = chatSerializer.getDeclaredMethod("a", String.class);
serialize.setAccessible(true);
}
String header = TabHFBukkit.instance.header;
String footer = TabHFBukkit.instance.footer;
int onlinePlayers = Bukkit.getServer().getOnlinePlayers().size();
Object headerComp = serialize.invoke(null, header.replace("{PLAYER}", p.getName())
.replace("{ONLINE}", Integer.toString(onlinePlayers)));
Object footerComp = serialize.invoke(null, footer.replace("{PLAYER}", p.getName())
.replace("{ONLINE}", Integer.toString(onlinePlayers)));
if (sendPacket == null) {
sendPacket = conn.getClass().getDeclaredMethod("sendPacket", getNMSClass("Packet"));
sendPacket.setAccessible(true);
}
Object headerFooterPacket = getHeaderFooterPacket(headerComp, footerComp);
sendPacket.invoke(conn, headerFooterPacket);
} catch (Exception e) {
e.printStackTrace();
}
}
private Constructor headerFooterPacketConstructor;
private Field bField;
private Object getHeaderFooterPacket(Object header, Object footer) {
try {
Class<?> packetClass = getNMSClass("PacketPlayOutPlayerListHeaderFooter");
if (headerFooterPacketConstructor == null) {
headerFooterPacketConstructor = packetClass.getDeclaredConstructor(getNMSClass("IChatBaseComponent"));
headerFooterPacketConstructor.setAccessible(true);
}
Object headerFooter = headerFooterPacketConstructor.newInstance(header);
if (bField == null) {
bField = headerFooter.getClass().getDeclaredField("b");
bField.setAccessible(true);
}
bField.set(headerFooter, footer);
return headerFooter;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment