diff --git a/src/main/java/land/chipmunk/chipmunkbot/ChipmunkBot.java b/src/main/java/land/chipmunk/chipmunkbot/ChipmunkBot.java index 98e5c77..7d19cd1 100644 --- a/src/main/java/land/chipmunk/chipmunkbot/ChipmunkBot.java +++ b/src/main/java/land/chipmunk/chipmunkbot/ChipmunkBot.java @@ -21,6 +21,7 @@ public class ChipmunkBot extends Client { @Getter public final ChatCommandHandler chatCommandHandler = new ChatCommandHandler(this); @Getter public final PositionManager position = new PositionManager(this); @Getter public final CommandCore core = new CommandCore(this); + @Getter public final SelfCarePlugin selfCare = new SelfCarePlugin(this); public ChipmunkBot (ClientOptions options) { super(options); } } diff --git a/src/main/java/land/chipmunk/chipmunkbot/plugins/SelfCarePlugin.java b/src/main/java/land/chipmunk/chipmunkbot/plugins/SelfCarePlugin.java new file mode 100644 index 0000000..db1f4a8 --- /dev/null +++ b/src/main/java/land/chipmunk/chipmunkbot/plugins/SelfCarePlugin.java @@ -0,0 +1,97 @@ +package land.chipmunk.chipmunkbot.plugins; + +import land.chipmunk.chipmunkbot.ChipmunkBot; +import com.github.steveice10.packetlib.packet.Packet; +import com.github.steveice10.packetlib.Session; +import com.github.steveice10.packetlib.packet.PacketProtocol; +import com.github.steveice10.mc.protocol.MinecraftProtocol; +import com.github.steveice10.mc.protocol.data.game.entity.player.GameMode; +import com.github.steveice10.mc.protocol.data.ProtocolState; +import com.github.steveice10.mc.protocol.data.game.level.notify.GameEvent; +import com.github.steveice10.mc.protocol.data.game.level.notify.GameEventValue; +import com.github.steveice10.mc.protocol.data.game.entity.EntityEvent; +import com.github.steveice10.mc.protocol.data.game.ClientCommand; +import com.github.steveice10.packetlib.event.session.SessionAdapter; +import com.github.steveice10.packetlib.event.session.SessionListener; +import com.github.steveice10.packetlib.event.session.DisconnectedEvent; +import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundLoginPacket; +import com.github.steveice10.mc.protocol.packet.ingame.clientbound.level.ClientboundGameEventPacket; +import com.github.steveice10.mc.protocol.packet.ingame.clientbound.entity.ClientboundEntityEventPacket; +import com.github.steveice10.mc.protocol.packet.ingame.serverbound.ServerboundClientCommandPacket; +import lombok.Getter; +import lombok.Setter; +import java.util.Timer; +import java.util.TimerTask; + +public class SelfCarePlugin extends SessionAdapter { + private final ChipmunkBot client; + + @Getter @Setter private GameMode gamemode; + @Getter @Setter private int permissionLevel; + private Timer timer; + private int entityId; // TODO: Move entity id handling somewhere else + + public SelfCarePlugin (ChipmunkBot client) { + this.client = client; + client.addListener((SessionListener) this); + + final TimerTask task = new TimerTask() { + @Override + public void run () { + final Session session = client.session(); + final PacketProtocol protocol = session.getPacketProtocol(); + if (!session.isConnected() || (protocol instanceof MinecraftProtocol && ((MinecraftProtocol) protocol).getState() != ProtocolState.GAME)) return; + + // TODO: Maybe make it possible for other stuff to listen for ticks + tick(); + } + }; + + timer = new Timer(); + timer.schedule(task, 70, 70); + } + + public void tick () { + if (gamemode != GameMode.CREATIVE) client.chat().command("minecraft:gamemode creative"); + if (permissionLevel < 2) client.chat().command("minecraft:op @s[type=player]"); + } + + @Override + public void packetReceived (Session session, Packet packet) { + if (packet instanceof ClientboundGameEventPacket) packetReceived(session, (ClientboundGameEventPacket) packet); + else if (packet instanceof ClientboundGameEventPacket) packetReceived(session, (ClientboundGameEventPacket) packet); + else if (packet instanceof ClientboundEntityEventPacket) packetReceived(session, (ClientboundEntityEventPacket) packet); + else if (packet instanceof ClientboundLoginPacket) packetReceived(session, (ClientboundLoginPacket) packet); + } + + public void packetReceived (Session session, ClientboundGameEventPacket packet) { + final GameEvent notification = packet.getNotification(); + final GameEventValue value = packet.getValue(); + + if (notification == GameEvent.CHANGE_GAMEMODE) gamemode = (GameMode) value; + else if (notification == GameEvent.ENTER_CREDITS) session.send(new ServerboundClientCommandPacket(ClientCommand.RESPAWN)); + } + + public void packetReceived (Session session, ClientboundLoginPacket packet) { + entityId = packet.getEntityId(); // TODO: Move entity id handling somewhere else + gamemode = packet.getGameMode(); + } + + public void packetReceived (Session session, ClientboundEntityEventPacket packet) { + if (packet.getEntityId() != entityId) return; + final EntityEvent event = packet.getEvent(); + + if (event == EntityEvent.PLAYER_OP_PERMISSION_LEVEL_0) permissionLevel = 0; + else if (event == EntityEvent.PLAYER_OP_PERMISSION_LEVEL_1) permissionLevel = 1; + else if (event == EntityEvent.PLAYER_OP_PERMISSION_LEVEL_2) permissionLevel = 2; + else if (event == EntityEvent.PLAYER_OP_PERMISSION_LEVEL_3) permissionLevel = 3; + else if (event == EntityEvent.PLAYER_OP_PERMISSION_LEVEL_4) permissionLevel = 4; + } + + @Override + public void disconnected (DisconnectedEvent event) { + if (client.reconnectDelay() >= 0) return; + timer.cancel(); + timer.purge(); + } +}