Merge branch 'master' of https://github.com/runelite-extended/runelite into basebase

This commit is contained in:
7ate9
2019-07-01 13:15:40 -04:00
35 changed files with 1758 additions and 731 deletions

View File

@@ -184,6 +184,25 @@ public class WorldArea
return isInMeleeDistance(new WorldArea(other, 1, 1)); return isInMeleeDistance(new WorldArea(other, 1, 1));
} }
/**
* Checks whether this area is within melee distance of another without blocking in-between.
*
* @param client the client to test in
* @param other the other area
* @return true if in melee distance without blocking, false otherwise
*/
public boolean canMelee(Client client, WorldArea other)
{
if (isInMeleeDistance(other))
{
Point p1 = this.getComparisonPoint(other);
Point p2 = other.getComparisonPoint(this);
WorldArea w1 = new WorldArea(p1.getX(), p1.getY() , 1, 1, this.getPlane());
return (w1.canTravelInDirection(client, p2.getX() - p1.getX(), p2.getY() - p1.getY()));
}
return false;
}
/** /**
* Checks whether this area intersects with another. * Checks whether this area intersects with another.
* *

View File

@@ -284,6 +284,11 @@
<artifactId>asm-all</artifactId> <artifactId>asm-all</artifactId>
<version>6.0_BETA</version> <version>6.0_BETA</version>
</dependency> </dependency>
<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
<version>20180813</version>
</dependency>
</dependencies> </dependencies>
<build> <build>

View File

@@ -0,0 +1,78 @@
package net.runelite.client.plugins.chattranslation;
import net.runelite.client.config.Config;
import net.runelite.client.config.ConfigGroup;
import net.runelite.client.config.ConfigItem;
@ConfigGroup("chattranslation")
public interface ChatTranslationConfig extends Config
{
@ConfigItem(
keyName = "publicChat",
name = "Translate incoming Messages",
description = "Would you like to Translate Public Chat?",
position = 0,
group = "Public Chat Translation",
hidden = true
)
default boolean publicChat()
{
return false;
}
@ConfigItem(
keyName = "translateOptionVisable",
name = "Show 'Translate' menu option",
description = "Adds 'Translate' to the right-click menu in the Chatbox.",
position = 1,
group = "Public Chat Translation",
hidden = true
// unhide = "publicChat"
)
default boolean translateOptionVisable()
{
return false;
}
@ConfigItem(
keyName = "publicTargetLanguage",
name = "Target Language",
description = "Language to translate messages too.",
position = 2,
group = "Public Chat Translation",
hidden = true
// unhide = "publicChat"
)
default Languages publicTargetLanguage()
{
return Languages.ENGLISH;
}
@ConfigItem(
keyName = "playerChat",
name = "Translate outgoing Messages",
description = "Would you like to Translate your Messages?",
position = 3,
group = "Player Message Translation"
)
default boolean playerChat()
{
return false;
}
@ConfigItem(
keyName = "playerTargetLanguage",
name = "Target Language",
description = "Language to translate messages too.",
position = 4,
group = "Player Message Translation",
hidden = true,
unhide = "playerChat"
)
default Languages playerTargetLanguage()
{
return Languages.SPANISH;
}
}

View File

@@ -0,0 +1,236 @@
package net.runelite.client.plugins.chattranslation;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ObjectArrays;
import com.google.inject.Provides;
import net.runelite.api.*;
import net.runelite.api.events.ChatMessage;
import net.runelite.api.events.MenuEntryAdded;
import net.runelite.api.events.PlayerMenuOptionClicked;
import net.runelite.api.widgets.Widget;
import net.runelite.api.widgets.WidgetInfo;
import net.runelite.client.callback.ClientThread;
import net.runelite.client.chat.ChatMessageManager;
import net.runelite.client.config.ConfigManager;
import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.input.KeyListener;
import net.runelite.client.input.KeyManager;
import net.runelite.client.menus.MenuManager;
import net.runelite.client.plugins.Plugin;
import net.runelite.client.plugins.PluginDescriptor;
import net.runelite.client.plugins.PluginType;
import org.apache.commons.lang3.ArrayUtils;
import javax.inject.Inject;
import javax.inject.Provider;
import java.awt.event.KeyEvent;
@PluginDescriptor(
name = "Chat Translator",
description = "Translates messages from one Language to another.",
tags = {"translate", "language", "english", "spanish", "dutch", "french"},
type = PluginType.UTILITY
)
public class ChatTranslationPlugin extends Plugin implements KeyListener
{
private static final String TRANSLATE = "Translate";
private static final ImmutableList<String> AFTER_OPTIONS = ImmutableList.of("Message", "Add ignore", "Remove friend", "Kick");
@Inject
private Client client;
@Inject
private ClientThread clientThread;
@Inject
private Provider<MenuManager> menuManager;
@Inject
private ChatMessageManager chatMessageManager;
@Inject
private KeyManager keyManager;
@Inject
private ChatTranslationConfig config;
@Provides
ChatTranslationConfig provideConfig(ConfigManager configManager)
{
return configManager.getConfig(ChatTranslationConfig.class);
}
@Override
protected void startUp() throws Exception
{
if (client != null)
{
if (config.translateOptionVisable())
{
menuManager.get().addPlayerMenuItem(TRANSLATE);
}
}
keyManager.registerKeyListener(this);
}
@Override
protected void shutDown() throws Exception
{
if (client != null)
{
if (config.translateOptionVisable())
{
menuManager.get().removePlayerMenuItem(TRANSLATE);
}
}
keyManager.unregisterKeyListener(this);
}
@Subscribe
public void onPlayerMenuOptionClicked(PlayerMenuOptionClicked event)
{
if (event.getMenuOption().equals(TRANSLATE))
{
//TODO: Translate selected message.
}
}
@Subscribe
public void onMenuEntryAdded(MenuEntryAdded event)
{
if (!config.translateOptionVisable())
{
return;
}
int groupId = WidgetInfo.TO_GROUP(event.getActionParam1());
String option = event.getOption();
if (groupId == WidgetInfo.CHATBOX.getGroupId())
{
boolean after;
if (!AFTER_OPTIONS.contains(option))
{
return;
}
final MenuEntry lookup = new MenuEntry();
lookup.setOption(TRANSLATE);
lookup.setTarget(event.getTarget());
lookup.setType(MenuAction.RUNELITE.getId());
lookup.setParam0(event.getActionParam0());
lookup.setParam1(event.getActionParam1());
lookup.setIdentifier(event.getIdentifier());
MenuEntry[] newMenu = ObjectArrays.concat(lookup, client.getMenuEntries());
int menuEntryCount = newMenu.length;
ArrayUtils.swap(newMenu, menuEntryCount - 1, menuEntryCount - 2);
client.setMenuEntries(newMenu);
}
}
@Subscribe
public void onChatMessage(ChatMessage chatMessage)
{
if (client.getGameState() != GameState.LOADING && client.getGameState() != GameState.LOGGED_IN)
{
return;
}
switch (chatMessage.getType())
{
case PUBLICCHAT:
case MODCHAT:
if (!config.publicChat())
{
return;
}
break;
default:
return;
}
String message = chatMessage.getMessage();
Translator translator = new Translator();
try
{
//Automatically check language of message and translate to selected language.
String translation = translator.translate("auto", config.publicTargetLanguage().toString(), message);
if (translation != null)
{
final MessageNode messageNode = chatMessage.getMessageNode();
messageNode.setRuneLiteFormatMessage(translation);
chatMessageManager.update(messageNode);
}
}
catch (Exception e)
{
e.printStackTrace();
}
client.refreshChat();
}
@Override
public void keyPressed(KeyEvent event)
{
if (client.getGameState() != GameState.LOADING && client.getGameState() != GameState.LOGGED_IN)
{
return;
}
if (!config.playerChat())
{
return;
}
Widget chatboxParent = client.getWidget(WidgetInfo.CHATBOX_PARENT);
if (chatboxParent != null && chatboxParent.getOnKeyListener() != null)
{
if (event.getKeyCode() == 0xA)
{
event.consume();
Translator translator = new Translator();
String message = client.getVar(VarClientStr.CHATBOX_TYPED_TEXT);
try
{
//Automatically check language of message and translate to selected language.
String translation = translator.translate("auto", config.playerTargetLanguage().toString(), message);
if (translation != null)
{
client.setVar(VarClientStr.CHATBOX_TYPED_TEXT, translation);
clientThread.invoke(() ->
{
client.runScript(96, 0, translation);
});
}
client.setVar(VarClientStr.CHATBOX_TYPED_TEXT, "");
}
catch (Exception e)
{
e.printStackTrace();
}
}
}
}
@Override
public void keyReleased(KeyEvent e)
{
// Nothing.
}
@Override
public void keyTyped(KeyEvent e)
{
// Nothing.
}
}

View File

@@ -0,0 +1,24 @@
package net.runelite.client.plugins.chattranslation;
public enum Languages
{
ENGLISH("en"),
DUTCH("nl"),
SPANISH("es"),
FRENCH("fr");
private final String shortName;
Languages(String shortName)
{
this.shortName = shortName;
}
@Override
public String toString()
{
return shortName;
}
}

View File

@@ -0,0 +1,46 @@
package net.runelite.client.plugins.chattranslation;
import org.json.JSONArray;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
public class Translator
{
public String translate(String source, String target, String message) throws Exception
{
String url = "https://translate.googleapis.com/translate_a/single?client=gtx&sl=" + source + "&tl=" + target + "&dt=t&q=" + URLEncoder.encode(message, "UTF-8");
URL obj = new URL(url);
HttpURLConnection con = (HttpURLConnection) obj.openConnection();
con.setRequestProperty("User-Agent", "Mozilla/5.0");
BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
String inputLine;
StringBuffer response = new StringBuffer();
while ((inputLine = in.readLine()) != null)
{
response.append(inputLine);
}
in.close();
return parseResult(response.toString());
}
private String parseResult(String inputJson) throws Exception
{
//TODO: find a way to do this using google.gson
JSONArray jsonArray = new JSONArray(inputJson);
JSONArray jsonArray2 = (JSONArray) jsonArray.get(0);
JSONArray jsonArray3 = (JSONArray) jsonArray2.get(0);
return jsonArray3.get(0).toString();
}
}

View File

@@ -29,7 +29,7 @@ public enum DigsitePendantMode
{ {
DIGSITE("Digsite"), DIGSITE("Digsite"),
FOSSIL_ISLAND("Fossil Island"), FOSSIL_ISLAND("Fossil Island"),
LITHKREN("Lithkren"); LITHKREN("Lithkren Dungeon");
private final String name; private final String name;

View File

@@ -25,7 +25,9 @@
package net.runelite.client.plugins.npchighlight; package net.runelite.client.plugins.npchighlight;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashSet;
import java.util.List; import java.util.List;
import java.util.Set;
import lombok.Getter; import lombok.Getter;
import lombok.Setter; import lombok.Setter;
import net.runelite.api.NPC; import net.runelite.api.NPC;
@@ -38,7 +40,7 @@ class MemorizedNpc
private int npcIndex; private int npcIndex;
@Getter @Getter
private String npcName; private Set<String> npcNames;
@Getter @Getter
private int npcSize; private int npcSize;
@@ -63,7 +65,8 @@ class MemorizedNpc
MemorizedNpc(NPC npc) MemorizedNpc(NPC npc)
{ {
this.npcName = npc.getName(); this.npcNames = new HashSet<>();
this.npcNames.add(npc.getName());
this.npcIndex = npc.getIndex(); this.npcIndex = npc.getIndex();
this.possibleRespawnLocations = new ArrayList<>(); this.possibleRespawnLocations = new ArrayList<>();
this.respawnTime = -1; this.respawnTime = -1;

View File

@@ -34,6 +34,7 @@ import java.util.Arrays;
import java.util.Collections; import java.util.Collections;
import java.util.HashMap; import java.util.HashMap;
import java.util.HashSet; import java.util.HashSet;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Set; import java.util.Set;
@@ -58,6 +59,7 @@ import net.runelite.api.events.GameTick;
import net.runelite.api.events.GraphicsObjectCreated; import net.runelite.api.events.GraphicsObjectCreated;
import net.runelite.api.events.MenuEntryAdded; import net.runelite.api.events.MenuEntryAdded;
import net.runelite.api.events.MenuOptionClicked; import net.runelite.api.events.MenuOptionClicked;
import net.runelite.api.events.NpcCompositionChanged;
import net.runelite.api.events.NpcDespawned; import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned; import net.runelite.api.events.NpcSpawned;
import net.runelite.client.callback.ClientThread; import net.runelite.client.callback.ClientThread;
@@ -304,14 +306,15 @@ public class NpcIndicatorsPlugin extends Plugin
if (removed) if (removed)
{ {
highlightedNpcs.remove(npc); MemorizedNpc mn = memorizedNpcs.get(npc.getIndex());
memorizedNpcs.remove(npc.getIndex()); if (mn != null && isNpcMemorizationUnnecessary(mn))
{
memorizedNpcs.remove(npc.getIndex());
}
} }
else else
{ {
memorizeNpc(npc);
npcTags.add(id); npcTags.add(id);
highlightedNpcs.add(npc);
} }
click.consume(); click.consume();
@@ -320,30 +323,28 @@ public class NpcIndicatorsPlugin extends Plugin
@Subscribe @Subscribe
public void onNpcSpawned(NpcSpawned npcSpawned) public void onNpcSpawned(NpcSpawned npcSpawned)
{ {
final NPC npc = npcSpawned.getNpc(); NPC npc = npcSpawned.getNpc();
final String npcName = npc.getName(); highlightNpcIfMatch(npc);
if (npcName == null) if (memorizedNpcs.containsKey(npc.getIndex()))
{ {
return;
}
if (npcTags.contains(npc.getIndex()))
{
memorizeNpc(npc);
highlightedNpcs.add(npc);
spawnedNpcsThisTick.add(npc); spawnedNpcsThisTick.add(npc);
return;
} }
}
for (String highlight : highlights) @Subscribe
public void onNpcCompositionChanged(NpcCompositionChanged event)
{
NPC npc = event.getNpc();
highlightNpcIfMatch(npc);
MemorizedNpc mn = memorizedNpcs.get(npc.getIndex());
if (mn != null)
{ {
if (WildcardMatcher.matches(highlight, npcName)) String npcName = npc.getName();
if (npcName != null)
{ {
memorizeNpc(npc); mn.getNpcNames().add(npcName);
highlightedNpcs.add(npc);
spawnedNpcsThisTick.add(npc);
break;
} }
} }
} }
@@ -428,12 +429,59 @@ public class NpcIndicatorsPlugin extends Plugin
return new WorldPoint(currWP.getX() - dx, currWP.getY() - dy, currWP.getPlane()); return new WorldPoint(currWP.getX() - dx, currWP.getY() - dy, currWP.getPlane());
} }
private void highlightNpcIfMatch(final NPC npc)
{
if (npcTags.contains(npc.getIndex()))
{
memorizeNpc(npc);
highlightedNpcs.add(npc);
return;
}
final String npcName = npc.getName();
if (npcName != null)
{
for (String highlight : highlights)
{
if (WildcardMatcher.matches(highlight, npcName))
{
memorizeNpc(npc);
highlightedNpcs.add(npc);
return;
}
}
}
highlightedNpcs.remove(npc);
}
private void memorizeNpc(NPC npc) private void memorizeNpc(NPC npc)
{ {
final int npcIndex = npc.getIndex(); final int npcIndex = npc.getIndex();
memorizedNpcs.putIfAbsent(npcIndex, new MemorizedNpc(npc)); memorizedNpcs.putIfAbsent(npcIndex, new MemorizedNpc(npc));
} }
private boolean isNpcMemorizationUnnecessary(final MemorizedNpc mn)
{
if (npcTags.contains(mn.getNpcIndex()))
{
return false;
}
for (String npcName : mn.getNpcNames())
{
for (String highlight : highlights)
{
if (WildcardMatcher.matches(highlight, npcName))
{
return false;
}
}
}
return true;
}
private void removeOldHighlightedRespawns() private void removeOldHighlightedRespawns()
{ {
deadNpcsToDisplay.values().removeIf(x -> x.getDiedOnTick() + x.getRespawnTime() <= client.getTickCount() + 1); deadNpcsToDisplay.values().removeIf(x -> x.getDiedOnTick() + x.getRespawnTime() <= client.getTickCount() + 1);
@@ -464,34 +512,21 @@ public class NpcIndicatorsPlugin extends Plugin
return; return;
} }
outer: Iterator<Map.Entry<Integer, MemorizedNpc>> it = memorizedNpcs.entrySet().iterator();
while (it.hasNext())
{
MemorizedNpc mn = it.next().getValue();
if (isNpcMemorizationUnnecessary(mn))
{
deadNpcsToDisplay.remove(mn.getNpcIndex());
it.remove();
}
}
for (NPC npc : client.getNpcs()) for (NPC npc : client.getNpcs())
{ {
final String npcName = npc.getName(); highlightNpcIfMatch(npc);
if (npcName == null)
{
continue;
}
if (npcTags.contains(npc.getIndex()))
{
highlightedNpcs.add(npc);
continue;
}
for (String highlight : highlights)
{
if (WildcardMatcher.matches(highlight, npcName))
{
memorizeNpc(npc);
highlightedNpcs.add(npc);
continue outer;
}
}
// NPC is not highlighted
memorizedNpcs.remove(npc.getIndex());
} }
} }
@@ -524,7 +559,7 @@ public class NpcIndicatorsPlugin extends Plugin
if (!mn.getPossibleRespawnLocations().isEmpty()) if (!mn.getPossibleRespawnLocations().isEmpty())
{ {
log.debug("Starting {} tick countdown for {}", mn.getRespawnTime(), mn.getNpcName()); log.debug("Starting {} tick countdown for {}", mn.getRespawnTime(), mn.getNpcNames().iterator().next());
deadNpcsToDisplay.put(mn.getNpcIndex(), mn); deadNpcsToDisplay.put(mn.getNpcIndex(), mn);
} }
} }

View File

@@ -0,0 +1,84 @@
/*
* Copyright (c) 2019, GeChallengeM <https://github.com/GeChallengeM>
* 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.npcstatus;
import java.awt.Color;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.Setter;
import net.runelite.api.NPC;
import net.runelite.api.coords.WorldArea;
import net.runelite.api.Actor;
@Getter
class MemorizedNPC
{
private NPC npc;
private int npcIndex;
private String npcName;
private int attackSpeed;
@Setter
private int combatTimerEnd;
@Setter
private int timeLeft;
@Setter
private int flinchTimerEnd;
@Setter
private Status status;
@Setter
private WorldArea lastnpcarea;
@Setter
private Actor lastinteracted;
@Setter
private int lastspotanimation;
MemorizedNPC(NPC npc, int attackSpeed, WorldArea worldArea)
{
this.npc = npc;
this.npcIndex = npc.getIndex();
this.npcName = npc.getName();
this.attackSpeed = attackSpeed;
this.combatTimerEnd = -1;
this.flinchTimerEnd = -1;
this.timeLeft = 0;
this.status = Status.OUT_OF_COMBAT;
this.lastnpcarea = worldArea;
this.lastinteracted = null;
this.lastspotanimation = -1;
}
@Getter
@AllArgsConstructor
enum Status
{
FLINCHING("Flinching", Color.GREEN),
IN_COMBAT_DELAY("In Combat Delay", Color.ORANGE),
IN_COMBAT("In Combat", Color.RED),
OUT_OF_COMBAT("Out of Combat", Color.BLUE);
private String name;
private Color color;
}
}

View File

@@ -0,0 +1,43 @@
/*
* Copyright (c) 2019, GeChallengeM <https://github.com/GeChallengeM>
* 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.npcstatus;
import net.runelite.client.config.Config;
import net.runelite.client.config.ConfigGroup;
import net.runelite.client.config.ConfigItem;
@ConfigGroup("npcstatus")
public interface NpcStatusConfig extends Config
{
@ConfigItem(
keyName = "AttackRange",
name = "NPC Attack range",
description = "The attack range of the NPC"
)
default int getRange()
{
return 1;
}
}

View File

@@ -0,0 +1,89 @@
/*
* Copyright (c) 2018, GeChallengeM <https://github.com/GeChallengeM>
* 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.npcstatus;
import java.awt.Dimension;
import java.awt.Graphics2D;
import javax.inject.Inject;
import net.runelite.api.Client;
import net.runelite.api.Point;
import net.runelite.client.ui.overlay.Overlay;
import net.runelite.client.ui.overlay.OverlayLayer;
import net.runelite.client.ui.overlay.OverlayPosition;
import net.runelite.client.ui.overlay.OverlayUtil;
public class NpcStatusOverlay extends Overlay
{
private final Client client;
private final NpcStatusPlugin plugin;
@Inject
NpcStatusOverlay(Client client, NpcStatusPlugin plugin)
{
this.client = client;
this.plugin = plugin;
setPosition(OverlayPosition.DYNAMIC);
setLayer(OverlayLayer.ABOVE_SCENE);
}
@Override
public Dimension render(Graphics2D graphics)
{
for (MemorizedNPC npc : plugin.getMemorizedNPCs())
{
if (npc.getNpc().getInteracting() == null)
{
continue;
}
if (npc.getNpc().getInteracting() == client.getLocalPlayer() || client.getLocalPlayer().getInteracting() == npc.getNpc())
{
switch (npc.getStatus())
{
case FLINCHING:
npc.setTimeLeft(Math.max(0, npc.getFlinchTimerEnd() - client.getTickCount()));
break;
case IN_COMBAT_DELAY:
npc.setTimeLeft(Math.max(0, npc.getCombatTimerEnd() - client.getTickCount() - 7));
break;
case IN_COMBAT:
npc.setTimeLeft(Math.max(0, npc.getCombatTimerEnd() - client.getTickCount()));
break;
case OUT_OF_COMBAT:
default:
npc.setTimeLeft(0);
break;
}
Point textLocation = npc.getNpc().getCanvasTextLocation(graphics, Integer.toString(npc.getTimeLeft()), npc.getNpc().getLogicalHeight() + 40);
if (textLocation != null)
{
OverlayUtil.renderTextLocation(graphics, textLocation, Integer.toString(npc.getTimeLeft()), npc.getStatus().getColor());
}
}
}
return null;
}
}

View File

@@ -0,0 +1,231 @@
/*
* Copyright (c) 2019, GeChallengeM <https://github.com/GeChallengeM>
* 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.npcstatus;
import com.google.inject.Provides;
import java.time.Instant;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Set;
import javax.inject.Inject;
import lombok.AccessLevel;
import lombok.Getter;
import lombok.extern.slf4j.Slf4j;
import net.runelite.api.Client;
import net.runelite.api.GameState;
import net.runelite.api.GraphicID;
import net.runelite.api.Hitsplat;
import net.runelite.api.NPC;
import net.runelite.api.coords.WorldArea;
import net.runelite.api.events.GameStateChanged;
import net.runelite.api.events.GameTick;
import net.runelite.api.events.HitsplatApplied;
import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned;
import net.runelite.client.config.ConfigManager;
import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.game.ItemManager;
import net.runelite.client.game.NPCManager;
import net.runelite.client.plugins.Plugin;
import net.runelite.client.plugins.PluginDescriptor;
import net.runelite.client.ui.overlay.OverlayManager;
@Slf4j
@PluginDescriptor(
name = "NPC Status Timer",
description = "Adds a timer on NPC's for their attacks and flinching.",
tags = {"flinch", "npc"},
enabledByDefault = false
)
public class NpcStatusPlugin extends Plugin
{
@Getter(AccessLevel.PACKAGE)
private final Set<MemorizedNPC> memorizedNPCs = new HashSet<>();
@Inject
private Client client;
@Inject
private OverlayManager overlayManager;
@Inject
private ItemManager itemManager;
@Inject
private NPCManager npcManager;
@Inject
private NpcStatusConfig config;
@Inject
private NpcStatusOverlay npcStatusOverlay;
@Getter(AccessLevel.PACKAGE)
private Instant lastTickUpdate;
private WorldArea lastPlayerLocation;
@Provides
NpcStatusConfig provideConfig(ConfigManager configManager)
{
return configManager.getConfig(NpcStatusConfig.class);
}
@Override
protected void startUp() throws Exception
{
overlayManager.add(npcStatusOverlay);
}
@Override
protected void shutDown() throws Exception
{
overlayManager.remove(npcStatusOverlay);
memorizedNPCs.clear();
}
@Subscribe
public void onNpcSpawned(NpcSpawned npcSpawned)
{
final NPC npc = npcSpawned.getNpc();
final String npcName = npc.getName();
if (npcName == null || !Arrays.asList(npc.getDefinition().getActions()).contains("Attack"))
{
return;
}
memorizedNPCs.add(new MemorizedNPC(npc, npcManager.getAttackSpeed(npc.getId()), npc.getWorldArea()));
}
@Subscribe
public void onNpcDespawned(NpcDespawned npcDespawned)
{
final NPC npc = npcDespawned.getNpc();
memorizedNPCs.removeIf(c -> c.getNpc() == npc);
}
@Subscribe
public void onGameStateChanged(GameStateChanged event)
{
if (event.getGameState() == GameState.LOGIN_SCREEN ||
event.getGameState() == GameState.HOPPING)
{
memorizedNPCs.clear();
}
}
@Subscribe
public void onHitsplatApplied(HitsplatApplied event)
{
if (event.getActor().getInteracting() != client.getLocalPlayer())
{
return;
}
final Hitsplat hitsplat = event.getHitsplat();
if (hitsplat.getHitsplatType() == Hitsplat.HitsplatType.DAMAGE || hitsplat.getHitsplatType() == Hitsplat.HitsplatType.BLOCK)
{
if (event.getActor() instanceof NPC)
{
for (MemorizedNPC mn : memorizedNPCs)
{
if (mn.getStatus() == MemorizedNPC.Status.OUT_OF_COMBAT || (mn.getStatus() == MemorizedNPC.Status.IN_COMBAT && mn.getCombatTimerEnd() - client.getTickCount() < 1) || mn.getLastinteracted() == null)
{
mn.setStatus(MemorizedNPC.Status.FLINCHING);
mn.setCombatTimerEnd(-1);
mn.setFlinchTimerEnd(client.getTickCount() + mn.getAttackSpeed() / 2 + 1);
}
}
}
}
}
private void checkStatus()
{
for (MemorizedNPC npc : memorizedNPCs)
{
final int ATTACK_SPEED = npc.getAttackSpeed();
final double CombatTime = npc.getCombatTimerEnd() - client.getTickCount();
final double FlinchTime = npc.getFlinchTimerEnd() - client.getTickCount();
if (npc.getNpc().getWorldArea() == null)
{
continue;
}
if (npc.getNpc().getInteracting() == client.getLocalPlayer())
{
if (npc.getLastspotanimation() == GraphicID.SPLASH && npc.getNpc().getSpotAnimation() == GraphicID.SPLASH) //For splash flinching
{
npc.setLastspotanimation(-1);
if ((npc.getStatus() == MemorizedNPC.Status.OUT_OF_COMBAT ) || npc.getLastinteracted() == null)
{
npc.setStatus(MemorizedNPC.Status.FLINCHING);
npc.setCombatTimerEnd(-1);
npc.setFlinchTimerEnd(client.getTickCount() + ATTACK_SPEED / 2 + 1);
npc.setLastnpcarea(npc.getNpc().getWorldArea());
npc.setLastinteracted(npc.getNpc().getInteracting());
continue;
}
}
//Checks: will the NPC attack this tick?
if (((npc.getNpc().getWorldArea().canMelee(client, lastPlayerLocation) && config.getRange() == 1) //Separate mechanics for meleerange-only NPC's because they have extra collisiondata checks (fences etc.) and can't attack diagonally
|| (lastPlayerLocation.hasLineOfSightTo(client, npc.getNpc().getWorldArea()) && npc.getNpc().getWorldArea().distanceTo(lastPlayerLocation) <= config.getRange() && config.getRange() > 1))
&& ((npc.getStatus() != MemorizedNPC.Status.FLINCHING && CombatTime < 9) || (npc.getStatus() == MemorizedNPC.Status.FLINCHING && FlinchTime < 2))
&& npc.getNpc().getAnimation() != -1 //Failsafe, attacking NPC's always have an animation.
&& !(npc.getLastnpcarea().distanceTo(lastPlayerLocation) == 0 && npc.getLastnpcarea() != npc.getNpc().getWorldArea())) //Weird mechanic: NPC's can't attack on the tick they do a random move
{
npc.setCombatTimerEnd(client.getTickCount() + ATTACK_SPEED + 8);
npc.setStatus(MemorizedNPC.Status.IN_COMBAT_DELAY);
npc.setLastnpcarea(npc.getNpc().getWorldArea());
npc.setLastspotanimation(npc.getNpc().getSpotAnimation());
npc.setLastinteracted(npc.getNpc().getInteracting());
continue;
}
}
switch (npc.getStatus())
{
case IN_COMBAT:
if (CombatTime < 2)
{
npc.setStatus(MemorizedNPC.Status.OUT_OF_COMBAT);
}
break;
case IN_COMBAT_DELAY:
if (CombatTime < 9)
{
npc.setStatus(MemorizedNPC.Status.IN_COMBAT);
}
break;
case FLINCHING:
if (FlinchTime < 2)
{
npc.setStatus(MemorizedNPC.Status.IN_COMBAT);
npc.setCombatTimerEnd(client.getTickCount() + 8);
}
}
npc.setLastnpcarea(npc.getNpc().getWorldArea());
npc.setLastspotanimation(npc.getNpc().getSpotAnimation());
npc.setLastinteracted(npc.getNpc().getInteracting());
}
}
@Subscribe
public void onGameTick(GameTick event)
{
lastTickUpdate = Instant.now();
checkStatus();
lastPlayerLocation = client.getLocalPlayer().getWorldArea();
}
}

View File

@@ -36,6 +36,7 @@ import java.time.Instant;
import java.time.temporal.ChronoUnit; import java.time.temporal.ChronoUnit;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashSet;
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Set; import java.util.Set;
@@ -66,6 +67,7 @@ import net.runelite.api.events.ExperienceChanged;
import net.runelite.api.events.GameStateChanged; import net.runelite.api.events.GameStateChanged;
import net.runelite.api.events.GameTick; import net.runelite.api.events.GameTick;
import net.runelite.api.events.InteractingChanged; import net.runelite.api.events.InteractingChanged;
import net.runelite.api.events.NpcCompositionChanged;
import net.runelite.api.events.NpcDespawned; import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned; import net.runelite.api.events.NpcSpawned;
import net.runelite.api.events.VarbitChanged; import net.runelite.api.events.VarbitChanged;
@@ -79,7 +81,6 @@ import net.runelite.client.chat.ChatCommandManager;
import net.runelite.client.chat.ChatMessageBuilder; import net.runelite.client.chat.ChatMessageBuilder;
import net.runelite.client.chat.ChatMessageManager; import net.runelite.client.chat.ChatMessageManager;
import net.runelite.client.config.ConfigManager; import net.runelite.client.config.ConfigManager;
import net.runelite.client.eventbus.EventBus;
import net.runelite.client.eventbus.Subscribe; import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.events.ChatInput; import net.runelite.client.events.ChatInput;
import net.runelite.client.game.AsyncBufferedImage; import net.runelite.client.game.AsyncBufferedImage;
@@ -215,11 +216,8 @@ public class SlayerPlugin extends Plugin
@Inject @Inject
private ChatClient chatClient; private ChatClient chatClient;
@Inject
private EventBus eventBus;
@Getter(AccessLevel.PACKAGE) @Getter(AccessLevel.PACKAGE)
private List<NPC> highlightedTargets = new ArrayList<>(); private final Set<NPC> highlightedTargets = new HashSet<>();
@Getter(AccessLevel.PACKAGE) @Getter(AccessLevel.PACKAGE)
@Setter(AccessLevel.PACKAGE) @Setter(AccessLevel.PACKAGE)
@@ -349,8 +347,17 @@ public class SlayerPlugin extends Plugin
if (isTarget(npc, targetNames)) if (isTarget(npc, targetNames))
{ {
highlightedTargets.add(npc); highlightedTargets.add(npc);
NPCPresence newPresence = NPCPresence.buildPresence(npc); }
// log.debug("New presence of " + newPresence.toString()); }
@Subscribe
public void onNpcCompositionChanged(NpcCompositionChanged event)
{
NPC npc = event.getNpc();
if (isTarget(npc, targetNames))
{
highlightedTargets.add(npc);
} }
} }
@@ -363,7 +370,6 @@ public class SlayerPlugin extends Plugin
{ {
NPCPresence lingeringPresence = NPCPresence.buildPresence(npc); NPCPresence lingeringPresence = NPCPresence.buildPresence(npc);
lingeringPresences.add(lingeringPresence); lingeringPresences.add(lingeringPresence);
// log.debug("Presence of " + lingeringPresence.toString() + " now lingering");
} }
} }
@@ -583,8 +589,6 @@ public class SlayerPlugin extends Plugin
streak = 1; streak = 1;
break; break;
case 1: case 1:
streak = Integer.parseInt(matches.get(0));
break;
case 3: case 3:
streak = Integer.parseInt(matches.get(0)); streak = Integer.parseInt(matches.get(0));
break; break;
@@ -665,29 +669,13 @@ public class SlayerPlugin extends Plugin
// this is not the initial xp sent on login so these are new xp gains // this is not the initial xp sent on login so these are new xp gains
int gains = slayerExp - cachedXp; int gains = slayerExp - cachedXp;
//log.debug("Slayer xp drop received");
//StringBuilder debugString = new StringBuilder();
// potential npcs to give xp drop are current highlighted npcs and the lingering presences // potential npcs to give xp drop are current highlighted npcs and the lingering presences
List<NPCPresence> potentialNPCs = new ArrayList<>(); List<NPCPresence> potentialNPCs = new ArrayList<>(lingeringPresences);
//debugString.append("Lingering presences {");
for (NPCPresence presence : lingeringPresences)
{
potentialNPCs.add(presence);
// debugString.append(presence.toString());
// debugString.append(", ");
}
//debugString.append("}\nCurrent presences {");
for (NPC npc : highlightedTargets) for (NPC npc : highlightedTargets)
{ {
NPCPresence currentPresence = NPCPresence.buildPresence(npc); NPCPresence currentPresence = NPCPresence.buildPresence(npc);
potentialNPCs.add(currentPresence); potentialNPCs.add(currentPresence);
// debugString.append(currentPresence.toString());
// debugString.append(", ");
} }
//debugString.append("}");
//log.debug(debugString.toString());
int killCount = estimateKillCount(potentialNPCs, gains); int killCount = estimateKillCount(potentialNPCs, gains);
for (int i = 0; i < killCount; i++) for (int i = 0; i < killCount; i++)
@@ -906,8 +894,7 @@ public class SlayerPlugin extends Plugin
if (task != null) if (task != null)
{ {
task.getNpcIds().stream() targetIds.addAll(task.getNpcIds());
.forEach(targetIds::add);
} }
} }

View File

@@ -30,7 +30,7 @@ import java.awt.Color;
import java.awt.Dimension; import java.awt.Dimension;
import java.awt.Graphics2D; import java.awt.Graphics2D;
import java.awt.Polygon; import java.awt.Polygon;
import java.util.List; import java.util.Set;
import javax.inject.Inject; import javax.inject.Inject;
import net.runelite.api.Client; import net.runelite.api.Client;
import net.runelite.api.NPC; import net.runelite.api.NPC;
@@ -71,7 +71,7 @@ public class TargetClickboxOverlay extends Overlay
{ {
if (config.highlightTargets()) if (config.highlightTargets())
{ {
List<NPC> targets = plugin.getHighlightedTargets(); Set<NPC> targets = plugin.getHighlightedTargets();
for (NPC target : targets) for (NPC target : targets)
{ {
if (target == null || target.getName() == null) if (target == null || target.getName() == null)

View File

@@ -29,9 +29,8 @@ package net.runelite.client.plugins.slayer;
import java.awt.Color; import java.awt.Color;
import java.awt.Dimension; import java.awt.Dimension;
import java.awt.Graphics2D; import java.awt.Graphics2D;
import java.util.List; import java.util.Set;
import javax.inject.Inject; import javax.inject.Inject;
import net.runelite.api.Client;
import net.runelite.api.NPC; import net.runelite.api.NPC;
import net.runelite.api.Point; import net.runelite.api.Point;
import net.runelite.client.ui.overlay.Overlay; import net.runelite.client.ui.overlay.Overlay;
@@ -41,15 +40,12 @@ import net.runelite.client.ui.overlay.OverlayUtil;
public class TargetMinimapOverlay extends Overlay public class TargetMinimapOverlay extends Overlay
{ {
private final Client client;
private final SlayerConfig config; private final SlayerConfig config;
private final SlayerPlugin plugin; private final SlayerPlugin plugin;
@Inject @Inject
TargetMinimapOverlay(Client client, SlayerConfig config, SlayerPlugin plugin) TargetMinimapOverlay(SlayerConfig config, SlayerPlugin plugin)
{ {
this.client = client;
this.config = config; this.config = config;
this.plugin = plugin; this.plugin = plugin;
setPosition(OverlayPosition.DYNAMIC); setPosition(OverlayPosition.DYNAMIC);
@@ -64,7 +60,7 @@ public class TargetMinimapOverlay extends Overlay
return null; return null;
} }
List<NPC> targets = plugin.getHighlightedTargets(); Set<NPC> targets = plugin.getHighlightedTargets();
for (NPC target : targets) for (NPC target : targets)
{ {
if (target == null || target.getName() == null) if (target == null || target.getName() == null)

View File

@@ -1,17 +1,23 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
import net.runelite.api.*; import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.Polygon;
import java.util.Iterator;
import java.util.Map;
import net.runelite.api.Client;
import net.runelite.api.NPC;
import net.runelite.api.NPCDefinition;
import net.runelite.api.Perspective;
import net.runelite.api.Point; import net.runelite.api.Point;
import net.runelite.api.Projectile;
import net.runelite.api.coords.LocalPoint; import net.runelite.api.coords.LocalPoint;
import net.runelite.api.coords.WorldArea;
import net.runelite.api.coords.WorldPoint; import net.runelite.api.coords.WorldPoint;
import net.runelite.client.ui.overlay.OverlayUtil; import net.runelite.client.ui.overlay.OverlayUtil;
import java.awt.*;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
public abstract class RoomHandler public abstract class RoomHandler
{ {
protected final Client client; protected final Client client;
@@ -29,7 +35,7 @@ public abstract class RoomHandler
public abstract void onStop(); public abstract void onStop();
protected void drawTile2(Graphics2D graphics, WorldPoint point, Color color, int strokeWidth, int outlineAlpha, int fillAlpha) protected void drawTile2(Graphics2D graphics, WorldPoint point, Color color, int strokeWidth, int outlineAlpha, int fillAlpha)
{ {
WorldPoint playerLocation = client.getLocalPlayer().getWorldLocation(); WorldPoint playerLocation = client.getLocalPlayer().getWorldLocation();
if (point.distanceTo(playerLocation) >= 32) if (point.distanceTo(playerLocation) >= 32)
@@ -71,14 +77,14 @@ public abstract class RoomHandler
Point textLocation = Perspective.getCanvasTextLocation(client, graphics, projectilePoint, text, 0); Point textLocation = Perspective.getCanvasTextLocation(client, graphics, projectilePoint, text, 0);
if (textLocation != null) if (textLocation != null)
{ {
if (projectileId == 1607) if (projectileId == 1607)
{ // range { // range
renderTextLocation(graphics, text, 17, Font.BOLD, new Color(57, 255, 20, 255), textLocation); renderTextLocation(graphics, text, 17, Font.BOLD, new Color(57, 255, 20, 255), textLocation);
} }
else if (projectileId == 1606) else if (projectileId == 1606)
{ //mage { //mage
renderTextLocation(graphics, text, 17, Font.BOLD, new Color(64, 224, 208, 255), textLocation); renderTextLocation(graphics, text, 17, Font.BOLD, new Color(64, 224, 208, 255), textLocation);
} }
else else
{ //Orb of death? i hope { //Orb of death? i hope
renderTextLocation(graphics, text, 20, Font.BOLD, Color.WHITE, textLocation); renderTextLocation(graphics, text, 20, Font.BOLD, Color.WHITE, textLocation);
@@ -87,20 +93,26 @@ public abstract class RoomHandler
} }
} }
protected void drawTile(Graphics2D graphics, WorldPoint point, Color color, int strokeWidth, int outlineAlpha, int fillAlpha) protected void drawTile(Graphics2D graphics, WorldPoint point, Color color, int strokeWidth, int outlineAlpha, int fillAlpha)
{ {
WorldPoint playerLocation = client.getLocalPlayer().getWorldLocation(); WorldPoint playerLocation = client.getLocalPlayer().getWorldLocation();
if (point.distanceTo(playerLocation) >= 32) if (point.distanceTo(playerLocation) >= 32)
{
return; return;
}
LocalPoint lp = LocalPoint.fromWorld(client, point); LocalPoint lp = LocalPoint.fromWorld(client, point);
if (lp == null) if (lp == null)
{
return; return;
}
Polygon poly = Perspective.getCanvasTilePoly(client, lp); Polygon poly = Perspective.getCanvasTilePoly(client, lp);
if (poly == null) if (poly == null)
{
return; return;
}
graphics.setColor(new Color(color.getRed(), color.getGreen(), color.getBlue(), outlineAlpha)); graphics.setColor(new Color(color.getRed(), color.getGreen(), color.getBlue(), outlineAlpha));
graphics.setStroke(new BasicStroke(strokeWidth)); graphics.setStroke(new BasicStroke(strokeWidth));
@@ -109,13 +121,15 @@ public abstract class RoomHandler
graphics.fill(poly); graphics.fill(poly);
} }
protected void renderNpcOverlay(Graphics2D graphics, NPC actor, Color color, int outlineWidth, int outlineAlpha, int fillAlpha) protected void renderNpcOverlay(Graphics2D graphics, NPC actor, Color color, int outlineWidth, int outlineAlpha, int fillAlpha)
{ {
int size = 1; int size = 1;
NPCDefinition composition = actor.getTransformedDefinition(); NPCDefinition composition = actor.getTransformedDefinition();
if (composition != null) if (composition != null)
{
size = composition.getSize(); size = composition.getSize();
}
LocalPoint lp = actor.getLocalLocation(); LocalPoint lp = actor.getLocalLocation();
Polygon tilePoly = Perspective.getCanvasTileAreaPoly(client, lp, size); Polygon tilePoly = Perspective.getCanvasTileAreaPoly(client, lp, size);
@@ -143,26 +157,6 @@ public abstract class RoomHandler
} }
} }
protected List<WorldPoint> getHitSquares(WorldPoint npcLoc, int npcSize, int thickness, boolean includeUnder)
{
List<WorldPoint> little = new WorldArea(npcLoc, npcSize, npcSize).toWorldPointList();
List<WorldPoint> big = new WorldArea(npcLoc.getX() - thickness, npcLoc.getY() - thickness, npcSize + (thickness * 2), npcSize + (thickness * 2), npcLoc.getPlane()).toWorldPointList();
if (!includeUnder)
{
for (Iterator<WorldPoint> it = big.iterator(); it.hasNext(); )
{
WorldPoint p = it.next();
if (little.contains(p))
{
it.remove();
}
}
}
return big;
}
protected String twoDigitString(long number) protected String twoDigitString(long number)
{ {

View File

@@ -8,30 +8,15 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
import java.awt.Color;
import net.runelite.client.config.Config; import net.runelite.client.config.Config;
import net.runelite.client.config.ConfigGroup; import net.runelite.client.config.ConfigGroup;
import net.runelite.client.config.ConfigItem; import net.runelite.client.config.ConfigItem;
import java.awt.*;
@ConfigGroup("Theatre") @ConfigGroup("Theatre")
public interface TheatreConfig extends Config public interface TheatreConfig extends Config
{ {
enum NYLOCAS
{
NONE,
MAGE,
MELEE,
RANGER
}
enum NYLOOPTION
{
NONE,
TILE,
TIMER
}
@ConfigItem( @ConfigItem(
position = 0, position = 0,
keyName = "showMaidenBloodToss", keyName = "showMaidenBloodToss",
@@ -39,7 +24,7 @@ public interface TheatreConfig extends Config
description = "Displays the tile location where tossed blood will land.", description = "Displays the tile location where tossed blood will land.",
group = "Maiden" group = "Maiden"
) )
default boolean showMaidenBloodToss() default boolean showMaidenBloodToss()
{ {
return true; return true;
} }
@@ -51,7 +36,19 @@ public interface TheatreConfig extends Config
description = "Show the tiles that blood spawns will travel to.", description = "Show the tiles that blood spawns will travel to.",
group = "Maiden" group = "Maiden"
) )
default boolean showMaidenBloodSpawns() default boolean showMaidenBloodSpawns()
{
return true;
}
@ConfigItem(
position = 2,
keyName = "showNyloFreezeHighlights",
name = "Show Nylo Freeze Highlights",
description = "Show when to freeze Nylos at maiden. Say n1,n2,s1,s2 in chat for it to register.",
group = "Maiden"
)
default boolean showNyloFreezeHighlights()
{ {
return true; return true;
} }
@@ -63,7 +60,7 @@ public interface TheatreConfig extends Config
description = "Displays Bloat's status (asleep, wake, and enrage) using color code.", description = "Displays Bloat's status (asleep, wake, and enrage) using color code.",
group = "Bloat" group = "Bloat"
) )
default boolean showBloatIndicator() default boolean showBloatIndicator()
{ {
return true; return true;
} }
@@ -75,7 +72,7 @@ public interface TheatreConfig extends Config
description = "Highlights the falling hands inside Bloat.", description = "Highlights the falling hands inside Bloat.",
group = "Bloat" group = "Bloat"
) )
default boolean showBloatHands() default boolean showBloatHands()
{ {
return true; return true;
} }
@@ -87,8 +84,8 @@ public interface TheatreConfig extends Config
description = "", description = "",
group = "Bloat" group = "Bloat"
) )
default boolean BloatFeetIndicatorRaveEdition() default boolean BloatFeetIndicatorRaveEdition()
{ {
return false; return false;
} }
@@ -135,45 +132,40 @@ public interface TheatreConfig extends Config
description = "An overlay will appear that counts the amount of Nylocas in the room.", description = "An overlay will appear that counts the amount of Nylocas in the room.",
group = "Nylocas" group = "Nylocas"
) )
default boolean showNylocasAmount() default boolean showNylocasAmount()
{ {
return true; return true;
} }
/** /**
@ConfigItem( * @ConfigItem( position = 8,
position = 8, * keyName = "showNylocasSpawns",
keyName = "showNylocasSpawns", * name = "Show Nylocas Pre-spawns",
name = "Show Nylocas Pre-spawns", * description = "Know the contents of the next upcoming wave."
description = "Know the contents of the next upcoming wave." * )
) * default boolean showNylocasSpawns()
default boolean showNylocasSpawns() * {
{ * return true;
return true; * }
} * @ConfigItem( position = 9,
* keyName = "highlightNyloRoles",
@ConfigItem( * name = "Highlight Nylo Prespawns",
position = 9, * description = "Highlights the next upcoming wave based on role. FOR BEGINNERS"
keyName = "highlightNyloRoles", * )
name = "Highlight Nylo Prespawns", * default NYLOCAS highlightNyloRoles()
description = "Highlights the next upcoming wave based on role. FOR BEGINNERS" * {
) * return NYLOCAS.NONE;
default NYLOCAS highlightNyloRoles() * }
{ * @ConfigItem( position = 10,
return NYLOCAS.NONE; * keyName = "highlightNyloParents",
} * name = "Show Nylo Parents (Un-used)",
* description = "Highlight the Nylocas that spawn outside the center."
@ConfigItem( * )
position = 10, * default boolean highlightNyloParents()
keyName = "highlightNyloParents", * {
name = "Show Nylo Parents (Un-used)", * return true;
description = "Highlight the Nylocas that spawn outside the center." * }
) **/
default boolean highlightNyloParents()
{
return true;
}
**/
@ConfigItem( @ConfigItem(
position = 11, position = 11,
@@ -218,7 +210,7 @@ public interface TheatreConfig extends Config
description = "Marks the tiles of Sotetseg's maze while in the underworld.", description = "Marks the tiles of Sotetseg's maze while in the underworld.",
group = "Sotetseg" group = "Sotetseg"
) )
default boolean showSotetsegSolo() default boolean showSotetsegSolo()
{ {
return true; return true;
} }
@@ -234,6 +226,7 @@ public interface TheatreConfig extends Config
{ {
return Color.WHITE; return Color.WHITE;
} }
@ConfigItem( @ConfigItem(
position = 15, position = 15,
keyName = "showXarpusHeals", keyName = "showXarpusHeals",
@@ -302,10 +295,10 @@ public interface TheatreConfig extends Config
group = "Verzik" group = "Verzik"
) )
default boolean VerzikTankTile() default boolean VerzikTankTile()
{ {
return false; return false;
} }
@ConfigItem( @ConfigItem(
position = 22, position = 22,
keyName = "verzikrangeattacks", keyName = "verzikrangeattacks",
@@ -314,10 +307,10 @@ public interface TheatreConfig extends Config
group = "Verzik" group = "Verzik"
) )
default boolean verzikRangeAttacks() default boolean verzikRangeAttacks()
{ {
return true; return true;
} }
@ConfigItem( @ConfigItem(
position = 23, position = 23,
keyName = "extratimers", keyName = "extratimers",
@@ -329,7 +322,7 @@ public interface TheatreConfig extends Config
{ {
return false; return false;
} }
@ConfigItem( @ConfigItem(
position = 24, position = 24,
keyName = "p1attacks", keyName = "p1attacks",
@@ -341,7 +334,7 @@ public interface TheatreConfig extends Config
{ {
return true; return true;
} }
@ConfigItem( @ConfigItem(
position = 25, position = 25,
keyName = "p2attacks", keyName = "p2attacks",
@@ -353,7 +346,7 @@ public interface TheatreConfig extends Config
{ {
return true; return true;
} }
@ConfigItem( @ConfigItem(
position = 26, position = 26,
keyName = "p3attacks", keyName = "p3attacks",
@@ -365,4 +358,19 @@ public interface TheatreConfig extends Config
{ {
return true; return true;
} }
enum NYLOCAS
{
NONE,
MAGE,
MELEE,
RANGER
}
enum NYLOOPTION
{
NONE,
TILE,
TIMER
}
} }

View File

@@ -1,6 +1,6 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
public class TheatreConstant public class TheatreConstant
{ {
public static final int MAIDEN_BLOOD_THROW = 1579; public static final int MAIDEN_BLOOD_THROW = 1579;

View File

@@ -8,28 +8,30 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
import java.awt.*; import java.awt.Dimension;
import java.util.*; import java.awt.Graphics2D;
import javax.inject.Inject; import javax.inject.Inject;
import net.runelite.api.*; import net.runelite.api.Client;
import net.runelite.client.graphics.ModelOutlineRenderer;
import net.runelite.client.ui.overlay.Overlay; import net.runelite.client.ui.overlay.Overlay;
import net.runelite.client.ui.overlay.OverlayLayer; import net.runelite.client.ui.overlay.OverlayLayer;
import net.runelite.client.ui.overlay.OverlayPosition; import net.runelite.client.ui.overlay.OverlayPosition;
import net.runelite.client.ui.overlay.OverlayPriority; import net.runelite.client.ui.overlay.OverlayPriority;
public class TheatreOverlay extends Overlay public class TheatreOverlay extends Overlay
{ {
private final Client client; private final Client client;
private final TheatrePlugin plugin; private final TheatrePlugin plugin;
private final TheatreConfig config; private final TheatreConfig config;
private final ModelOutlineRenderer modelOutline;
@Inject @Inject
private TheatreOverlay(Client client, TheatrePlugin plugin, TheatreConfig config) private TheatreOverlay(Client client, TheatrePlugin plugin, TheatreConfig config, ModelOutlineRenderer modelOutline)
{ {
this.client = client; this.client = client;
this.plugin = plugin; this.plugin = plugin;
this.config = config; this.config = config;
this.modelOutline = modelOutline;
setPosition(OverlayPosition.DYNAMIC); setPosition(OverlayPosition.DYNAMIC);
setPriority(OverlayPriority.HIGH); setPriority(OverlayPriority.HIGH);

View File

@@ -9,32 +9,43 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
import com.google.inject.Provides; import com.google.inject.Provides;
import java.awt.Color;
import java.util.LinkedList;
import java.util.List;
import javax.inject.Inject;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import lombok.Setter; import lombok.Setter;
import lombok.extern.slf4j.Slf4j;
import net.runelite.api.Client; import net.runelite.api.Client;
import java.util.LinkedList; import net.runelite.api.events.AnimationChanged;
import java.util.List; import net.runelite.api.events.ChatMessage;
import net.runelite.api.events.*; import net.runelite.api.events.ConfigChanged;
import net.runelite.client.config.ConfigManager; import net.runelite.api.events.GameTick;
import net.runelite.client.eventbus.Subscribe; import net.runelite.api.events.GroundObjectSpawned;
import net.runelite.client.plugins.Plugin; import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned;
import net.runelite.api.events.ProjectileMoved;
import net.runelite.api.events.SpotAnimationChanged;
import net.runelite.api.events.VarbitChanged;
import net.runelite.api.events.WidgetLoaded;
import net.runelite.api.widgets.Widget; import net.runelite.api.widgets.Widget;
import net.runelite.api.widgets.WidgetID; import net.runelite.api.widgets.WidgetID;
import net.runelite.api.widgets.WidgetInfo; import net.runelite.api.widgets.WidgetInfo;
import net.runelite.client.config.ConfigManager;
import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.graphics.ModelOutlineRenderer;
import net.runelite.client.plugins.Plugin;
import net.runelite.client.plugins.PluginDescriptor; import net.runelite.client.plugins.PluginDescriptor;
import net.runelite.client.plugins.PluginType; import net.runelite.client.plugins.PluginType;
import net.runelite.client.plugins.theatre.rooms.BloatHandler; import net.runelite.client.plugins.theatre.rooms.BloatHandler;
import net.runelite.client.plugins.theatre.rooms.MaidenHandler; import net.runelite.client.plugins.theatre.rooms.MaidenHandler;
import net.runelite.client.plugins.theatre.rooms.SotetsegHandler; import net.runelite.client.plugins.theatre.rooms.SotetsegHandler;
import net.runelite.client.plugins.theatre.rooms.VerzikHandler; import net.runelite.client.plugins.theatre.rooms.VerzikHandler;
import net.runelite.client.plugins.theatre.rooms.xarpus.XarpusHandler;
import net.runelite.client.plugins.theatre.rooms.nylocas.NyloHandler; import net.runelite.client.plugins.theatre.rooms.nylocas.NyloHandler;
import net.runelite.client.plugins.theatre.rooms.xarpus.XarpusHandler;
import net.runelite.client.ui.overlay.OverlayManager; import net.runelite.client.ui.overlay.OverlayManager;
import javax.inject.Inject;
import java.awt.*;
@PluginDescriptor( @PluginDescriptor(
name = "Theatre of Blood", name = "Theatre of Blood",
description = "All-in-one plugin for Theatre of Blood.", description = "All-in-one plugin for Theatre of Blood.",
@@ -43,9 +54,9 @@ import java.awt.*;
enabledByDefault = false enabledByDefault = false
) )
public class TheatrePlugin extends Plugin @Slf4j
public class TheatrePlugin extends Plugin
{ {
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
@Setter(AccessLevel.PUBLIC) @Setter(AccessLevel.PUBLIC)
private TheatreRoom room; private TheatreRoom room;
@@ -83,6 +94,9 @@ public class TheatrePlugin extends Plugin
@Inject @Inject
private TheatreConfig config; private TheatreConfig config;
@Inject
private ModelOutlineRenderer modelOutline;
@Provides @Provides
TheatreConfig getConfig(ConfigManager configManager) TheatreConfig getConfig(ConfigManager configManager)
{ {
@@ -94,7 +108,7 @@ public class TheatrePlugin extends Plugin
{ {
room = TheatreRoom.UNKNOWN; room = TheatreRoom.UNKNOWN;
maidenHandler = new MaidenHandler(client, this, config); maidenHandler = new MaidenHandler(client, this, config, modelOutline);
bloatHandler = new BloatHandler(client, this, config); bloatHandler = new BloatHandler(client, this, config);
nyloHandler = new NyloHandler(client, this, config); nyloHandler = new NyloHandler(client, this, config);
sotetsegHandler = new SotetsegHandler(client, this, config); sotetsegHandler = new SotetsegHandler(client, this, config);
@@ -131,26 +145,47 @@ public class TheatrePlugin extends Plugin
overlayManager.remove(overlay); overlayManager.remove(overlay);
} }
@Subscribe
public void onSpotAnimationChanged(SpotAnimationChanged event)
{
if (maidenHandler != null)
{
maidenHandler.onSpotAnimationChanged(event);
}
}
@Subscribe @Subscribe
public void onNpcSpawned(NpcSpawned event) public void onNpcSpawned(NpcSpawned event)
{ {
if (maidenHandler != null) if (maidenHandler != null)
{
maidenHandler.onNpcSpawned(event); maidenHandler.onNpcSpawned(event);
}
if (bloatHandler != null) if (bloatHandler != null)
{
bloatHandler.onNpcSpawned(event); bloatHandler.onNpcSpawned(event);
}
if (nyloHandler != null) if (nyloHandler != null)
{
nyloHandler.onNpcSpawned(event); nyloHandler.onNpcSpawned(event);
}
if (sotetsegHandler != null) if (sotetsegHandler != null)
{
sotetsegHandler.onNpcSpawned(event); sotetsegHandler.onNpcSpawned(event);
}
if (xarpusHandler != null) if (xarpusHandler != null)
{
xarpusHandler.onNpcSpawned(event); xarpusHandler.onNpcSpawned(event);
}
if (verzikHandler != null) if (verzikHandler != null)
{
verzikHandler.onNpcSpawned(event); verzikHandler.onNpcSpawned(event);
}
} }
@@ -158,19 +193,29 @@ public class TheatrePlugin extends Plugin
public void onNpcDespawned(NpcDespawned event) public void onNpcDespawned(NpcDespawned event)
{ {
if (maidenHandler != null) if (maidenHandler != null)
{
maidenHandler.onNpcDespawned(event); maidenHandler.onNpcDespawned(event);
}
if (bloatHandler != null) if (bloatHandler != null)
{
bloatHandler.onNpcDespawned(event); bloatHandler.onNpcDespawned(event);
}
if (nyloHandler != null) if (nyloHandler != null)
{
nyloHandler.onNpcDespawned(event); nyloHandler.onNpcDespawned(event);
}
if (sotetsegHandler != null) if (sotetsegHandler != null)
{
sotetsegHandler.onNpcDespawned(event); sotetsegHandler.onNpcDespawned(event);
}
if (xarpusHandler != null) if (xarpusHandler != null)
{
xarpusHandler.onNpcDespawned(event); xarpusHandler.onNpcDespawned(event);
}
} }
@@ -178,7 +223,18 @@ public class TheatrePlugin extends Plugin
public void onAnimationChanged(AnimationChanged event) public void onAnimationChanged(AnimationChanged event)
{ {
if (verzikHandler != null) if (verzikHandler != null)
{
verzikHandler.onAnimationChanged(event); verzikHandler.onAnimationChanged(event);
}
}
@Subscribe
public void onChatMessage(ChatMessage event)
{
if (maidenHandler != null)
{
maidenHandler.onChatMessage(event);
}
} }
@Subscribe @Subscribe
@@ -204,22 +260,34 @@ public class TheatrePlugin extends Plugin
public void onGameTick(GameTick event) public void onGameTick(GameTick event)
{ {
if (maidenHandler != null) if (maidenHandler != null)
{
maidenHandler.onGameTick(); maidenHandler.onGameTick();
}
if (bloatHandler != null) if (bloatHandler != null)
{
bloatHandler.onGameTick(); bloatHandler.onGameTick();
}
if (nyloHandler != null) if (nyloHandler != null)
{
nyloHandler.onGameTick(); nyloHandler.onGameTick();
}
if (sotetsegHandler != null) if (sotetsegHandler != null)
{
sotetsegHandler.onGameTick(); sotetsegHandler.onGameTick();
}
if (xarpusHandler != null) if (xarpusHandler != null)
{
xarpusHandler.onGameTick(); xarpusHandler.onGameTick();
}
if (verzikHandler != null) if (verzikHandler != null)
{
verzikHandler.onGameTick(); verzikHandler.onGameTick();
}
if (widget == null) if (widget == null)
{ {
@@ -315,27 +383,37 @@ public class TheatrePlugin extends Plugin
public void onGroundObjectSpawned(GroundObjectSpawned event) public void onGroundObjectSpawned(GroundObjectSpawned event)
{ {
if (sotetsegHandler != null) if (sotetsegHandler != null)
{
sotetsegHandler.onGroundObjectSpawned(event); sotetsegHandler.onGroundObjectSpawned(event);
}
if (xarpusHandler != null) if (xarpusHandler != null)
{
xarpusHandler.onGroundObjectSpawned(event); xarpusHandler.onGroundObjectSpawned(event);
}
} }
@Subscribe @Subscribe
public void onConfigChanged(ConfigChanged event) public void onConfigChanged(ConfigChanged event)
{ {
if (nyloHandler != null) if (nyloHandler != null)
{
nyloHandler.onConfigChanged(); nyloHandler.onConfigChanged();
}
} }
@Subscribe @Subscribe
public void onVarbitChanged(VarbitChanged event) public void onVarbitChanged(VarbitChanged event)
{ {
if (bloatHandler != null) if (bloatHandler != null)
{
bloatHandler.onVarbitChanged(event); bloatHandler.onVarbitChanged(event);
}
if (xarpusHandler != null) if (xarpusHandler != null)
{
xarpusHandler.onVarbitChanged(event); xarpusHandler.onVarbitChanged(event);
}
} }
@Subscribe @Subscribe

View File

@@ -1,6 +1,6 @@
package net.runelite.client.plugins.theatre; package net.runelite.client.plugins.theatre;
public enum TheatreRoom public enum TheatreRoom
{ {
MAIDEN, MAIDEN,
BLOAT, BLOAT,
@@ -8,5 +8,5 @@ public enum TheatreRoom
SOTETSEG, SOTETSEG,
XARPUS, XARPUS,
VERSIK, VERSIK,
UNKNOWN; UNKNOWN
} }

View File

@@ -1,42 +1,36 @@
package net.runelite.client.plugins.theatre.rooms; package net.runelite.client.plugins.theatre.rooms;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.util.Random;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import net.runelite.api.*; import net.runelite.api.Client;
import net.runelite.api.GraphicsObject;
import net.runelite.api.NPC;
import net.runelite.api.NpcID;
import net.runelite.api.Point; import net.runelite.api.Point;
import net.runelite.api.Varbits;
import net.runelite.api.coords.WorldPoint; import net.runelite.api.coords.WorldPoint;
import net.runelite.api.events.NpcDespawned; import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned; import net.runelite.api.events.NpcSpawned;
import net.runelite.api.events.VarbitChanged; import net.runelite.api.events.VarbitChanged;
import net.runelite.client.eventbus.Subscribe; import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.plugins.theatre.RoomHandler;
import net.runelite.client.plugins.theatre.TheatreConfig; import net.runelite.client.plugins.theatre.TheatreConfig;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import net.runelite.client.plugins.theatre.RoomHandler;
import java.awt.*;
import java.util.Random;
public class BloatHandler extends RoomHandler public class BloatHandler extends RoomHandler
{ {
public static enum BloatState private int bloatTimer;
{
DOWN,
UP,
WARN;
}
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private NPC bloat; private NPC bloat;
private int counter; private int counter;
//My variables
private boolean bloatFlag; private boolean bloatFlag;
int bloatTimer;
private Color color; private Color color;
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private BloatState bloatState; private BloatState bloatState;
@@ -49,7 +43,9 @@ public class BloatHandler extends RoomHandler
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.BLOAT) if (this.plugin.getRoom() == TheatreRoom.BLOAT)
{
return; return;
}
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.BLOAT); this.plugin.setRoom(TheatreRoom.BLOAT);
@@ -106,8 +102,8 @@ public class BloatHandler extends RoomHandler
WorldPoint point = WorldPoint.fromLocal(client, object.getLocation()); WorldPoint point = WorldPoint.fromLocal(client, object.getLocation());
if (!config.BloatFeetIndicatorRaveEdition()) if (!config.BloatFeetIndicatorRaveEdition())
{ {
drawTile(graphics, point, new Color(36, 248, 229), 2, 255, 10); drawTile(graphics, point, new Color(36, 248, 229), 2, 255, 10);
} }
else else
{ {
drawTile(graphics, point, color, 2, 255, 10); drawTile(graphics, point, color, 2, 255, 10);
@@ -120,15 +116,15 @@ public class BloatHandler extends RoomHandler
if (config.showBloatTimer()) if (config.showBloatTimer())
{ {
final String tickCounter = String.valueOf(bloatTimer); final String tickCounter = String.valueOf(bloatTimer);
int secondConversion = (int)(bloatTimer * .6); int secondConversion = (int) (bloatTimer * .6);
if (bloat != null) if (bloat != null)
{ {
Point canvasPoint = bloat.getCanvasTextLocation(graphics, tickCounter, 60); Point canvasPoint = bloat.getCanvasTextLocation(graphics, tickCounter, 60);
if (bloatTimer <= 37) if (bloatTimer <= 37)
{ {
renderTextLocation(graphics, tickCounter + "( " + secondConversion + " )", 15, Font.BOLD, Color.WHITE, canvasPoint); renderTextLocation(graphics, tickCounter + "( " + secondConversion + " )", 15, Font.BOLD, Color.WHITE, canvasPoint);
} }
else else
{ {
renderTextLocation(graphics, tickCounter + "( " + secondConversion + " )", 15, Font.BOLD, Color.RED, canvasPoint); renderTextLocation(graphics, tickCounter + "( " + secondConversion + " )", 15, Font.BOLD, Color.RED, canvasPoint);
} }
@@ -139,9 +135,9 @@ public class BloatHandler extends RoomHandler
@Subscribe @Subscribe
public void onVarbitChanged(VarbitChanged event) public void onVarbitChanged(VarbitChanged event)
{ {
if (client.getVar(Varbits.BLOAT_DOOR) == 1) if (client.getVar(Varbits.BLOAT_DOOR) == 1)
{ {
if (!bloatFlag) if (!bloatFlag)
{ {
bloatTimer = 0; bloatTimer = 0;
bloatFlag = true; bloatFlag = true;
@@ -149,12 +145,12 @@ public class BloatHandler extends RoomHandler
} }
} }
public void onNpcSpawned(NpcSpawned event) public void onNpcSpawned(NpcSpawned event)
{ {
NPC npc = event.getNpc(); NPC npc = event.getNpc();
int id = npc.getId(); int id = npc.getId();
if (id == NpcID.PESTILENT_BLOAT) if (id == NpcID.PESTILENT_BLOAT)
{ {
this.onStart(); this.onStart();
bloatTimer = 0; bloatTimer = 0;
@@ -162,12 +158,12 @@ public class BloatHandler extends RoomHandler
} }
} }
public void onNpcDespawned(NpcDespawned event) public void onNpcDespawned(NpcDespawned event)
{ {
NPC npc = event.getNpc(); NPC npc = event.getNpc();
int id = npc.getId(); int id = npc.getId();
if (id == NpcID.PESTILENT_BLOAT) if (id == NpcID.PESTILENT_BLOAT)
{ {
this.onStop(); this.onStop();
bloatTimer = 0; bloatTimer = 0;
@@ -175,9 +171,9 @@ public class BloatHandler extends RoomHandler
} }
} }
public void onGameTick() public void onGameTick()
{ {
if (plugin.getRoom() != TheatreRoom.BLOAT) if (plugin.getRoom() != TheatreRoom.BLOAT)
{ {
return; return;
} }
@@ -196,39 +192,46 @@ public class BloatHandler extends RoomHandler
counter++; counter++;
if (bloat.getAnimation() == -1) if (bloat.getAnimation() == -1)
{ {
bloatTimer++; bloatTimer++;
counter = 0; counter = 0;
if (bloat.getHealth() == 0) if (bloat.getHealth() == 0)
{ {
bloatState = BloatState.DOWN; bloatState = BloatState.DOWN;
} }
else else
{ {
bloatState = BloatState.UP; bloatState = BloatState.UP;
} }
} }
else else
{ {
if (25 < counter && counter < 35) if (25 < counter && counter < 35)
{ {
bloatState = BloatState.WARN; bloatState = BloatState.WARN;
} }
else if (counter < 26) else if (counter < 26)
{ {
bloatTimer = 0; bloatTimer = 0;
bloatState = BloatState.DOWN; bloatState = BloatState.DOWN;
} }
else if (bloat.getModelHeight() == 568) else if (bloat.getModelHeight() == 568)
{ {
bloatTimer = 0; bloatTimer = 0;
bloatState = BloatState.DOWN; bloatState = BloatState.DOWN;
} }
else else
{ {
bloatState = BloatState.UP; bloatState = BloatState.UP;
} }
} }
} }
public enum BloatState
{
DOWN,
UP,
WARN
}
} }

View File

@@ -1,162 +1,298 @@
package net.runelite.client.plugins.theatre.rooms; package net.runelite.client.plugins.theatre.rooms;
import lombok.AccessLevel; import com.google.common.collect.ImmutableSet;
import lombok.Getter; import java.awt.Color;
import java.awt.Graphics2D;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import lombok.extern.slf4j.Slf4j;
import net.runelite.api.ChatMessageType; import net.runelite.api.ChatMessageType;
import net.runelite.api.Client; import net.runelite.api.Client;
import net.runelite.api.GraphicsObject; import net.runelite.api.GraphicsObject;
import net.runelite.api.NPC; import net.runelite.api.NPC;
import net.runelite.api.NpcID;
import net.runelite.api.coords.WorldPoint; import net.runelite.api.coords.WorldPoint;
import net.runelite.api.events.ChatMessage;
import net.runelite.api.events.NpcDespawned; import net.runelite.api.events.NpcDespawned;
import net.runelite.api.events.NpcSpawned; import net.runelite.api.events.NpcSpawned;
import net.runelite.api.events.SpotAnimationChanged;
import net.runelite.client.graphics.ModelOutlineRenderer;
import net.runelite.client.plugins.theatre.RoomHandler; import net.runelite.client.plugins.theatre.RoomHandler;
import net.runelite.client.plugins.theatre.TheatreConfig; import net.runelite.client.plugins.theatre.TheatreConfig;
import net.runelite.client.plugins.theatre.TheatreConstant; import net.runelite.client.plugins.theatre.TheatreConstant;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import net.runelite.client.util.Text;
import java.awt.*; @Slf4j
import java.util.ArrayList; public class MaidenHandler extends RoomHandler
import java.util.List;
public class MaidenHandler extends RoomHandler
{ {
private static final ImmutableSet<WorldPoint> N1 = ImmutableSet.of(
@Getter(AccessLevel.PACKAGE) new WorldPoint(3182, 4457, 0),
new WorldPoint(3174, 4457, 0)
);
private static final ImmutableSet<WorldPoint> N2 = ImmutableSet.of(
new WorldPoint(3178, 4457, 0),
new WorldPoint(3186, 4455, 0),
new WorldPoint(3186, 4457, 0)
);
private static final ImmutableSet<WorldPoint> S1 = ImmutableSet.of(
new WorldPoint(3174, 4437, 0),
new WorldPoint(3182, 4437, 0)
);
private static final ImmutableSet<WorldPoint> S2 = ImmutableSet.of(
new WorldPoint(3186, 4439, 0),
new WorldPoint(3186, 4437, 0),
new WorldPoint(3178, 4437, 0)
);
private static final ImmutableSet<Integer> FREEZEANIMS = ImmutableSet.of(
361,
363,
367,
369
);
private static final Color TRANSPARENT = new Color(0, 0, 0, 0);
private static final Color FREEZE = new Color(0, 226, 255, 255);
private List<WorldPoint> bloodThrows = new ArrayList<>(); private List<WorldPoint> bloodThrows = new ArrayList<>();
@Getter(AccessLevel.PACKAGE)
private List<NPC> bloodSpawns = new ArrayList<>(); private List<NPC> bloodSpawns = new ArrayList<>();
@Getter(AccessLevel.PACKAGE)
private List<WorldPoint> bloodSpawnLocation = new ArrayList<>(); private List<WorldPoint> bloodSpawnLocation = new ArrayList<>();
@Getter(AccessLevel.PACKAGE)
private List<WorldPoint> bloodSpawnTarget = new ArrayList<>(); private List<WorldPoint> bloodSpawnTarget = new ArrayList<>();
private NPC maiden;
private String nyloCall = "n1";
private Set<Nylos> nylos = new HashSet<>();
private List<NPC> healers = new ArrayList<>(); private List<NPC> healers = new ArrayList<>();
private int healerCount = 0; private int healerCount = 0;
private int wave = 1; private int wave = 1;
private long startTime = 0; private long startTime = 0;
private ModelOutlineRenderer modelOutline;
public MaidenHandler(Client client, TheatrePlugin plugin, TheatreConfig config) public MaidenHandler(Client client, TheatrePlugin plugin, TheatreConfig config, ModelOutlineRenderer modelOutline)
{ {
super(client, plugin, config); super(client, plugin, config);
this.modelOutline = modelOutline;
} }
@Override @Override
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.MAIDEN) if (this.plugin.getRoom() == TheatreRoom.MAIDEN)
{
return; return;
}
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.MAIDEN); this.plugin.setRoom(TheatreRoom.MAIDEN);
this.startTime = System.currentTimeMillis(); this.startTime = System.currentTimeMillis();
System.out.println("Starting Maiden Room"); log.debug("Starting Maiden Room");
} }
@Override @Override
public void onStop() public void onStop()
{ {
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.UNKNOWN); this.plugin.setRoom(TheatreRoom.UNKNOWN);
System.out.println("Stopping Maiden Room"); log.debug("Stopping Maiden Room");
} }
public void reset() public void reset()
{ {
this.bloodThrows.clear(); this.bloodThrows.clear();
this.bloodSpawns.clear(); this.bloodSpawns.clear();
this.bloodSpawnLocation.clear(); this.bloodSpawnLocation.clear();
this.bloodSpawnTarget.clear(); this.bloodSpawnTarget.clear();
this.healers.clear(); this.healers.clear();
this.healerCount = 0; this.healerCount = 0;
this.startTime = -1; this.startTime = -1;
this.wave = 1; this.wave = 1;
} }
public void render(Graphics2D graphics) public void render(Graphics2D graphics)
{ {
if (config.showMaidenBloodToss()) for (Nylos nylo : nylos)
{ {
for (WorldPoint point : bloodThrows) if (nylo.getNpc() == null || nylo.getNpc().getId() == -1)
{
continue;
}
final String location = nylo.getSpawnLocation().getName();
if (location.equals(nyloCall))
{
Color color = Color.WHITE;
int width = 4;
if (nylo.getNpc().getWorldArea().distanceTo(maiden.getWorldArea()) <= 3)
{
color = FREEZE;
width = 8;
}
modelOutline.drawOutline(nylo.getNpc(), width, color, TRANSPARENT);
}
}
if (config.showMaidenBloodToss())
{
for (WorldPoint point : bloodThrows)
{ {
drawTile(graphics, point, new Color(36, 248, 229), 2, 150, 10); drawTile(graphics, point, new Color(36, 248, 229), 2, 150, 10);
} }
} }
if (config.showMaidenBloodSpawns()) if (config.showMaidenBloodSpawns())
{ {
for (WorldPoint point : bloodSpawnLocation) for (WorldPoint point : bloodSpawnLocation)
{ {
drawTile(graphics, point, new Color(36, 248, 229), 2, 180, 20); drawTile(graphics, point, new Color(36, 248, 229), 2, 180, 20);
} }
for (WorldPoint point : bloodSpawnTarget) for (WorldPoint point : bloodSpawnTarget)
{ {
drawTile(graphics, point, new Color(36, 248, 229), 1, 120, 10); drawTile(graphics, point, new Color(36, 248, 229), 1, 120, 10);
} }
} }
} }
public void onNpcSpawned(NpcSpawned event) public void onSpotAnimationChanged(SpotAnimationChanged event)
{ {
NPC npc = event.getNpc(); if (event.getActor() instanceof NPC)
String name = npc.getName(); {
int id = npc.getId(); NPC npc = (NPC) event.getActor();
if (npc.getName() != null && name.equals("The Maiden of Sugadinti")) if (npc.getId() != 8366)
{
this.onStart();
}
else if (plugin.getRoom() == TheatreRoom.MAIDEN)
{
if (id == NpcID.BLOOD_SPAWN)
{ {
if (!bloodSpawns.contains(npc)) return;
bloodSpawns.add(npc); }
}
else if (name != null && name.equalsIgnoreCase("Nylocas Matomenos")) int anim = npc.getSpotAnimation();
if (FREEZEANIMS.contains(anim))
{ {
this.healers.add(npc); nylos.removeIf(c -> c.getNpc() == npc);
} }
} }
} }
public void onNpcDespawned(NpcDespawned event) public void onNpcSpawned(NpcSpawned event)
{ {
NPC npc = event.getNpc(); NPC npc = event.getNpc();
String name = npc.getName();
int id = npc.getId();
if (npc.getName() != null && name.equals("The Maiden of Sugadinti")) if (npc.getName() == null)
{
this.onStop();
}
else if (plugin.getRoom() == TheatreRoom.MAIDEN)
{
if (id == NpcID.BLOOD_SPAWN)
{
bloodSpawns.remove(npc);
}
}
}
public void onGameTick()
{
if (plugin.getRoom() != TheatreRoom.MAIDEN)
{ {
return; return;
} }
bloodThrows.clear(); switch (npc.getName())
for (GraphicsObject o : client.getGraphicsObjects())
{ {
if (o.getId() == TheatreConstant.MAIDEN_BLOOD_THROW) case "The Maiden of Sugadinti":
this.onStart();
maiden = npc;
break;
case "Nylocas Matomenos":
if (!config.showNyloFreezeHighlights())
{
return;
}
this.healers.add(npc);
WorldPoint wp = WorldPoint.fromLocalInstance(client, npc.getLocalLocation());
if (N1.contains(wp))
{
addNylo(npc, Nylos.SpawnLocation.N1);
}
if (N2.contains(wp))
{
addNylo(npc, Nylos.SpawnLocation.N2);
}
if (S1.contains(wp))
{
addNylo(npc, Nylos.SpawnLocation.S1);
}
if (S2.contains(wp))
{
addNylo(npc, Nylos.SpawnLocation.S2);
}
if (!N1.contains(wp) && !N2.contains(wp) && !S1.contains(wp) && !S2.contains(wp))
{
log.debug("------------------------");
log.debug("No World Points Matched");
log.debug("Dumping Location");
log.debug("Instance Loc: " + wp);
log.debug("------------------------");
}
break;
case "Blood spawn":
if (!bloodSpawns.contains(npc))
{
bloodSpawns.add(npc);
}
break;
}
}
public void onChatMessage(ChatMessage event)
{
if (event.getSender() != null && !event.getSender().equals(client.getLocalPlayer().getName()))
{
return;
}
String msg = Text.standardize(event.getMessageNode().getValue());
switch (msg)
{
case "n1":
case "n2":
case "s1":
case "s2":
nyloCall = msg;
break;
}
}
public void onNpcDespawned(NpcDespawned event)
{
NPC npc = event.getNpc();
if (npc.getName() == null)
{
return;
}
switch (npc.getName())
{
case "The Maiden of Sugadinti":
this.onStop();
break;
case "Blood Spawn":
bloodSpawns.remove(npc);
break;
}
}
public void onGameTick()
{
if (plugin.getRoom() != TheatreRoom.MAIDEN)
{
return;
}
if (!nylos.isEmpty())
{
for (Nylos nylo : nylos)
{
nylos.removeIf(c -> c.getNpc().getId() == -1);
}
}
bloodThrows.clear();
for (GraphicsObject o : client.getGraphicsObjects())
{
if (o.getId() == TheatreConstant.MAIDEN_BLOOD_THROW)
{ {
bloodThrows.add(WorldPoint.fromLocal(client, o.getLocation())); bloodThrows.add(WorldPoint.fromLocal(client, o.getLocation()));
} }
@@ -164,12 +300,13 @@ public class MaidenHandler extends RoomHandler
bloodSpawnLocation = new ArrayList<>(bloodSpawnTarget); bloodSpawnLocation = new ArrayList<>(bloodSpawnTarget);
bloodSpawnTarget.clear(); bloodSpawnTarget.clear();
for (NPC spawn : bloodSpawns)
for (NPC spawn : bloodSpawns)
{ {
bloodSpawnTarget.add(spawn.getWorldLocation()); bloodSpawnTarget.add(spawn.getWorldLocation());
} }
if (this.healerCount != this.healers.size()) if (this.healerCount != this.healers.size())
{ {
this.healerCount = this.healers.size(); this.healerCount = this.healers.size();
@@ -181,7 +318,15 @@ public class MaidenHandler extends RoomHandler
int percentage = 70 - (20 * ((wave++) - 1)); int percentage = 70 - (20 * ((wave++) - 1));
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Maiden of Sugadinti - " + percentage + "%' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Maiden of Sugadinti - " + percentage + "%' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
} }
private void addNylo(NPC npc, Nylos.SpawnLocation spawnLocation)
{
nylos.add(new Nylos(npc, spawnLocation));
}
} }

View File

@@ -0,0 +1,36 @@
package net.runelite.client.plugins.theatre.rooms;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.Setter;
import net.runelite.api.NPC;
class Nylos
{
@Getter
private NPC npc;
@Getter
private int npcIndex;
@Getter
@Setter
private SpawnLocation spawnLocation;
Nylos(NPC npc, SpawnLocation spawnLocation)
{
this.npc = npc;
this.npcIndex = npc.getIndex();
this.spawnLocation = spawnLocation;
}
@Getter
@AllArgsConstructor
enum SpawnLocation
{
N1("n1"),
N2("n2"),
S1("s1"),
S2("s2");
private String name;
}
}

View File

@@ -1,9 +1,23 @@
package net.runelite.client.plugins.theatre.rooms; package net.runelite.client.plugins.theatre.rooms;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Polygon;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import net.runelite.api.*; import net.runelite.api.Client;
import net.runelite.api.GroundObject;
import net.runelite.api.NPC;
import net.runelite.api.NpcID;
import net.runelite.api.Point; import net.runelite.api.Point;
import net.runelite.api.Projectile;
import net.runelite.api.Tile;
import net.runelite.api.coords.WorldPoint; import net.runelite.api.coords.WorldPoint;
import net.runelite.api.events.GroundObjectSpawned; import net.runelite.api.events.GroundObjectSpawned;
import net.runelite.api.events.NpcDespawned; import net.runelite.api.events.NpcDespawned;
@@ -16,33 +30,24 @@ import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import net.runelite.client.ui.overlay.OverlayUtil; import net.runelite.client.ui.overlay.OverlayUtil;
import java.awt.*;
import java.util.*;
import java.util.List;
public class SotetsegHandler extends RoomHandler public class SotetsegHandler extends RoomHandler
{ {
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private final Map<GroundObject, Tile> redTiles = new LinkedHashMap<>(); private final Map<GroundObject, Tile> redTiles = new LinkedHashMap<>();
//My variables
private int playerX;
private int playerY;
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private List<WorldPoint> redOverworld = new ArrayList<>(); private List<WorldPoint> redOverworld = new ArrayList<>();
private List<WorldPoint> blackOverworld = new ArrayList<>(); private List<WorldPoint> blackOverworld = new ArrayList<>();
private List<WorldPoint> blackUnderworld = new ArrayList<>(); private List<WorldPoint> blackUnderworld = new ArrayList<>();
private List<WorldPoint> redUnderworld = new ArrayList<>(); private List<WorldPoint> redUnderworld = new ArrayList<>();
private List<Point> gridPath = new ArrayList<>(); private List<Point> gridPath = new ArrayList<>();
//My variables
int playerX;
int playerY;
private Map<Projectile, WorldPoint> soteyProjectiles = new HashMap<>(); private Map<Projectile, WorldPoint> soteyProjectiles = new HashMap<>();
private NPC npc; private NPC npc;
private long startTime = 0; private long startTime = 0;
public SotetsegHandler(Client client, TheatrePlugin plugin, TheatreConfig config) public SotetsegHandler(Client client, TheatrePlugin plugin, TheatreConfig config)
{ {
super(client, plugin, config); super(client, plugin, config);
@@ -52,7 +57,9 @@ public class SotetsegHandler extends RoomHandler
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.SOTETSEG) if (this.plugin.getRoom() == TheatreRoom.SOTETSEG)
{
return; return;
}
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.SOTETSEG); this.plugin.setRoom(TheatreRoom.SOTETSEG);
@@ -125,68 +132,16 @@ public class SotetsegHandler extends RoomHandler
String countdownStr; String countdownStr;
if (id == 1607) if (id == 1607)
{ {
countdownStr = "R " + String.valueOf(ticksRemaining); countdownStr = "R " + ticksRemaining;
} }
else else
{ {
countdownStr = "M " + String.valueOf(ticksRemaining); countdownStr = "M " + ticksRemaining;
} }
projectileMap.put(p, countdownStr); projectileMap.put(p, countdownStr);
} }
renderProjectiles(graphics, projectileMap); renderProjectiles(graphics, projectileMap);
//Legacy code from yuri, works great but shows all projectiles not just ones targetting local player
/**
for (Projectile projectile : client.getProjectiles())
{
int id = projectile.getId();
String name = null;
Color color = null;
double millis = projectile.getRemainingCycles();
double ticks = millis / 60; // 10 millis per cycle, 0.6 ticks per second, 10/0.6 = 60
double round = Math.round(ticks * 10d) / 10d;
if (id == TheatreConstant.SOTETSEG_BOMB)
{
name = "" + round;
color = Color.WHITE;
}
else if (id == TheatreConstant.SOTETSEG_MAGE)
{
name = "" + round;
color = new Color(64, 224, 208, 255);
}
else if (id == TheatreConstant.SOTETSEG_RANGE)
{
name = "" + round;
color = new Color(57, 255, 20, 255);
}
if (name != null)
{
int x = (int) projectile.getX();
int y = (int) projectile.getY();
LocalPoint point = new LocalPoint(x, y);
Point loc = Perspective.getCanvasTextLocation(client, graphics, point, name, 0);
if (loc != null)
{
if (id == TheatreConstant.SOTETSEG_BOMB)
{
graphics.setFont(new Font("Arial", Font.BOLD, 20));
}
else
{
graphics.setFont(new Font("Arial", Font.BOLD, 17));
}
OverlayUtil.renderTextLocation(graphics, loc, name, color);
}
}
}**/
} }
} }
@@ -242,12 +197,16 @@ public class SotetsegHandler extends RoomHandler
if (t.getPlane() == 0) if (t.getPlane() == 0)
{ {
if (!blackOverworld.contains(p)) if (!blackOverworld.contains(p))
{
blackOverworld.add(p); blackOverworld.add(p);
}
} }
else else
{ {
if (!blackUnderworld.contains(p)) if (!blackUnderworld.contains(p))
{
blackUnderworld.add(p); blackUnderworld.add(p);
}
} }
} }
@@ -265,7 +224,9 @@ public class SotetsegHandler extends RoomHandler
else else
{ {
if (!redUnderworld.contains(p)) if (!redUnderworld.contains(p))
{
redUnderworld.add(p); redUnderworld.add(p);
}
} }
} }
} }
@@ -282,19 +243,10 @@ public class SotetsegHandler extends RoomHandler
playerY = client.getLocalPlayer().getLocalLocation().getY(); playerY = client.getLocalPlayer().getLocalLocation().getY();
//Remove projectiles that are about to die //Remove projectiles that are about to die
if (!soteyProjectiles.isEmpty()) if (!soteyProjectiles.isEmpty())
{ {
for (Iterator<Projectile> it = soteyProjectiles.keySet().iterator(); it.hasNext(); ) soteyProjectiles.keySet().removeIf(p -> p.getRemainingCycles() < 1);
{
Projectile projectile = it.next();
if (projectile.getRemainingCycles() < 1)
{
it.remove();
}
}
} }
boolean sotetsegFighting = false; boolean sotetsegFighting = false;
@@ -338,7 +290,7 @@ public class SotetsegHandler extends RoomHandler
WorldPoint pW = new WorldPoint(p.getX() - 1, p.getY(), p.getPlane()); WorldPoint pW = new WorldPoint(p.getX() - 1, p.getY(), p.getPlane());
if (!((redUnderworld.contains(pN) && redUnderworld.contains(pS)) || if (!((redUnderworld.contains(pN) && redUnderworld.contains(pS)) ||
(redUnderworld.contains(pE) && redUnderworld.contains(pW)))) (redUnderworld.contains(pE) && redUnderworld.contains(pW))))
{ {
gridPath.add(new Point(p.getX() - minX, p.getY() - minY)); gridPath.add(new Point(p.getX() - minX, p.getY() - minY));
if (!messageSent) if (!messageSent)

View File

@@ -1,5 +1,12 @@
package net.runelite.client.plugins.theatre.rooms; package net.runelite.client.plugins.theatre.rooms;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.util.HashMap;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import net.runelite.api.Actor; import net.runelite.api.Actor;
@@ -22,38 +29,26 @@ import net.runelite.client.plugins.theatre.TheatreConfig;
import net.runelite.client.plugins.theatre.TheatreConstant; import net.runelite.client.plugins.theatre.TheatreConstant;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import java.awt.*;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class VerzikHandler extends RoomHandler public class VerzikHandler extends RoomHandler
{ {
@Getter(AccessLevel.PACKAGE) @Getter(AccessLevel.PACKAGE)
private final Map<Projectile, WorldPoint> Verzik_RangeProjectiles = new HashMap<>(); private final Map<Projectile, WorldPoint> Verzik_RangeProjectiles = new HashMap<>();
//My variables
private int redCrabsTimer;
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private int versikCounter = 0; private int versikCounter = 0;
private int attacksLeft = 0; private int attacksLeft = 0;
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private NPC npc; private NPC npc;
private int lastId = -1; private int lastId = -1;
private int autosSinceYellows; private int autosSinceYellows;
private int yellows; private int yellows;
private boolean tornados; private boolean tornados;
private int attackTick = -1; private int attackTick = -1;
private long startTime = 0; private long startTime = 0;
//My variables
int redCrabsTimer;
public VerzikHandler(Client client, TheatrePlugin plugin, TheatreConfig config) public VerzikHandler(Client client, TheatrePlugin plugin, TheatreConfig config)
{ {
super(client, plugin, config); super(client, plugin, config);
@@ -63,7 +58,9 @@ public class VerzikHandler extends RoomHandler
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.VERSIK) if (this.plugin.getRoom() == TheatreRoom.VERSIK)
{
return; return;
}
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.VERSIK); this.plugin.setRoom(TheatreRoom.VERSIK);
@@ -117,10 +114,10 @@ public class VerzikHandler extends RoomHandler
if (this.versikCounter >= 0) if (this.versikCounter >= 0)
{ {
String str = Integer.toString(versikCounter); String str = Integer.toString(versikCounter);
LocalPoint lp = npc.getLocalLocation(); LocalPoint lp = npc.getLocalLocation();
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, str, 0); Point point = Perspective.getCanvasTextLocation(client, graphics, lp, str, 0);
renderTextLocation(graphics, str, 20, Font.BOLD, Color.CYAN, point); renderTextLocation(graphics, str, 20, Font.BOLD, Color.CYAN, point);
} }
} }
@@ -141,19 +138,6 @@ public class VerzikHandler extends RoomHandler
} }
} }
/*
if (npc.getAnimation() == 8117){
if (this.redCrabsTimer > 0){
String str = Integer.toString(redCrabsTimer);
LocalPoint lp = npc.getLocalLocation();
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, str, 60);
renderTextLocation(graphics, str, 15, Font.BOLD, Color.WHITE, point);
}
}*/
else if (id == TheatreConstant.VERZIK_ID_P3) else if (id == TheatreConstant.VERZIK_ID_P3)
{ {
if (config.p3attacks()) if (config.p3attacks())
@@ -162,10 +146,10 @@ public class VerzikHandler extends RoomHandler
if (versikCounter > 0 && versikCounter < 8) if (versikCounter > 0 && versikCounter < 8)
{ {
String str = Math.max(versikCounter, 0) + "";// + " | " + model.getModelHeight();// + " | " + model.getRadius(); String str = Math.max(versikCounter, 0) + "";// + " | " + model.getModelHeight();// + " | " + model.getRadius();
LocalPoint lp = npc.getLocalLocation(); LocalPoint lp = npc.getLocalLocation();
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, str, 0); Point point = Perspective.getCanvasTextLocation(client, graphics, lp, str, 0);
renderTextLocation(graphics, str, 15, Font.BOLD, Color.WHITE, point); renderTextLocation(graphics, str, 15, Font.BOLD, Color.WHITE, point);
} }
} }
@@ -210,16 +194,22 @@ public class VerzikHandler extends RoomHandler
for (NPC npc : client.getNpcs()) for (NPC npc : client.getNpcs())
{ {
if (npc.getName() == null) if (npc.getName() == null)
{
continue; continue;
}
Pattern p = Pattern.compile("Nylocas (Hagios|Toxobolos|Ischyros)"); Pattern p = Pattern.compile("Nylocas (Hagios|Toxobolos|Ischyros)");
Matcher m = p.matcher(npc.getName()); Matcher m = p.matcher(npc.getName());
if (!m.matches()) if (!m.matches())
{
continue; continue;
}
Actor target = npc.getInteracting(); Actor target = npc.getInteracting();
if (target == null || target.getName() == null) if (target == null || target.getName() == null)
{
continue; continue;
}
LocalPoint lp = npc.getLocalLocation(); LocalPoint lp = npc.getLocalLocation();
Color color = local.getName().equals(target.getName()) ? Color.RED : Color.GREEN; Color color = local.getName().equals(target.getName()) ? Color.RED : Color.GREEN;
@@ -231,15 +221,17 @@ public class VerzikHandler extends RoomHandler
} }
} }
public void onProjectileMoved(ProjectileMoved event)
{ public void onProjectileMoved(ProjectileMoved event)
Projectile projectile = event.getProjectile();
if (projectile.getId() == 1583)
{ {
WorldPoint p = WorldPoint.fromLocal(client, event.getPosition()); Projectile projectile = event.getProjectile();
Verzik_RangeProjectiles.put(projectile, p); if (projectile.getId() == 1583)
{
WorldPoint p = WorldPoint.fromLocal(client, event.getPosition());
Verzik_RangeProjectiles.put(projectile, p);
}
} }
}
public void onNpcSpawned(NpcSpawned event) public void onNpcSpawned(NpcSpawned event)
{ {
NPC npc = event.getNpc(); NPC npc = event.getNpc();
@@ -282,7 +274,9 @@ public void onProjectileMoved(ProjectileMoved event)
Actor actor = event.getActor(); Actor actor = event.getActor();
if (!(actor instanceof NPC)) if (!(actor instanceof NPC))
{
return; return;
}
NPC npc = (NPC) actor; NPC npc = (NPC) actor;
int id = npc.getId(); int id = npc.getId();
@@ -325,29 +319,22 @@ public void onProjectileMoved(ProjectileMoved event)
} }
if (!Verzik_RangeProjectiles.isEmpty()) if (!Verzik_RangeProjectiles.isEmpty())
{ {
for (Iterator<Projectile> it = Verzik_RangeProjectiles.keySet().iterator(); it.hasNext();) Verzik_RangeProjectiles.keySet().removeIf(p -> p.getRemainingCycles() < 1);
{
Projectile projectile = it.next();
if (projectile.getRemainingCycles() < 1)
{
it.remove();
}
}
} }
if (this.yellows == 0) if (this.yellows == 0)
{ {
//if (this.autosSinceYellows > 0){ //if (this.autosSinceYellows > 0){
for (GraphicsObject object : client.getGraphicsObjects()) for (GraphicsObject object : client.getGraphicsObjects())
{
if (object.getId() == TheatreConstant.GRAPHIC_ID_YELLOWS)
{ {
if (object.getId() == TheatreConstant.GRAPHIC_ID_YELLOWS) this.yellows = 14;
{
this.yellows = 14;
// this.versikCounter = 22; // this.versikCounter = 22;
this.autosSinceYellows = 0; this.autosSinceYellows = 0;
System.out.println("Yellows have spawned."); System.out.println("Yellows have spawned.");
break; break;
}
} }
}
//} //}
} }
else else
@@ -380,7 +367,9 @@ public void onProjectileMoved(ProjectileMoved event)
} }
if (foundTornado && foundVerzik) if (foundTornado && foundVerzik)
{
break; break;
}
} }
if (!foundVerzik) if (!foundVerzik)
@@ -390,7 +379,9 @@ public void onProjectileMoved(ProjectileMoved event)
} }
if (npc == null) if (npc == null)
{
return; return;
}
int id = npc.getId(); int id = npc.getId();
@@ -410,7 +401,9 @@ public void onProjectileMoved(ProjectileMoved event)
long minutes = seconds / 60L; long minutes = seconds / 60L;
seconds = seconds % 60; seconds = seconds % 60;
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Final Challenge - Part 1' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Final Challenge - Part 1' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
else if (id == TheatreConstant.VERZIK_ID_P2_TRANSFORM && this.startTime != 0) else if (id == TheatreConstant.VERZIK_ID_P2_TRANSFORM && this.startTime != 0)
{ {
@@ -424,7 +417,9 @@ public void onProjectileMoved(ProjectileMoved event)
this.versikCounter = -1; this.versikCounter = -1;
this.attacksLeft = 9; this.attacksLeft = 9;
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Final Challenge - Part 2' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Final Challenge - Part 2' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
} }
@@ -443,7 +438,9 @@ public void onProjectileMoved(ProjectileMoved event)
{ {
versikCounter--; versikCounter--;
if (versikCounter < 0) if (versikCounter < 0)
{
versikCounter = 0; versikCounter = 0;
}
} }
else if (id == TheatreConstant.VERZIK_ID_P3) else if (id == TheatreConstant.VERZIK_ID_P3)
{ {

View File

@@ -1,5 +1,17 @@
package net.runelite.client.plugins.theatre.rooms.nylocas; package net.runelite.client.plugins.theatre.rooms.nylocas;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.Polygon;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import lombok.Setter; import lombok.Setter;
@@ -18,41 +30,26 @@ import net.runelite.client.plugins.theatre.TheatreConstant;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import java.awt.*; public class NyloHandler extends RoomHandler
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class NyloHandler extends RoomHandler
{ {
public long startTime = 0L;
int startTick = 0;
ArrayList<NPC> waveSpawns = new ArrayList<NPC>();
ArrayList<NPC> waveAgros = new ArrayList<NPC>();
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private Map<NPC, Integer> pillars = new HashMap<>(); private Map<NPC, Integer> pillars = new HashMap<>();
@Getter(AccessLevel.PUBLIC) @Getter(AccessLevel.PUBLIC)
private Map<NPC, Integer> spiders = new HashMap<>(); private Map<NPC, Integer> spiders = new HashMap<>();
@Getter @Getter
@Setter @Setter
private int wave = 0; private int wave = 0;
private NyloOverlay overlay = null; private NyloOverlay overlay = null;
private NyloPredictor predictor = null; private NyloPredictor predictor = null;
private Point south = new Point(64, 41); private Point south = new Point(64, 41);
private Point west = new Point(49, 56); private Point west = new Point(49, 56);
private Point east = new Point(78, 56); private Point east = new Point(78, 56);
public long startTime = 0L;
public int startTick = 0;
public ArrayList<NPC> waveSpawns = new ArrayList<NPC>();
public ArrayList<NPC> waveAgros = new ArrayList<NPC>();
public NyloHandler(Client client, TheatrePlugin plugin, TheatreConfig config) public NyloHandler(Client client, TheatrePlugin plugin, TheatreConfig config)
{ {
super(client, plugin, config); super(client, plugin, config);
@@ -62,7 +59,9 @@ public class NyloHandler extends RoomHandler
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.NYLOCAS) if (this.plugin.getRoom() == TheatreRoom.NYLOCAS)
{
return; return;
}
this.reset(); this.reset();
@@ -102,7 +101,9 @@ public class NyloHandler extends RoomHandler
if (this.startTime != 0) if (this.startTime != 0)
{ {
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Nylocas - Waves' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'The Nylocas - Waves' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
System.out.println("Stopping Nylocas Room"); System.out.println("Stopping Nylocas Room");
} }
@@ -159,7 +160,7 @@ public class NyloHandler extends RoomHandler
for (NPC npc : pillars.keySet()) for (NPC npc : pillars.keySet())
{ {
final int health = pillars.get(npc); final int health = pillars.get(npc);
final String healthStr = String.valueOf(health) + "%"; final String healthStr = health + "%";
WorldPoint p = npc.getWorldLocation(); WorldPoint p = npc.getWorldLocation();
LocalPoint lp = LocalPoint.fromWorld(client, p.getX() + 1, p.getY() + 1); LocalPoint lp = LocalPoint.fromWorld(client, p.getX() + 1, p.getY() + 1);
@@ -203,45 +204,21 @@ public class NyloHandler extends RoomHandler
Set<NPC> toHighlight = new HashSet<NPC>(); Set<NPC> toHighlight = new HashSet<NPC>();
/** if (config.highlightNyloAgros())
if (config.highlightNyloParents())
{
for (NPC npc : new ArrayList<NPC>(this.waveSpawns))
{
try
{
if (npc.getHealthRatio() == 0 || npc.isDead())
{
this.waveSpawns.remove(npc);
continue;
}
if (!toHighlight.contains(npc))
toHighlight.add(npc);
}
catch (Exception ex)
{
}
}
}**/
if (config.highlightNyloAgros())
{ {
for (NPC npc : new ArrayList<NPC>(this.waveAgros)) for (NPC npc : new ArrayList<NPC>(this.waveAgros))
{ {
try try
{ {
if (npc.getHealthRatio() == 0 || npc.isDead()) if (npc.getHealthRatio() == 0 || npc.isDead())
{ {
this.waveAgros.remove(npc); this.waveAgros.remove(npc);
continue; continue;
} }
if (!toHighlight.contains(npc)) toHighlight.add(npc);
toHighlight.add(npc); }
} catch (Exception ex)
catch (Exception ex)
{ {
} }
@@ -258,58 +235,25 @@ public class NyloHandler extends RoomHandler
String name = npc.getName() != null ? npc.getName() : ""; String name = npc.getName() != null ? npc.getName() : "";
if (name.contains("Hagios")) if (name.contains("Hagios"))
{
color = Color.CYAN; color = Color.CYAN;
}
else if (name.contains("Toxobolos")) else if (name.contains("Toxobolos"))
{
color = Color.GREEN; color = Color.GREEN;
}
else else
{
color = Color.LIGHT_GRAY; color = Color.LIGHT_GRAY;
}
renderPoly(graphics, color, objectClickbox); renderPoly(graphics, color, objectClickbox);
} }
catch (Exception ex) catch (Exception ex)
{ {
} }
} }
/**
if (config.showNylocasSpawns() && predictor != null)
{
NyloPredictor.Wave nextWave = predictor.getNextWave();
if (nextWave != null)
{
TheatreConfig.NYLOCAS mark = config.highlightNyloRoles();
String southStr = predictor.getSpawnStr(NyloPredictor.Spawn.SOUTH, nextWave);
if (southStr != null && south != null)
{
LocalPoint lp = LocalPoint.fromScene(south.getX(), south.getY());
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, southStr, 1);
Color color = mark != TheatreConfig.NYLOCAS.NONE ? (((southStr.contains("Mage") && mark == TheatreConfig.NYLOCAS.MAGE) || (southStr.contains("Range") && mark == TheatreConfig.NYLOCAS.RANGER) || (southStr.contains("Melee") && mark == TheatreConfig.NYLOCAS.MELEE)) ? Color.MAGENTA : Color.RED) : Color.RED;
renderTextLocation(graphics, southStr, 18, Font.BOLD, color, point);
// drawTile(graphics, WorldPoint.fromLocal(client, lp), new Color(0, 150, 200), 2, 150, 10);
}
String westStr = predictor.getSpawnStr(NyloPredictor.Spawn.WEST, nextWave);
if (westStr != null && west != null)
{
LocalPoint lp = LocalPoint.fromScene(west.getX(), west.getY());
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, westStr, 1);
Color color = mark != TheatreConfig.NYLOCAS.NONE ? (((westStr.contains("Mage") && mark == TheatreConfig.NYLOCAS.MAGE) || (westStr.contains("Range") && mark == TheatreConfig.NYLOCAS.RANGER) || (westStr.contains("Melee") && mark == TheatreConfig.NYLOCAS.MELEE)) ? Color.MAGENTA : Color.RED) : Color.RED;
renderTextLocation(graphics, westStr, 18, Font.BOLD, color, point);
// drawTile(graphics, WorldPoint.fromLocal(client, lp), new Color(0, 150, 200), 2, 150, 10);
}
String eastStr = predictor.getSpawnStr(NyloPredictor.Spawn.EAST, nextWave);
if (eastStr != null && east != null)
{
LocalPoint lp = LocalPoint.fromScene(east.getX(), east.getY());
Point point = Perspective.getCanvasTextLocation(client, graphics, lp, eastStr, 1);
Color color = mark != TheatreConfig.NYLOCAS.NONE ? (((eastStr.contains("Mage") && mark == TheatreConfig.NYLOCAS.MAGE) || (eastStr.contains("Range") && mark == TheatreConfig.NYLOCAS.RANGER) || (eastStr.contains("Melee") && mark == TheatreConfig.NYLOCAS.MELEE)) ? Color.MAGENTA : Color.RED) : Color.RED;
renderTextLocation(graphics, eastStr, 18, Font.BOLD, color, point);
// drawTile(graphics, WorldPoint.fromLocal(client, lp), new Color(0, 150, 200), 2, 150, 10);
}
}
}**/
} }
public void onNpcSpawned(NpcSpawned event) public void onNpcSpawned(NpcSpawned event)
@@ -351,15 +295,9 @@ public class NyloHandler extends RoomHandler
NPC npc = event.getNpc(); NPC npc = event.getNpc();
int id = npc.getId(); int id = npc.getId();
if (this.waveSpawns.contains(npc)) this.waveSpawns.remove(npc);
{
this.waveSpawns.remove(npc);
}
if (this.waveAgros.contains(npc)) this.waveAgros.remove(npc);
{
this.waveAgros.remove(npc);
}
if (id == TheatreConstant.NPC_ID_NYLOCAS_PILLAR) if (id == TheatreConstant.NPC_ID_NYLOCAS_PILLAR)
{ {
@@ -393,7 +331,7 @@ public class NyloHandler extends RoomHandler
if (plugin.getRoom() != TheatreRoom.NYLOCAS) if (plugin.getRoom() != TheatreRoom.NYLOCAS)
{ {
return; return;
} }
else else
{ {
boolean findPillar = false; boolean findPillar = false;

View File

@@ -43,18 +43,17 @@ import net.runelite.client.ui.overlay.components.table.TableAlignment;
import net.runelite.client.ui.overlay.components.table.TableComponent; import net.runelite.client.ui.overlay.components.table.TableComponent;
import net.runelite.client.util.ColorUtil; import net.runelite.client.util.ColorUtil;
class NyloOverlay extends Overlay class NyloOverlay extends Overlay
{ {
private final Client client; private final Client client;
private final TheatrePlugin plugin; private final TheatrePlugin plugin;
private final TheatreConfig config;
private final PanelComponent panelComponent = new PanelComponent(); private final PanelComponent panelComponent = new PanelComponent();
private NyloHandler nylohandler; private NyloHandler nylohandler;
public NyloOverlay(Client client, TheatrePlugin plugin, TheatreConfig config, NyloHandler nylohandler) NyloOverlay(Client client, TheatrePlugin plugin, TheatreConfig config, NyloHandler nylohandler)
{ {
super(plugin); super(plugin);
@@ -63,7 +62,6 @@ class NyloOverlay extends Overlay
this.client = client; this.client = client;
this.plugin = plugin; this.plugin = plugin;
this.config = config;
this.nylohandler = nylohandler; this.nylohandler = nylohandler;
getMenuEntries().add(new OverlayMenuEntry(RUNELITE_OVERLAY_CONFIG, OPTION_CONFIGURE, "Nylocas Overlay")); getMenuEntries().add(new OverlayMenuEntry(RUNELITE_OVERLAY_CONFIG, OPTION_CONFIGURE, "Nylocas Overlay"));
@@ -111,14 +109,14 @@ class NyloOverlay extends Overlay
if (nyloCount > 12) if (nyloCount > 12)
{ {
tableComponent.addRow("Total Nylocas:", ColorUtil.prependColorTag(nyloCount + " / 12", Color.RED)); tableComponent.addRow("Total Nylocas:", ColorUtil.prependColorTag(nyloCount + " / 12", Color.RED));
} }
else else
{ {
tableComponent.addRow("Total Nylocas:", ColorUtil.prependColorTag(nyloCount + " / 12", Color.GREEN)); tableComponent.addRow("Total Nylocas:", ColorUtil.prependColorTag(nyloCount + " / 12", Color.GREEN));
} }
} }
else else
{ {
if (nyloCount > 24) if (nyloCount > 24)
{ {
@@ -132,23 +130,6 @@ class NyloOverlay extends Overlay
panelComponent.getChildren().add(tableComponent); panelComponent.getChildren().add(tableComponent);
/**
panelComponent.getChildren().add(LineComponent.builder()
.left("Ischyros:")
.right(Integer.toString(ischyros))
.build());
panelComponent.getChildren().add(LineComponent.builder()
.left("Toxobolos:")
.right(Integer.toString(toxobolos))
.build());
panelComponent.getChildren().add(LineComponent.builder()
.left("Hagios:")
.right(Integer.toString(hagios))
.build());
**/
return panelComponent.render(graphics); return panelComponent.render(graphics);
} }
} }

View File

@@ -1,91 +1,19 @@
package net.runelite.client.plugins.theatre.rooms.nylocas; package net.runelite.client.plugins.theatre.rooms.nylocas;
import net.runelite.api.Client;
import net.runelite.api.NPC;
import net.runelite.api.coords.LocalPoint;
import net.runelite.api.events.NpcSpawned;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import net.runelite.api.Client;
import net.runelite.api.NPC;
import net.runelite.api.coords.LocalPoint;
import net.runelite.api.events.NpcSpawned;
public class NyloPredictor public class NyloPredictor
{ {
public enum NylocasType private static final Wave[] NYLOCAS_WAVES = new Wave[]
{
MELEE_162,
RANGE_162,
MAGE_162,
MELEE_260,
RANGE_260,
MAGE_260;
}
public enum Spawn
{
WEST,
SOUTH,
EAST;
}
public static class Nylocas
{
private NylocasType type;
private Spawn spawn;
public Nylocas(NylocasType type, Spawn spawn)
{ {
this.type = type;
this.spawn = spawn;
}
public NylocasType getType()
{
return this.type;
}
public Spawn getSpawn()
{
return this.spawn;
}
@Override
public boolean equals(Object object)
{
if (object != null && (object instanceof Nylocas))
{
Nylocas nylo = (Nylocas) object;
if (nylo.getType() == this.type && nylo.getSpawn() == this.spawn)
{
return true;
}
}
return false;
}
}
public static class Wave
{
private Nylocas[] spawns;
public Wave(Nylocas... nylocas)
{
this.spawns = nylocas;
}
public Nylocas[] getSpawns()
{
return this.spawns;
}
}
public static final Wave[] NYLOCAS_WAVES = new Wave[]
{
new Wave(new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.EAST)), new Wave(new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.EAST)),
new Wave(new Nylocas(NylocasType.MAGE_162, Spawn.WEST), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST)), new Wave(new Nylocas(NylocasType.MAGE_162, Spawn.WEST), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST)),
new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MAGE_162, Spawn.EAST)), new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MAGE_162, Spawn.EAST)),
@@ -117,15 +45,16 @@ public class NyloPredictor
new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MELEE_260, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST), new Nylocas(NylocasType.MAGE_162, Spawn.EAST)), new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MELEE_260, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST), new Nylocas(NylocasType.MAGE_162, Spawn.EAST)),
new Wave(new Nylocas(NylocasType.RANGE_260, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.MAGE_260, Spawn.EAST)), new Wave(new Nylocas(NylocasType.RANGE_260, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.MAGE_260, Spawn.EAST)),
new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST), new Nylocas(NylocasType.MAGE_162, Spawn.EAST)) new Wave(new Nylocas(NylocasType.MELEE_162, Spawn.WEST), new Nylocas(NylocasType.RANGE_162, Spawn.WEST), new Nylocas(NylocasType.MAGE_162, Spawn.SOUTH), new Nylocas(NylocasType.MELEE_162, Spawn.SOUTH), new Nylocas(NylocasType.RANGE_162, Spawn.EAST), new Nylocas(NylocasType.MAGE_162, Spawn.EAST))
}; };
public Client client; public Client client;
public NyloHandler handler; int westBound = 50;
int eastBound = 77;
int southBound = 42;
private NyloHandler handler;
private Map<Nylocas, NPC> currentSpawns = new HashMap<Nylocas, NPC>();
private int currentIndex = -1;
public Map<Nylocas, NPC> currentSpawns = new HashMap<Nylocas, NPC>(); NyloPredictor(Client client, NyloHandler handler)
public int currentIndex = -1;
public NyloPredictor(Client client, NyloHandler handler)
{ {
this.client = client; this.client = client;
this.handler = handler; this.handler = handler;
@@ -138,12 +67,6 @@ public class NyloPredictor
this.currentIndex = -1; this.currentIndex = -1;
} }
public int westBound = 50;
public int eastBound = 77;
public int southBound = 42;
public void onNpcSpawned(NpcSpawned event) public void onNpcSpawned(NpcSpawned event)
{ {
NPC npc = event.getNpc(); NPC npc = event.getNpc();
@@ -157,11 +80,11 @@ public class NyloPredictor
if (x <= westBound) if (x <= westBound)
{ {
spawn = Spawn.WEST; spawn = Spawn.WEST;
} }
else if (x >= eastBound) else if (x >= eastBound)
{ {
spawn = Spawn.EAST; spawn = Spawn.EAST;
} }
else if (y <= southBound) else if (y <= southBound)
{ {
spawn = Spawn.SOUTH; spawn = Spawn.SOUTH;
@@ -175,11 +98,11 @@ public class NyloPredictor
if (name.contains("Hagios")) if (name.contains("Hagios"))
{ {
type = NylocasType.valueOf("MAGE_" + level); type = NylocasType.valueOf("MAGE_" + level);
} }
else if (name.contains("Toxobolos")) else if (name.contains("Toxobolos"))
{ {
type = NylocasType.valueOf("RANGE_" + level); type = NylocasType.valueOf("RANGE_" + level);
} }
else if (name.contains("Ischyros")) else if (name.contains("Ischyros"))
{ {
type = NylocasType.valueOf("MELEE_" + level); type = NylocasType.valueOf("MELEE_" + level);
@@ -213,7 +136,7 @@ public class NyloPredictor
int index = queue.indexOf(nylocas); int index = queue.indexOf(nylocas);
Nylocas hashed = queue.remove(index); Nylocas hashed = queue.remove(index);
npcs.put(currentSpawns.get(hashed), hashed); npcs.put(currentSpawns.get(hashed), hashed);
} }
else else
{ {
found = false; found = false;
@@ -257,12 +180,14 @@ public class NyloPredictor
for (NPC npc : client.getNpcs()) for (NPC npc : client.getNpcs())
{ {
if (npc.getHealthRatio() == 0) if (npc.getHealthRatio() == 0)
{
continue; continue;
}
if (npc.getName().equalsIgnoreCase("Nylocas Hagios")) if (npc.getName().equalsIgnoreCase("Nylocas Hagios"))
{ {
mage_level += npc.getCombatLevel(); mage_level += npc.getCombatLevel();
mage_count += 1; mage_count += 1;
} }
else if (npc.getName().equalsIgnoreCase("Nylocas Toxobolos")) else if (npc.getName().equalsIgnoreCase("Nylocas Toxobolos"))
{ {
range_level += npc.getCombatLevel(); range_level += npc.getCombatLevel();
@@ -300,7 +225,7 @@ public class NyloPredictor
} }
} }
public boolean isAgressive(NylocasType type, Spawn spawn, int wave) private boolean isAgressive(NylocasType type, Spawn spawn, int wave)
{ {
if (wave == 0 && spawn == Spawn.WEST) if (wave == 0 && spawn == Spawn.WEST)
{ {
@@ -329,9 +254,13 @@ public class NyloPredictor
else if (wave == 9) else if (wave == 9)
{ {
if (spawn == Spawn.EAST && type == NylocasType.RANGE_162) if (spawn == Spawn.EAST && type == NylocasType.RANGE_162)
{
return true; return true;
else if (spawn == Spawn.WEST) }
return true; else
{
return spawn == Spawn.WEST;
}
} }
else if (wave == 10 && (spawn == Spawn.EAST || spawn == Spawn.WEST)) else if (wave == 10 && (spawn == Spawn.EAST || spawn == Spawn.WEST))
{ {
@@ -344,23 +273,35 @@ public class NyloPredictor
else if (wave == 12) else if (wave == 12)
{ {
if (spawn == Spawn.WEST && type == NylocasType.MAGE_162) if (spawn == Spawn.WEST && type == NylocasType.MAGE_162)
{
return true; return true;
else if (spawn == Spawn.EAST) }
return true; else
{
return spawn == Spawn.EAST;
}
} }
else if (wave == 13) else if (wave == 13)
{ {
if (spawn == Spawn.WEST && type == NylocasType.MELEE_162) if (spawn == Spawn.WEST && type == NylocasType.MELEE_162)
{
return true; return true;
else if (spawn == Spawn.EAST) }
return true; else
{
return spawn == Spawn.EAST;
}
} }
else if (wave == 14) else if (wave == 14)
{ {
if (spawn == Spawn.WEST && type == NylocasType.RANGE_162) if (spawn == Spawn.WEST && type == NylocasType.RANGE_162)
{
return true; return true;
else if (spawn == Spawn.EAST && type == NylocasType.MAGE_162) }
return true; else
{
return spawn == Spawn.EAST && type == NylocasType.MAGE_162;
}
} }
else if (wave == 17 && spawn == Spawn.WEST) else if (wave == 17 && spawn == Spawn.WEST)
{ {
@@ -405,17 +346,20 @@ public class NyloPredictor
else if (wave == 28) else if (wave == 28)
{ {
if (spawn == Spawn.EAST && type == NylocasType.RANGE_162) if (spawn == Spawn.EAST && type == NylocasType.RANGE_162)
{
return true; return true;
else if (spawn == Spawn.WEST && type == NylocasType.MELEE_162) }
return true; else
{
return spawn == Spawn.WEST && type == NylocasType.MELEE_162;
}
} }
else if (wave == 29 && spawn == Spawn.EAST) else
{ {
return true; return wave == 29 && spawn == Spawn.EAST;
} }
return false;
} }
public int getCurrentWave() public int getCurrentWave()
@@ -487,4 +431,72 @@ public class NyloPredictor
return types.length() > 0 ? types : null; return types.length() > 0 ? types : null;
} }
} }
public enum NylocasType
{
MELEE_162,
RANGE_162,
MAGE_162,
MELEE_260,
RANGE_260,
MAGE_260
}
public enum Spawn
{
WEST,
SOUTH,
EAST
}
public static class Nylocas
{
private NylocasType type;
private Spawn spawn;
public Nylocas(NylocasType type, Spawn spawn)
{
this.type = type;
this.spawn = spawn;
}
public NylocasType getType()
{
return this.type;
}
public Spawn getSpawn()
{
return this.spawn;
}
@Override
public boolean equals(Object object)
{
if (object != null && (object instanceof Nylocas))
{
Nylocas nylo = (Nylocas) object;
return nylo.getType() == this.type && nylo.getSpawn() == this.spawn;
}
return false;
}
}
public static class Wave
{
private Nylocas[] spawns;
public Wave(Nylocas... nylocas)
{
this.spawns = nylocas;
}
public Nylocas[] getSpawns()
{
return this.spawns;
}
}
} }

View File

@@ -22,10 +22,8 @@ public class XarpusCounter extends Overlay
private final Client client; private final Client client;
private final TheatrePlugin plugin; private final TheatrePlugin plugin;
private final TheatreConfig config; private final TheatreConfig config;
private XarpusHandler xarpusHandler;
PanelComponent panelComponent = new PanelComponent(); PanelComponent panelComponent = new PanelComponent();
private XarpusHandler xarpusHandler;
public XarpusCounter(Client client, TheatrePlugin plugin, TheatreConfig config, XarpusHandler xarpushandler) public XarpusCounter(Client client, TheatrePlugin plugin, TheatreConfig config, XarpusHandler xarpushandler)
{ {
@@ -51,13 +49,13 @@ public class XarpusCounter extends Overlay
// Build overlay title // Build overlay title
panelComponent.getChildren().add(TitleComponent.builder() panelComponent.getChildren().add(TitleComponent.builder()
.text(overlayTitle) .text(overlayTitle)
.color(Color.GREEN) .color(Color.GREEN)
.build()); .build());
//Set the size of overlay //Set the size of overlay
panelComponent.setPreferredSize(new Dimension( panelComponent.setPreferredSize(new Dimension(
graphics.getFontMetrics().stringWidth(overlayTitle) + 30, 0 graphics.getFontMetrics().stringWidth(overlayTitle) + 30, 0
)); ));
TableComponent tableComponent = new TableComponent(); TableComponent tableComponent = new TableComponent();

View File

@@ -1,5 +1,13 @@
package net.runelite.client.plugins.theatre.rooms.xarpus; package net.runelite.client.plugins.theatre.rooms.xarpus;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.Polygon;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import lombok.Getter; import lombok.Getter;
import net.runelite.api.ChatMessageType; import net.runelite.api.ChatMessageType;
import net.runelite.api.Client; import net.runelite.api.Client;
@@ -19,20 +27,13 @@ import net.runelite.client.plugins.theatre.TheatreConfig;
import net.runelite.client.plugins.theatre.TheatreConstant; import net.runelite.client.plugins.theatre.TheatreConstant;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.plugins.theatre.TheatreRoom; import net.runelite.client.plugins.theatre.TheatreRoom;
import java.awt.*;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
public class XarpusHandler extends RoomHandler public class XarpusHandler extends RoomHandler
{ {
private int previousTurn;
private boolean staring;
private final Map<GroundObject, Integer> exhumes = new HashMap<>(); private final Map<GroundObject, Integer> exhumes = new HashMap<>();
private int previousTurn;
private boolean staring;
private int ticksUntilShoot = 8; private int ticksUntilShoot = 8;
@Getter @Getter
@@ -56,7 +57,9 @@ public class XarpusHandler extends RoomHandler
public void onStart() public void onStart()
{ {
if (this.plugin.getRoom() == TheatreRoom.XARPUS) if (this.plugin.getRoom() == TheatreRoom.XARPUS)
{
return; return;
}
this.reset(); this.reset();
this.plugin.setRoom(TheatreRoom.XARPUS); this.plugin.setRoom(TheatreRoom.XARPUS);
@@ -102,7 +105,9 @@ public class XarpusHandler extends RoomHandler
public void render(Graphics2D graphics) public void render(Graphics2D graphics)
{ {
if (npc == null) if (npc == null)
{
return; return;
}
if (npc.getId() == NpcID.XARPUS_8340) //&& !staring&& config.showXarpusTick()) if (npc.getId() == NpcID.XARPUS_8340) //&& !staring&& config.showXarpusTick())
{ {
@@ -111,13 +116,15 @@ public class XarpusHandler extends RoomHandler
this.up = true; this.up = true;
long elapsedTime = System.currentTimeMillis() - this.startTime; long elapsedTime = System.currentTimeMillis() - this.startTime;
long seconds = elapsedTime / 1000L; long seconds = elapsedTime / 1000L;
long minutes = seconds / 60L; long minutes = seconds / 60L;
seconds = seconds % 60; seconds = seconds % 60;
this.ticksUntilShoot = 8; this.ticksUntilShoot = 8;
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'Xarpus - Recovery' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'Xarpus - Recovery' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
final String ticksLeftStr = String.valueOf(ticksUntilShoot); final String ticksLeftStr = String.valueOf(ticksUntilShoot);
@@ -257,7 +264,9 @@ public class XarpusHandler extends RoomHandler
long minutes = seconds / 60L; long minutes = seconds / 60L;
seconds = seconds % 60; seconds = seconds % 60;
if (config.extraTimers()) if (config.extraTimers())
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'Xarpus - Acid' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null); {
this.client.addChatMessage(ChatMessageType.GAMEMESSAGE, "", "Wave 'Xarpus - Acid' completed! Duration: <col=ff0000>" + minutes + ":" + twoDigitString(seconds), null);
}
} }
ticksUntilShoot = 6; ticksUntilShoot = 6;
@@ -275,7 +284,7 @@ public class XarpusHandler extends RoomHandler
if (staring) if (staring)
{ {
ticksUntilShoot = 8; ticksUntilShoot = 8;
} }
else else
{ {
ticksUntilShoot = 4; ticksUntilShoot = 4;

View File

@@ -1,18 +1,20 @@
package net.runelite.client.plugins.theatre.timers; package net.runelite.client.plugins.theatre.timers;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics2D;
import javax.inject.Inject;
import net.runelite.api.Client; import net.runelite.api.Client;
import static net.runelite.api.MenuAction.RUNELITE_OVERLAY_CONFIG;
import net.runelite.api.Player; import net.runelite.api.Player;
import net.runelite.client.plugins.theatre.TheatrePlugin; import net.runelite.client.plugins.theatre.TheatrePlugin;
import net.runelite.client.ui.overlay.Overlay; import net.runelite.client.ui.overlay.Overlay;
import static net.runelite.client.ui.overlay.OverlayManager.OPTION_CONFIGURE;
import net.runelite.client.ui.overlay.OverlayMenuEntry; import net.runelite.client.ui.overlay.OverlayMenuEntry;
import net.runelite.client.ui.overlay.OverlayPosition; import net.runelite.client.ui.overlay.OverlayPosition;
import net.runelite.client.ui.overlay.OverlayPriority; import net.runelite.client.ui.overlay.OverlayPriority;
import net.runelite.client.ui.overlay.components.PanelComponent; import net.runelite.client.ui.overlay.components.PanelComponent;
import net.runelite.client.ui.overlay.components.TitleComponent; import net.runelite.client.ui.overlay.components.TitleComponent;
import javax.inject.Inject;
import java.awt.*;
import static net.runelite.api.MenuAction.RUNELITE_OVERLAY_CONFIG;
import static net.runelite.client.ui.overlay.OverlayManager.OPTION_CONFIGURE;
public class RoomTimer extends Overlay public class RoomTimer extends Overlay
{ {
@@ -25,9 +27,9 @@ public class RoomTimer extends Overlay
@Inject @Inject
public RoomTimer (Client client, TheatrePlugin plugin) public RoomTimer(Client client, TheatrePlugin plugin)
{ {
super (plugin); super(plugin);
setPosition(OverlayPosition.ABOVE_CHATBOX_RIGHT); setPosition(OverlayPosition.ABOVE_CHATBOX_RIGHT);
setPriority(OverlayPriority.HIGH); setPriority(OverlayPriority.HIGH);
@@ -40,15 +42,17 @@ public class RoomTimer extends Overlay
@Override @Override
public Dimension render(Graphics2D graphics) public Dimension render(Graphics2D graphics)
{ {
panelComponent.getChildren().clear(); panelComponent.getChildren().clear();
Player local = client.getLocalPlayer(); Player local = client.getLocalPlayer();
if (local == null || local.getName() == null) if (local == null || local.getName() == null)
{
return null; return null;
}
switch (plugin.getRoom()) switch (plugin.getRoom())
{ {
case MAIDEN: case MAIDEN:
plugin.getMaidenHandler().render(graphics); plugin.getMaidenHandler().render(graphics);

View File

@@ -4,5 +4,5 @@ import java.util.HashMap;
public interface Timeable public interface Timeable
{ {
public abstract HashMap<String, Long> getTimes(); HashMap<String, Long> getTimes();
} }

View File

@@ -112,13 +112,7 @@ public abstract class RSNPCMixin implements RSNPC
{ {
client.getCallbacks().post(new NpcDespawned(this)); client.getCallbacks().post(new NpcDespawned(this));
} }
} else if (this.getId() != -1)
@FieldHook("definition")
@Inject
public void afterCompositionChanged(int idx)
{
if (this.getDefinition() != null && this.getId() != -1)
{ {
client.getCallbacks().post(new NpcCompositionChanged(this)); client.getCallbacks().post(new NpcCompositionChanged(this));
} }