Skip to content

Commit

Permalink
Add highlights to mixing vessel
Browse files Browse the repository at this point in the history
  • Loading branch information
BlueSoapTurtle committed Oct 30, 2024
1 parent 76480f0 commit 03fb4d7
Show file tree
Hide file tree
Showing 3 changed files with 123 additions and 15 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ default boolean highlightLevers() {
keyName = "highlightStations",
name = "Highlight stations",
description = "Toggles alchemical station highlighting on or off",
position = 2
position = 3
)
default boolean highlightStations() {
return true;
Expand All @@ -56,17 +56,38 @@ default boolean highlightStations() {
keyName = "highlightQuickActionEvents",
name = "Highlight quick-action events",
description = "Toggles station quick-action events highlighting on or off",
position = 2
position = 4
)
default boolean highlightQuickActionEvents() {
return true;
}

@ConfigItem(
keyName = "highlightMixingVessel",
name = "Highlight mixing vessel",
description = "Highlight the mixing vessel",
position = 5
)
default boolean highlightMixingVessel() {
return true;
}

@ConfigItem(
keyName = "highlightMixingVesselInvalid",
name = "Highlight invalid mixing vessel",
description = "Highlight the mixing vessel red when you have the wrong ingredients",
position = 6
)
// used to enable highlighting the vessel red when you have the wrong ingredients
default boolean highlightMixingVesselInvalid() {
return true;
}

@ConfigItem(
keyName = "identifyPotions",
name = "Identify potions",
description = "Identify potions in your inventory",
position = 2
position = 7
)
default boolean identifyPotions() {
return true;
Expand All @@ -76,7 +97,7 @@ default boolean identifyPotions() {
keyName = "displayResin",
name = "Display resin amount",
description = "Display total resin amounts",
position = 2
position = 8
)
default boolean displayResin() {
return false;
Expand All @@ -86,7 +107,7 @@ default boolean displayResin() {
keyName = "stationHighlightColor",
name = "Station color",
description = "Configures the default station highlight color",
position = 3
position = 9
)
default Color stationHighlightColor() {
return Color.MAGENTA;
Expand All @@ -96,7 +117,7 @@ default Color stationHighlightColor() {
keyName = "stationQuickActionHighlightColor",
name = "Quick-action color",
description = "Configures the station quick-action highlight color",
position = 4
position = 10
)
default Color stationQuickActionHighlightColor() {
return Color.GREEN;
Expand All @@ -106,7 +127,7 @@ default Color stationQuickActionHighlightColor() {
keyName = "notifyDigweed",
name = "Notify DigWeed",
description = "Toggles digweed notifications on or off",
position = 5
position = 11
)
default Notification notifyDigWeed() {
return Notification.ON;
Expand All @@ -116,7 +137,7 @@ default Notification notifyDigWeed() {
keyName = "highlightDigweed",
name = "Highlight DigWeed",
description = "Toggles digweed highlighting on or off",
position = 6
position = 12
)
default boolean highlightDigWeed() {
return true;
Expand All @@ -126,7 +147,7 @@ default boolean highlightDigWeed() {
keyName = "digweedHighlightColor",
name = "DigWeed color",
description = "Configures the digweed highlight color",
position = 7
position = 13
)
default Color digweedHighlightColor() {
return Color.GREEN;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,21 +1,30 @@
package work.fking.masteringmixology;

import net.runelite.api.Client;
import net.runelite.api.Perspective;
import net.runelite.api.Point;
import net.runelite.api.coords.LocalPoint;
import net.runelite.client.ui.FontManager;
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;
import net.runelite.client.ui.overlay.outline.ModelOutlineRenderer;

import javax.inject.Inject;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics2D;

public class MasteringMixologyOverlay extends Overlay {

private final Client client;
private final MasteringMixologyPlugin plugin;
private final ModelOutlineRenderer modelOutlineRenderer;

@Inject
MasteringMixologyOverlay(MasteringMixologyPlugin plugin, ModelOutlineRenderer modelOutlineRenderer) {
MasteringMixologyOverlay(Client client, MasteringMixologyPlugin plugin, ModelOutlineRenderer modelOutlineRenderer) {
this.client = client;
this.plugin = plugin;
this.modelOutlineRenderer = modelOutlineRenderer;
setPosition(OverlayPosition.DYNAMIC);
Expand All @@ -26,7 +35,35 @@ public class MasteringMixologyOverlay extends Overlay {
public Dimension render(Graphics2D graphics) {
for (var highlightedObject : plugin.highlightedObjects().values()) {
modelOutlineRenderer.drawOutline(highlightedObject.object(), highlightedObject.outlineWidth(), highlightedObject.color(), highlightedObject.feather());
drawText(graphics, highlightedObject);
}
return null;
}

private void drawText(Graphics2D graphics, MasteringMixologyPlugin.HighlightedObject highlightedObject) {
String text = highlightedObject.text();
if (text == null || text.isEmpty()) {
return;
}

// Increase the font size
Font font = FontManager.getRunescapeFont().deriveFont(20f);
Font originalFont = graphics.getFont();
graphics.setFont(font);

// Draw the text
LocalPoint textLocation = highlightedObject.object().getLocalLocation();
// Parse </br> in the text and split it into multiple lines
int zOffset = 100;
for (String line : text.split("</br>")) {
Point canvasLocation = Perspective.getCanvasTextLocation(client, graphics, textLocation, line, zOffset);
OverlayUtil.renderTextLocation(graphics, canvasLocation, line, highlightedObject.color());

// Decrease the zOffset with font height + 5 to draw the next line below the previous one
zOffset -= graphics.getFontMetrics().getHeight() + 5;
}

// Set the font back to the original
graphics.setFont(originalFont);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -186,8 +186,9 @@ public void onConfigChanged(ConfigChanged event) {
clientThread.invokeLater(this::updatePotionOrders);
}

if (!config.highlightStations()) {
unHighlightAllStations();
// Refresh the highlight on the vessel if the config changes
if (event.getKey().equals("highlightMixingVessel") || event.getKey().equals("highlightMixingVesselInvalid")) {
clientThread.invokeLater(() -> validateVesselPotion(client.getVarbitValue(VARBIT_MIXING_VESSEL_POTION)));
}

if (!config.highlightDigWeed()) {
Expand Down Expand Up @@ -348,6 +349,45 @@ public void onVarbitChanged(VarbitChanged event) {
} else if (varbitId == VARBIT_ALEMBIC_QUICKACTION) {
// alembic quick action was just successfully popped
resetDefaultHighlight(AlchemyObject.ALEMBIC);
} else if (varbitId == VARBIT_MIXING_VESSEL_POTION) {
validateVesselPotion(value);
}
}

private void validateVesselPotion(int value) {
// Reset when they take out the potion
if (value == 0) {
unHighlightObject(AlchemyObject.MIXING_VESSEL);
return;
}

// Remove the highlight if the config is disabled
if (!config.highlightMixingVessel()) {
unHighlightObject(AlchemyObject.MIXING_VESSEL);
return;
}

// Find the potion in the vessel
PotionType potionInVessel = PotionType.fromIdx(value - 1);
if (potionInVessel == null) {
return;
}

// Check if the potion is valid
boolean validPotion = potionOrders.stream()
.anyMatch(order -> order.potionType() == potionInVessel && !order.fulfilled());

if (validPotion) {
// Highlight the vessel if it contains a valid potion
highlightObject(AlchemyObject.MIXING_VESSEL, Color.GREEN, potionInVessel.abbreviation());
} else {
// Highlight the vessel red if it contains an invalid potion
if (config.highlightMixingVesselInvalid()) {
highlightObject(AlchemyObject.MIXING_VESSEL, Color.RED, potionInVessel.abbreviation() + "</br>Invalid potion");
} else {
// Remove the highlight if the invalid config is disabled
unHighlightObject(AlchemyObject.MIXING_VESSEL);
}
}
}

Expand Down Expand Up @@ -458,6 +498,10 @@ private void initialize() {
}

public void highlightObject(AlchemyObject alchemyObject, Color color) {
highlightObject(alchemyObject, color, null);
}

public void highlightObject(AlchemyObject alchemyObject, Color color, String text) {
var worldView = client.getTopLevelWorldView();

if (worldView == null) {
Expand All @@ -477,15 +521,15 @@ public void highlightObject(AlchemyObject alchemyObject, Color color) {
}

if (gameObject.getId() == alchemyObject.objectId()) {
highlightedObjects.put(alchemyObject, new HighlightedObject(gameObject, color, config.highlightBorderWidth(), config.highlightFeather()));
highlightedObjects.put(alchemyObject, new HighlightedObject(gameObject, color, text, config.highlightBorderWidth(), config.highlightFeather()));
return;
}
}
// The aga lever is actually a wall decoration, not a scenery object
var decorativeObject = tile.getDecorativeObject();

if (decorativeObject != null && decorativeObject.getId() == alchemyObject.objectId()) {
highlightedObjects.put(alchemyObject, new HighlightedObject(decorativeObject, color, config.highlightBorderWidth(), config.highlightFeather()));
highlightedObjects.put(alchemyObject, new HighlightedObject(decorativeObject, color, text, config.highlightBorderWidth(), config.highlightFeather()));
}
}

Expand Down Expand Up @@ -633,12 +677,14 @@ public static class HighlightedObject {

private final TileObject object;
private final Color color;
private final String text;
private final int outlineWidth;
private final int feather;

private HighlightedObject(TileObject object, Color color, int outlineWidth, int feather) {
private HighlightedObject(TileObject object, Color color, String text, int outlineWidth, int feather) {
this.object = object;
this.color = color;
this.text = text;
this.outlineWidth = outlineWidth;
this.feather = feather;
}
Expand All @@ -651,6 +697,10 @@ public Color color() {
return color;
}

public String text() {
return text;
}

public int outlineWidth() {
return outlineWidth;
}
Expand Down

0 comments on commit 03fb4d7

Please sign in to comment.