diff --git a/runelite-api/src/main/java/net/runelite/api/Perspective.java b/runelite-api/src/main/java/net/runelite/api/Perspective.java index d657efbf42..8011ceef15 100644 --- a/runelite-api/src/main/java/net/runelite/api/Perspective.java +++ b/runelite-api/src/main/java/net/runelite/api/Perspective.java @@ -35,10 +35,13 @@ import java.util.ArrayList; import java.util.List; import java.util.stream.Collectors; import javax.annotation.Nonnull; +import javax.annotation.Nullable; import net.runelite.api.coords.LocalPoint; import net.runelite.api.model.Jarvis; import net.runelite.api.model.Triangle; import net.runelite.api.model.Vertex; +import net.runelite.api.widgets.Widget; +import net.runelite.api.widgets.WidgetInfo; /** * A utility class containing methods to help with conversion between @@ -188,6 +191,7 @@ public class Perspective * @return a {@link Point} on screen corresponding to the position in * 3D-space */ + @Nullable public static Point worldToMiniMap(@Nonnull Client client, int x, int y) { return worldToMiniMap(client, x, y, 6400); @@ -204,30 +208,52 @@ public class Perspective * @return a {@link Point} on screen corresponding to the position in * 3D-space */ + @Nullable public static Point worldToMiniMap(@Nonnull Client client, int x, int y, int distance) { - int angle = client.getMapAngle() & 0x7FF; - LocalPoint localLocation = client.getLocalPlayer().getLocalLocation(); - x = x / 32 - localLocation.getX() / 32; - y = y / 32 - localLocation.getY() / 32; + final int sceneX = x >>> LOCAL_COORD_BITS; + final int sceneY = y >>> LOCAL_COORD_BITS; + x = sceneX * 4 + 2 - localLocation.getX() / 32; + y = sceneY * 4 + 2 - localLocation.getY() / 32; int dist = x * x + y * y; if (dist < distance) { - int sin = SINE[angle]; - int cos = COSINE[angle]; + Widget minimapDrawWidget; + if (client.isResized()) + { + if (client.getVar(Varbits.SIDE_PANELS) == 1) + { + minimapDrawWidget = client.getWidget(WidgetInfo.RESIZABLE_MINIMAP_DRAW_AREA); + } + else + { + minimapDrawWidget = client.getWidget(WidgetInfo.RESIZABLE_MINIMAP_STONES_DRAW_AREA); + } + } + else + { + minimapDrawWidget = client.getWidget(WidgetInfo.FIXED_VIEWPORT_MINIMAP_DRAW_AREA); + } - int xx = y * sin + cos * x >> 16; - int yy = sin * x - y * cos >> 16; + if (minimapDrawWidget == null || minimapDrawWidget.isHidden()) + { + return null; + } - int miniMapX = client.isResized() - ? client.getCanvas().getWidth() - 167 - : Constants.GAME_FIXED_WIDTH - 208; + final int angle = client.getMapAngle() & 0x7FF; - x = (miniMapX + 167 / 2) + xx; - y = (167 / 2 - 1) + yy; - return new Point(x, y); + final int sin = SINE[angle]; + final int cos = COSINE[angle]; + + final int xx = y * sin + cos * x >> 16; + final int yy = sin * x - y * cos >> 16; + + Point loc = minimapDrawWidget.getCanvasLocation(); + int miniMapX = loc.getX() + xx + minimapDrawWidget.getWidth() / 2; + int miniMapY = minimapDrawWidget.getHeight() / 2 + loc.getY() + yy; + return new Point(miniMapX, miniMapY); } return null; diff --git a/runelite-api/src/main/java/net/runelite/api/widgets/WidgetID.java b/runelite-api/src/main/java/net/runelite/api/widgets/WidgetID.java index 81ae00f5c5..32ffcfa9ef 100644 --- a/runelite-api/src/main/java/net/runelite/api/widgets/WidgetID.java +++ b/runelite-api/src/main/java/net/runelite/api/widgets/WidgetID.java @@ -254,6 +254,8 @@ public class WidgetID static class FixedViewport { + static final int MINIMAP = 3; + static final int MINIMAP_DRAW_AREA = 8; static final int CLAN_CHAT_TAB = 31; static final int FRIENDS_TAB = 32; static final int IGNORES_TAB = 33; diff --git a/runelite-api/src/main/java/net/runelite/api/widgets/WidgetInfo.java b/runelite-api/src/main/java/net/runelite/api/widgets/WidgetInfo.java index 41169393eb..bdaf93d0cd 100644 --- a/runelite-api/src/main/java/net/runelite/api/widgets/WidgetInfo.java +++ b/runelite-api/src/main/java/net/runelite/api/widgets/WidgetInfo.java @@ -169,6 +169,8 @@ public enum WidgetInfo FIXED_VIEWPORT_OPTIONS_ICON(WidgetID.FIXED_VIEWPORT_GROUP_ID, WidgetID.FixedViewport.OPTIONS_ICON), FIXED_VIEWPORT_EMOTES_ICON(WidgetID.FIXED_VIEWPORT_GROUP_ID, WidgetID.FixedViewport.EMOTES_ICON), FIXED_VIEWPORT_MUSIC_ICON(WidgetID.FIXED_VIEWPORT_GROUP_ID, WidgetID.FixedViewport.MUSIC_ICON), + FIXED_VIEWPORT_MINIMAP(WidgetID.FIXED_VIEWPORT_GROUP_ID, WidgetID.FixedViewport.MINIMAP), + FIXED_VIEWPORT_MINIMAP_DRAW_AREA(WidgetID.FIXED_VIEWPORT_GROUP_ID, WidgetID.FixedViewport.MINIMAP_DRAW_AREA), RESIZABLE_MINIMAP_WIDGET(WidgetID.RESIZABLE_VIEWPORT_BOTTOM_LINE_GROUP_ID, WidgetID.Viewport.MINIMAP_RESIZABLE_WIDGET), RESIZABLE_MINIMAP_CLICKBOX(WidgetID.RESIZABLE_VIEWPORT_BOTTOM_LINE_GROUP_ID, WidgetID.Viewport.MINIMAP_RESIZABLE_CLICKBOX), diff --git a/runelite-mixins/src/main/java/net/runelite/mixins/RSClientMixin.java b/runelite-mixins/src/main/java/net/runelite/mixins/RSClientMixin.java index 9708ae1379..5ffd2acac9 100644 --- a/runelite-mixins/src/main/java/net/runelite/mixins/RSClientMixin.java +++ b/runelite-mixins/src/main/java/net/runelite/mixins/RSClientMixin.java @@ -1119,20 +1119,17 @@ public abstract class RSClientMixin implements RSClient for (Widget rlWidget : widgets) { RSWidget widget = (RSWidget) rlWidget; - if (widget == null) + if (widget == null || widget.getRSParentId() != parentId) { continue; } - if (widget.getRSParentId() == parentId) + if (parentId != -1) { - if (parentId != -1) - { - widget.setRenderParentId(parentId); - } - widget.setRenderX(x + widget.getRelativeX()); - widget.setRenderY(y + widget.getRelativeY()); + widget.setRenderParentId(parentId); } + widget.setRenderX(x + widget.getRelativeX()); + widget.setRenderY(y + widget.getRelativeY()); HashTable componentTable = client.getComponentTable(); WidgetNode childNode = componentTable.get(widget.getId()); diff --git a/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java b/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java index 3b197f10ed..4e4c9008f0 100644 --- a/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java +++ b/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java @@ -119,6 +119,13 @@ public abstract class RSWidgetMixin implements RSWidget return rsParentId; } + final int id = getId(); + if (TO_GROUP(id) == client.getWidgetRoot()) + { + // this is a root widget + return -1; + } + int parentId = rl$parentId; if (parentId != -1) { @@ -130,7 +137,7 @@ public abstract class RSWidgetMixin implements RSWidget // check the parent in the component table HashTable componentTable = client.getComponentTable(); WidgetNode widgetNode = componentTable.get(parentId); - if (widgetNode == null || widgetNode.getId() != TO_GROUP(getId())) + if (widgetNode == null || widgetNode.getId() != TO_GROUP(id)) { // invalidate parent rl$parentId = -1; @@ -191,6 +198,11 @@ public abstract class RSWidgetMixin implements RSWidget @Override public boolean isHidden() { + if (isSelfHidden()) + { + return true; + } + Widget parent = getParent(); if (parent == null) @@ -208,7 +220,7 @@ public abstract class RSWidgetMixin implements RSWidget return true; } - return isSelfHidden(); + return false; } @Inject