From ed32646b52317604a08559d45d44d890a5b85638 Mon Sep 17 00:00:00 2001 From: Tomas Slusny Date: Sun, 29 Apr 2018 15:31:39 +0200 Subject: [PATCH] Add Cerberus plugin Add Cerberus plugin that will show order of ghosts in bottom right corner. Signed-off-by: Tomas Slusny --- .../plugins/cerberus/CerberusGhost.java | 67 +++++++++++++++ .../plugins/cerberus/CerberusOverlay.java | 72 ++++++++++++++++ .../plugins/cerberus/CerberusPlugin.java | 86 +++++++++++++++++++ 3 files changed, 225 insertions(+) create mode 100644 runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusGhost.java create mode 100644 runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusOverlay.java create mode 100644 runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusPlugin.java diff --git a/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusGhost.java b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusGhost.java new file mode 100644 index 0000000000..7bdf9d6788 --- /dev/null +++ b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusGhost.java @@ -0,0 +1,67 @@ +/* + * Copyright (c) 2018, Tomas Slusny + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR + * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +package net.runelite.client.plugins.cerberus; + +import java.util.HashMap; +import java.util.Map; +import java.util.Optional; +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import net.runelite.api.NPC; +import net.runelite.api.NpcID; +import net.runelite.api.Skill; + +@Getter +@RequiredArgsConstructor +public enum CerberusGhost +{ + RANGE(NpcID.SUMMONED_SOUL, Skill.RANGED), + MAGE(NpcID.SUMMONED_SOUL_5868, Skill.MAGIC), + MELEE(NpcID.SUMMONED_SOUL_5869, Skill.ATTACK); + + private static final Map MAP = new HashMap<>(); + private final int npcId; + private final Skill type; + + static + { + final CerberusGhost[] values = CerberusGhost.values(); + + for (final CerberusGhost ghost : values) + { + MAP.put(ghost.getNpcId(), ghost); + } + } + + /** + * Try to identify if NPC is ghost + * @param npc npc + * @return optional ghost + */ + public static Optional fromNPC(final NPC npc) + { + return npc == null ? Optional.empty() : Optional.ofNullable(MAP.get(npc.getId())); + } +} diff --git a/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusOverlay.java b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusOverlay.java new file mode 100644 index 0000000000..f4a4a3242d --- /dev/null +++ b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusOverlay.java @@ -0,0 +1,72 @@ +/* + * Copyright (c) 2018, Tomas Slusny + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR + * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +package net.runelite.client.plugins.cerberus; + +import java.awt.Dimension; +import java.awt.Graphics2D; +import javax.inject.Inject; +import javax.inject.Singleton; +import lombok.extern.slf4j.Slf4j; +import net.runelite.api.NPC; +import net.runelite.client.game.SkillIconManager; +import net.runelite.client.ui.overlay.Overlay; +import net.runelite.client.ui.overlay.OverlayPosition; +import net.runelite.client.ui.overlay.components.ImagePanelComponent; + +@Slf4j +@Singleton +public class CerberusOverlay extends Overlay +{ + private final CerberusPlugin plugin; + private final SkillIconManager iconManager; + + @Inject + CerberusOverlay(final CerberusPlugin plugin, final SkillIconManager iconManager) + { + this.plugin = plugin; + this.iconManager = iconManager; + setPosition(OverlayPosition.BOTTOM_RIGHT); + } + + @Override + public Dimension render(Graphics2D graphics) + { + if (plugin.getGhosts().isEmpty()) + { + return null; + } + + final ImagePanelComponent imagePanelComponent = new ImagePanelComponent(); + imagePanelComponent.setTitle("Ghost order"); + + for (final NPC npc : plugin.getGhosts()) + { + CerberusGhost.fromNPC(npc).ifPresent(ghost -> imagePanelComponent + .getImages().add(iconManager.getSkillImage(ghost.getType()))); + } + + return imagePanelComponent.render(graphics); + } +} diff --git a/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusPlugin.java b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusPlugin.java new file mode 100644 index 0000000000..d46ad4cd07 --- /dev/null +++ b/runelite-client/src/main/java/net/runelite/client/plugins/cerberus/CerberusPlugin.java @@ -0,0 +1,86 @@ +/* + * Copyright (c) 2018, Tomas Slusny + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR + * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package net.runelite.client.plugins.cerberus; + +import com.google.common.eventbus.Subscribe; +import java.util.ArrayList; +import java.util.List; +import javax.inject.Inject; +import javax.inject.Singleton; +import lombok.Getter; +import net.runelite.api.NPC; +import net.runelite.api.events.NpcDespawned; +import net.runelite.api.events.NpcSpawned; +import net.runelite.client.plugins.Plugin; +import net.runelite.client.plugins.PluginDescriptor; +import net.runelite.client.ui.overlay.Overlay; + +@PluginDescriptor(name = "Cerberus") +@Singleton +public class CerberusPlugin extends Plugin +{ + @Getter + private final List ghosts = new ArrayList<>(); + + @Inject + private CerberusOverlay overlay; + + @Override + protected void shutDown() throws Exception + { + ghosts.clear(); + } + + @Override + public Overlay getOverlay() + { + return overlay; + } + + @Subscribe + public void onNpcSpawned(final NpcSpawned event) + { + final NPC npc = event.getNpc(); + + CerberusGhost.fromNPC(npc).ifPresent(ghost -> + { + if (ghosts.size() == CerberusGhost.values().length) + { + // Reset ghosts as this is new ghost wave + ghosts.clear(); + } + + ghosts.add(npc); + ghosts.sort((a, b) -> Integer.compare(b.getLocalLocation().getY(), a.getLocalLocation().getY())); + }); + } + + @Subscribe + public void onNpcDespawned(final NpcDespawned event) + { + ghosts.remove(event.getNpc()); + } +}