aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--loader/src/main/java/kr/syeyoung/dungeonsguide/launcher/gui/tooltip/NotificationManager.java3
-rwxr-xr-xmod/src/main/java/kr/syeyoung/dungeonsguide/mod/DungeonsGuide.java2
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/chat/ChatTransmitter.java2
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/commands/CommandDgDebug.java5
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/GuiFeature.java79
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/impl/secret/mechanicbrowser/FeatureMechanicBrowse.java4
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/DomElement.java7
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/AspectRatioFitter.java5
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/Flexible.java5
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/SizedBox.java5
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/layouter/Layouter.java4
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManager.java260
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManagerRootWidget.java77
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayType.java23
-rw-r--r--mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayWidget.java84
15 files changed, 538 insertions, 27 deletions
diff --git a/loader/src/main/java/kr/syeyoung/dungeonsguide/launcher/gui/tooltip/NotificationManager.java b/loader/src/main/java/kr/syeyoung/dungeonsguide/launcher/gui/tooltip/NotificationManager.java
index 53f9e1f9..e458383a 100644
--- a/loader/src/main/java/kr/syeyoung/dungeonsguide/launcher/gui/tooltip/NotificationManager.java
+++ b/loader/src/main/java/kr/syeyoung/dungeonsguide/launcher/gui/tooltip/NotificationManager.java
@@ -51,6 +51,9 @@ public class NotificationManager {
@SubscribeEvent
public void onRender(RenderGameOverlayEvent.Post postRender) {
+ if (!(postRender.type == RenderGameOverlayEvent.ElementType.EXPERIENCE || postRender.type == RenderGameOverlayEvent.ElementType.JUMPBAR))
+ return;
+
ScaledResolution sr = new ScaledResolution(Minecraft.getMinecraft());
FontRenderer fr = Minecraft.getMinecraft().fontRendererObj;
int widthX = fr.getStringWidth("X");
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/DungeonsGuide.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/DungeonsGuide.java
index cfb85aa9..ad27c7c2 100755
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/DungeonsGuide.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/DungeonsGuide.java
@@ -35,6 +35,7 @@ import kr.syeyoung.dungeonsguide.mod.events.annotations.EventHandlerRegistry;
import kr.syeyoung.dungeonsguide.mod.events.listener.DungeonListener;
import kr.syeyoung.dungeonsguide.mod.events.listener.PacketListener;
import kr.syeyoung.dungeonsguide.mod.features.FeatureRegistry;
+import kr.syeyoung.dungeonsguide.mod.overlay.OverlayManager;
import kr.syeyoung.dungeonsguide.mod.party.PartyManager;
import kr.syeyoung.dungeonsguide.mod.resources.DGTexturePack;
import kr.syeyoung.dungeonsguide.mod.stomp.StompManager;
@@ -230,6 +231,7 @@ public class DungeonsGuide implements DGInterface {
registerEventsForge(PartyManager.INSTANCE);
registerEventsForge(ChatProcessor.INSTANCE);
registerEventsForge(StaticResourceCache.INSTANCE);
+ registerEventsForge(OverlayManager.getEventHandler());
registerEventsForge(new AhUtils());
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/chat/ChatTransmitter.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/chat/ChatTransmitter.java
index 9658616a..69518af8 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/chat/ChatTransmitter.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/chat/ChatTransmitter.java
@@ -78,8 +78,6 @@ public class ChatTransmitter {
Minecraft.getMinecraft().thePlayer.addChatMessage(event.message);
}
}
-
-
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/commands/CommandDgDebug.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/commands/CommandDgDebug.java
index c3c8f581..e6affd66 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/commands/CommandDgDebug.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/commands/CommandDgDebug.java
@@ -102,11 +102,6 @@ public class CommandDgDebug extends CommandBase {
ScoreBoardUtils.forEachLineClean(l -> {
ChatTransmitter.addToQueue("LINE: " + l, false);
});
- } else if ("title".equals(arg)) {
- if (args.length == 2) {
- System.out.println("Displayuing title:" + args[1]);
- TitleRender.displayTitle(args[1], "", 10, 40, 20);
- }
} else if ("mockdungeonstart".equals(arg)) {
if (!Minecraft.getMinecraft().isSingleplayer()) {
ChatTransmitter.addToQueue("This only works in singlepauer", false);
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/GuiFeature.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/GuiFeature.java
index 79112aca..f6fdc880 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/GuiFeature.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/GuiFeature.java
@@ -29,6 +29,17 @@ import kr.syeyoung.dungeonsguide.mod.gui.elements.MButton;
import kr.syeyoung.dungeonsguide.mod.gui.elements.MLabel;
import kr.syeyoung.dungeonsguide.mod.gui.elements.MPassiveLabelAndElement;
import kr.syeyoung.dungeonsguide.mod.gui.elements.MToggleButton;
+import kr.syeyoung.dungeonsguide.mod.guiv2.DomElement;
+import kr.syeyoung.dungeonsguide.mod.guiv2.Widget;
+import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.Layouter;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.ConstraintBox;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Rect;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Size;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.Renderer;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.RenderingContext;
+import kr.syeyoung.dungeonsguide.mod.overlay.OverlayManager;
+import kr.syeyoung.dungeonsguide.mod.overlay.OverlayType;
+import kr.syeyoung.dungeonsguide.mod.overlay.OverlayWidget;
import lombok.AccessLevel;
import lombok.Getter;
import lombok.Setter;
@@ -43,12 +54,25 @@ import org.lwjgl.opengl.GL14;
import java.awt.*;
import java.util.ArrayList;
+import java.util.Collections;
import java.util.List;
@Getter
public abstract class GuiFeature extends AbstractFeature {
- @Setter
private GUIRectangle featureRect;
+
+ public void setFeatureRect(GUIRectangle featureRect) {
+ this.featureRect = featureRect;
+
+ Rectangle loc = featureRect.getRectangleNoScale();
+ widget = new OverlayWidget(
+ new WidgetFeatureWrapper(),
+ OverlayType.UNDER_CHAT,
+ new Rect(loc.x, loc.y, loc.width, loc.height)
+ );
+ OverlayManager.getInstance().updateOverlayPosition(widget);
+ }
+
@Setter(value = AccessLevel.PROTECTED)
private boolean keepRatio;
@Setter(value = AccessLevel.PROTECTED)
@@ -57,6 +81,8 @@ public abstract class GuiFeature extends AbstractFeature {
private double defaultHeight;
private final double defaultRatio;
+ private OverlayWidget widget;
+
protected GuiFeature(String category, String name, String description, String key, boolean keepRatio, int width, int height) {
super(category, name, description, key);
this.keepRatio = keepRatio;
@@ -64,30 +90,39 @@ public abstract class GuiFeature extends AbstractFeature {
this.defaultHeight = height;
this.defaultRatio = defaultWidth / defaultHeight;
this.featureRect = new GUIRectangle(0, 0, width, height);
+
+ Rectangle loc = featureRect.getRectangleNoScale();
+ widget = new OverlayWidget(
+ new WidgetFeatureWrapper(),
+ OverlayType.UNDER_CHAT,
+ new Rect(loc.x, loc.y, loc.width, loc.height)
+ );
+ OverlayManager.getInstance().addOverlay(widget);
}
- @DGEventHandler
- public void drawScreen(RenderGameOverlayEvent.Post postRender) {
- if (!(postRender.type == RenderGameOverlayEvent.ElementType.EXPERIENCE || postRender.type == RenderGameOverlayEvent.ElementType.JUMPBAR)) return;
+ public class WidgetFeatureWrapper extends Widget implements Renderer, Layouter {
+ @Override
+ public List<Widget> build(DomElement buildContext) {
+ return Collections.emptyList();
+ }
+
+ @Override
+ public void doRender(int absMouseX, int absMouseY, double relMouseX, double relMouseY, float partialTicks, RenderingContext context, DomElement buildContext) {
+ drawScreen(partialTicks);
+ }
+
+ @Override
+ public Size layout(DomElement buildContext, ConstraintBox constraintBox) {
+ return new Size(constraintBox.getMaxWidth(), constraintBox.getMaxHeight());
+ }
+ }
- GlStateManager.pushMatrix();
+ public void drawScreen(float partialTicks) {
Rectangle featureRect = this.featureRect.getRectangleNoScale();
- ScaledResolution scaledResolution = new ScaledResolution(Minecraft.getMinecraft());
- GlStateManager.scale(1.0/scaledResolution.getScaleFactor(), 1.0/scaledResolution.getScaleFactor(), 1);
clip(featureRect.x, featureRect.y, featureRect.width, featureRect.height);
GL11.glEnable(GL11.GL_SCISSOR_TEST);
-
- GlStateManager.translate(featureRect.x, featureRect.y, 0);
- drawHUD(postRender.partialTicks);
-
+ drawHUD(partialTicks);
GL11.glDisable(GL11.GL_SCISSOR_TEST);
- GlStateManager.popMatrix();
-
-
- GlStateManager.enableBlend();
- GlStateManager.color(1,1,1,1);
- GL14.glBlendFuncSeparate(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA, GL11.GL_ONE, GL11.GL_ONE_MINUS_SRC_ALPHA);
- GlStateManager.tryBlendFuncSeparate(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA, GL11.GL_ONE, GL11.GL_ONE_MINUS_SRC_ALPHA);
}
@@ -112,6 +147,14 @@ public abstract class GuiFeature extends AbstractFeature {
public void loadConfig(JsonObject jsonObject) {
super.loadConfig(jsonObject);
this.featureRect = TypeConverterRegistry.getTypeConverter("guirect",GUIRectangle.class).deserialize(jsonObject.get("$bounds"));
+
+ Rectangle loc = featureRect.getRectangleNoScale();
+ widget = new OverlayWidget(
+ new WidgetFeatureWrapper(),
+ OverlayType.UNDER_CHAT,
+ new Rect(loc.x, loc.y, loc.width, loc.height)
+ );
+ OverlayManager.getInstance().updateOverlayPosition(widget);
}
@Override
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/impl/secret/mechanicbrowser/FeatureMechanicBrowse.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/impl/secret/mechanicbrowser/FeatureMechanicBrowse.java
index fb279ea9..48e515bb 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/impl/secret/mechanicbrowser/FeatureMechanicBrowse.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/features/impl/secret/mechanicbrowser/FeatureMechanicBrowse.java
@@ -89,13 +89,13 @@ public class FeatureMechanicBrowse extends GuiFeature {
private int lastWidth, lastHeight;
@Override
- public void drawScreen(RenderGameOverlayEvent.Post post) {
+ public void drawScreen(float partialTicks) {
int i = Mouse.getEventX();
int j = Minecraft.getMinecraft().displayHeight - Mouse.getEventY();
if (Minecraft.getMinecraft().displayWidth != lastWidth || Minecraft.getMinecraft().displayHeight != lastHeight) mGuiMechanicBrowser.initGui();
lastWidth = Minecraft.getMinecraft().displayWidth; lastHeight = Minecraft.getMinecraft().displayHeight;
- mGuiMechanicBrowser.drawScreen(i,j,post.partialTicks);
+ mGuiMechanicBrowser.drawScreen(i,j,partialTicks);
}
@Override
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/DomElement.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/DomElement.java
index 44c538d6..b3e4b0cf 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/DomElement.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/DomElement.java
@@ -21,6 +21,7 @@ package kr.syeyoung.dungeonsguide.mod.guiv2;
import kr.syeyoung.dungeonsguide.mod.guiv2.elements.Stack;
import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.Layouter;
import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.NullLayouter;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.ConstraintBox;
import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Position;
import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Rect;
import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Size;
@@ -100,6 +101,12 @@ public class DomElement {
// event propagation
public void requestRelayout() {
+ if (layouter.canCutRequest()) {
+ layouter.layout(this, new ConstraintBox(
+ size.getWidth(), size.getWidth(), size.getHeight(), size.getHeight()
+ ));
+ return;
+ }
if (parent != null)
parent.requestRelayout();
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/AspectRatioFitter.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/AspectRatioFitter.java
index 0e6f9ed9..6984bf32 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/AspectRatioFitter.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/AspectRatioFitter.java
@@ -81,6 +81,11 @@ public class AspectRatioFitter extends AnnotatedExportOnlyWidget implements Layo
}
@Override
+ public boolean canCutRequest() {
+ return Flexible.FlexFit.TIGHT == fit.getValue();
+ }
+
+ @Override
public List<Widget> build(DomElement buildContext) {
return Collections.singletonList(widget.getValue());
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/Flexible.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/Flexible.java
index b799cb3b..5585395a 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/Flexible.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/Flexible.java
@@ -74,4 +74,9 @@ public class Flexible extends AnnotatedExportOnlyWidget implements Layouter {
getDomElement().getChildren().get(0).setRelativeBound(new Rect(0,0, dim.getWidth(),dim.getHeight()));
return dim;
}
+
+ @Override
+ public boolean canCutRequest() {
+ return Flexible.FlexFit.TIGHT == fit.getValue();
+ }
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/SizedBox.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/SizedBox.java
index 37a277a5..123cf53c 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/SizedBox.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/elements/SizedBox.java
@@ -69,4 +69,9 @@ public class SizedBox extends AnnotatedExportOnlyWidget implements Layouter {
child.setRelativeBound(new Rect(0,0,dim.getWidth(),dim.getHeight()));
return dim;
}
+
+ @Override
+ public boolean canCutRequest() {
+ return true;
+ }
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/layouter/Layouter.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/layouter/Layouter.java
index 5330e222..6afcf07b 100644
--- a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/layouter/Layouter.java
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/guiv2/layouter/Layouter.java
@@ -29,4 +29,8 @@ public interface Layouter {
if (val > max) return max;
return val;
}
+
+ default boolean canCutRequest() {
+ return false;
+ }
}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManager.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManager.java
new file mode 100644
index 00000000..30fcd96a
--- /dev/null
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManager.java
@@ -0,0 +1,260 @@
+/*
+ * Dungeons Guide - The most intelligent Hypixel Skyblock Dungeons Mod
+ * Copyright (C) 2023 cyoung06 (syeyoung)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published
+ * by the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+package kr.syeyoung.dungeonsguide.mod.overlay;
+
+import kr.syeyoung.dungeonsguide.mod.guiv2.RootDom;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.ConstraintBox;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Rect;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Size;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.RenderingContext;
+import kr.syeyoung.dungeonsguide.mod.utils.cursor.EnumCursor;
+import kr.syeyoung.dungeonsguide.mod.utils.cursor.GLCursors;
+import lombok.Getter;
+import net.minecraft.client.Minecraft;
+import net.minecraft.client.gui.GuiChat;
+import net.minecraft.client.gui.ScaledResolution;
+import net.minecraft.client.renderer.GlStateManager;
+import net.minecraftforge.client.event.GuiScreenEvent;
+import net.minecraftforge.client.event.RenderGameOverlayEvent;
+import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
+import org.lwjgl.input.Keyboard;
+import org.lwjgl.input.Mouse;
+import org.lwjgl.opengl.GL11;
+
+import java.io.IOException;
+
+import static org.lwjgl.opengl.GL11.GL_GREATER;
+
+public class OverlayManager {
+ private final RootDom view;
+ private final Minecraft mc;
+
+ private static final OverlayManager INSTANCE = new OverlayManager();
+ @Getter
+ private final OverlayManagerRootWidget root = new OverlayManagerRootWidget();
+
+
+ public static OverlayManager getEventHandler() {
+ return INSTANCE;
+ }
+
+ public static OverlayManagerRootWidget getInstance() {
+ return getEventHandler().root;
+ }
+
+ public static final String OVERLAY_TYPE_KEY = "OVERLAY_TYPE";
+
+ private OverlayManager() {
+ this.mc = Minecraft.getMinecraft();
+ view = new RootDom(root);
+
+ view.setRelativeBound(new Rect(0,0, Minecraft.getMinecraft().displayWidth, Minecraft.getMinecraft().displayHeight));
+ view.setAbsBounds(new Rect(0,0, Minecraft.getMinecraft().displayWidth, Minecraft.getMinecraft().displayHeight));
+ view.setSize(new Size(Minecraft.getMinecraft().displayWidth, Minecraft.getMinecraft().displayHeight));
+ view.getLayouter().layout(view, new ConstraintBox(
+ Minecraft.getMinecraft().displayWidth,
+ Minecraft.getMinecraft().displayWidth,
+ Minecraft.getMinecraft().displayHeight,
+ Minecraft.getMinecraft().displayHeight
+ ));
+ view.setMounted(true);
+ }
+
+ @SubscribeEvent
+ public void renderOverlay(RenderGameOverlayEvent.Post postRender) {
+ if (!(postRender.type == RenderGameOverlayEvent.ElementType.EXPERIENCE || postRender.type == RenderGameOverlayEvent.ElementType.JUMPBAR))
+ return;
+ System.out.println("overlay");
+ view.getContext().CONTEXT.put(OVERLAY_TYPE_KEY, OverlayType.UNDER_CHAT);
+ drawScreen(postRender.partialTicks);
+ }
+
+ @SubscribeEvent
+ public void renderGui(GuiScreenEvent.DrawScreenEvent.Post postRender) {
+ System.out.println("gui: "+postRender.gui);
+ if (postRender.gui instanceof GuiChat)
+ view.getContext().CONTEXT.put(OVERLAY_TYPE_KEY, OverlayType.OVER_CHAT);
+ else
+ view.getContext().CONTEXT.put(OVERLAY_TYPE_KEY, OverlayType.OVER_ANY);
+ drawScreen(postRender.renderPartialTicks);
+ }
+
+
+ private void drawScreen( float partialTicks) {
+ int i = Mouse.getEventX();
+ int j = this.mc.displayHeight - Mouse.getEventY();
+
+ ScaledResolution scaledResolution = new ScaledResolution(Minecraft.getMinecraft());
+ GlStateManager.pushMatrix();
+ GlStateManager.disableDepth();
+ GlStateManager.enableBlend();
+ GlStateManager.enableAlpha();
+ GlStateManager.alphaFunc(GL_GREATER, 0);
+ GlStateManager.tryBlendFuncSeparate(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA, 1, 0);
+ GlStateManager.color(1, 1, 1, 1);
+ GlStateManager.scale(1.0 / scaledResolution.getScaleFactor(), 1.0 / scaledResolution.getScaleFactor(), 1.0d);
+ view.getRenderer().doRender(i, j, i, j, partialTicks, new RenderingContext(), view);
+ GlStateManager.alphaFunc(GL_GREATER, 0.1f);
+ GlStateManager.popMatrix();
+ GlStateManager.enableDepth();
+ GlStateManager.disableTexture2D();
+ GL11.glDisable(GL11.GL_SCISSOR_TEST);
+ }
+
+ private void keyTyped(char typedChar, int keyCode) throws IOException {
+ try {
+ view.keyPressed0(typedChar, keyCode);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+ private void keyHeld(int keyCode, char typedChar) throws IOException {
+ try {
+ view.keyHeld0(typedChar, keyCode);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+ private void keyReleased(int keyCode, char typedChar) throws IOException {
+ try {
+ view.keyReleased0(typedChar, keyCode);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+ private boolean mouseClicked(int mouseX, int mouseY, int mouseButton) throws IOException {
+ try {
+ return view.mouseClicked0(mouseX, mouseY
+ , mouseX, mouseY, mouseButton);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ return false;
+ }
+
+ private void mouseReleased(int mouseX, int mouseY, int state) {
+ try {
+ view.mouseReleased0(mouseX, mouseY
+ , mouseX, mouseY, state);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+ private void mouseClickMove(int mouseX, int mouseY, int clickedMouseButton, long timeSinceLastClick) {
+ try {
+ view.mouseClickMove0(mouseX, mouseY
+ , mouseX, mouseY, clickedMouseButton, timeSinceLastClick);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+ private void mouseMove(int mouseX, int mouseY) {
+ try {
+ view.mouseMoved0(mouseX, mouseY
+ , mouseX, mouseY);
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+
+ private int touchValue;
+ private int eventButton;
+ private long lastMouseEvent;
+
+
+ private int lastX, lastY;
+
+
+ @SubscribeEvent
+ public void handleMouseInput(GuiScreenEvent.MouseInputEvent.Pre mouseInputEvent) throws IOException {
+ try {
+ int i = Mouse.getEventX();
+ int j = this.mc.displayHeight - Mouse.getEventY();
+ int k = Mouse.getEventButton();
+
+ if (Mouse.getEventButtonState()) {
+ if (this.mc.gameSettings.touchscreen && this.touchValue++ > 0) {
+ return;
+ }
+
+ this.eventButton = k;
+ this.lastMouseEvent = Minecraft.getSystemTime();
+ if (this.mouseClicked(i, j, this.eventButton))
+ mouseInputEvent.setCanceled(true);
+ } else if (k != -1) {
+ if (this.mc.gameSettings.touchscreen && --this.touchValue > 0) {
+ return;
+ }
+
+ this.eventButton = -1;
+ this.mouseReleased(i, j, k);
+ } else if (this.eventButton != -1 && this.lastMouseEvent > 0L) {
+ long l = Minecraft.getSystemTime() - this.lastMouseEvent;
+ this.mouseClickMove(i, j, this.eventButton, l);
+ }
+ if (lastX != i || lastY != j) {
+ try {
+ EnumCursor prevCursor = view.getCurrentCursor();
+ view.setCursor(EnumCursor.DEFAULT);
+ this.mouseMove(i, j);
+ EnumCursor newCursor = view.getCurrentCursor();
+ if (prevCursor != newCursor) Mouse.setNativeCursor(GLCursors.getCursor(newCursor));
+ } catch (Throwable e) {
+ if (e.getMessage() == null || !e.getMessage().contains("hack to stop"))
+ e.printStackTrace();
+ }
+ }
+
+
+ int wheel = Mouse.getEventDWheel();
+ if (wheel != 0) {
+ view.mouseScrolled0(i, j, i, j, wheel);
+ }
+ lastX = i;
+ lastY = j;
+ } catch (Throwable e) {
+ e.printStackTrace();
+ }
+ }
+
+ @SubscribeEvent
+ public void handleKeyboardInput(GuiScreenEvent.KeyboardInputEvent.Pre keyboardInputEvent) throws IOException {
+ if (Keyboard.getEventKeyState()) {
+ if (Keyboard.isRepeatEvent())
+ this.keyHeld(Keyboard.getEventKey(), Keyboard.getEventCharacter());
+ else
+ this.keyTyped(Keyboard.getEventCharacter(), Keyboard.getEventKey());
+ } else {
+ this.keyReleased(Keyboard.getEventKey(), Keyboard.getEventCharacter());
+ }
+ }
+}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManagerRootWidget.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManagerRootWidget.java
new file mode 100644
index 00000000..807472df
--- /dev/null
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayManagerRootWidget.java
@@ -0,0 +1,77 @@
+/*
+ * Dungeons Guide - The most intelligent Hypixel Skyblock Dungeons Mod
+ * Copyright (C) 2023 cyoung06 (syeyoung)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published
+ * by the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+package kr.syeyoung.dungeonsguide.mod.overlay;
+
+import kr.syeyoung.dungeonsguide.mod.guiv2.DomElement;
+import kr.syeyoung.dungeonsguide.mod.guiv2.Widget;
+import kr.syeyoung.dungeonsguide.mod.guiv2.elements.Scaler;
+import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.Layouter;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.ConstraintBox;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Rect;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Size;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.OnlyChildrenRenderer;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.Renderer;
+
+import java.util.Collections;
+import java.util.List;
+
+public class OverlayManagerRootWidget extends Widget implements Layouter {
+ @Override
+ public List<Widget> build(DomElement buildContext) {
+ return Collections.emptyList();
+ }
+
+ public void addOverlay(OverlayWidget overlayWidget) {
+ DomElement domElement = overlayWidget.createDomElement(getDomElement());
+ getDomElement().addElement(domElement);
+
+ Rect posSize = overlayWidget.positionSize;
+ Size size = domElement.getLayouter().layout(domElement, new ConstraintBox(posSize.getWidth(), posSize.getWidth(), posSize.getHeight(), posSize.getHeight()));
+ domElement.setRelativeBound(new Rect(posSize.getX(), posSize.getY(), size.getWidth(), size.getHeight()));
+ }
+
+ public void removeOverlay(OverlayWidget widget) {
+ getDomElement().removeElement(widget.getDomElement());
+ }
+
+ public void updateOverlayPosition(OverlayWidget overlayWidget) {
+ DomElement domElement = overlayWidget.getDomElement();
+ Rect posSize = overlayWidget.positionSize;
+ Size size = domElement.getLayouter().layout(domElement, new ConstraintBox(posSize.getWidth(), posSize.getWidth(), posSize.getHeight(), posSize.getHeight()));
+ domElement.setRelativeBound(new Rect(posSize.getX(), posSize.getY(), size.getWidth(), size.getHeight()));
+ }
+
+ @Override
+ public Size layout(DomElement buildContext, ConstraintBox constraintBox) {
+ for (DomElement child : buildContext.getChildren()) {
+ if (!(child.getWidget() instanceof OverlayWidget)) continue;
+
+ Rect posSize = ((OverlayWidget) child.getWidget()).positionSize;
+ Size size = child.getLayouter().layout(child, new ConstraintBox(posSize.getWidth(), posSize.getWidth(), posSize.getHeight(), posSize.getHeight()));
+ child.setRelativeBound(new Rect(posSize.getX(), posSize.getY(), size.getWidth(), size.getHeight()));
+ }
+
+ return new Size(constraintBox.getMaxWidth(), constraintBox.getMaxHeight());
+ }
+
+ @Override
+ protected Renderer createRenderer() {
+ return OnlyChildrenRenderer.INSTANCE;
+ }
+}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayType.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayType.java
new file mode 100644
index 00000000..875c4b70
--- /dev/null
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayType.java
@@ -0,0 +1,23 @@
+/*
+ * Dungeons Guide - The most intelligent Hypixel Skyblock Dungeons Mod
+ * Copyright (C) 2023 cyoung06 (syeyoung)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published
+ * by the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+package kr.syeyoung.dungeonsguide.mod.overlay;
+
+public enum OverlayType {
+ UNDER_CHAT, OVER_CHAT, OVER_ANY
+}
diff --git a/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayWidget.java b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayWidget.java
new file mode 100644
index 00000000..aef258ca
--- /dev/null
+++ b/mod/src/main/java/kr/syeyoung/dungeonsguide/mod/overlay/OverlayWidget.java
@@ -0,0 +1,84 @@
+/*
+ * Dungeons Guide - The most intelligent Hypixel Skyblock Dungeons Mod
+ * Copyright (C) 2023 cyoung06 (syeyoung)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published
+ * by the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ */
+
+package kr.syeyoung.dungeonsguide.mod.overlay;
+
+import kr.syeyoung.dungeonsguide.mod.guiv2.DomElement;
+import kr.syeyoung.dungeonsguide.mod.guiv2.Widget;
+import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.Layouter;
+import kr.syeyoung.dungeonsguide.mod.guiv2.layouter.SingleChildPassingLayouter;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.ConstraintBox;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Rect;
+import kr.syeyoung.dungeonsguide.mod.guiv2.primitive.Size;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.Renderer;
+import kr.syeyoung.dungeonsguide.mod.guiv2.renderer.RenderingContext;
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+import net.minecraft.client.renderer.GlStateManager;
+
+import java.util.Collections;
+import java.util.List;
+
+@AllArgsConstructor
+public class OverlayWidget extends Widget implements Renderer, Layouter {
+ public Widget wrappingWidget;
+ public OverlayType overlayType;
+ public Rect positionSize;
+
+ @Override
+ public List<Widget> build(DomElement buildContext) {
+ return Collections.singletonList(wrappingWidget);
+ }
+
+ @Override
+ public void doRender(int absMouseX, int absMouseY, double relMouseX, double relMouseY, float partialTicks, RenderingContext context, DomElement buildContext) {
+ if (buildContext.getChildren().isEmpty()) return;
+ OverlayType type = buildContext.getContext().getValue(OverlayType.class, OverlayManager.OVERLAY_TYPE_KEY);
+ if (this.overlayType.ordinal() < type.ordinal()) return;
+
+ DomElement value = buildContext.getChildren().get(0);
+
+ Rect original = value.getRelativeBound();
+ GlStateManager.translate(original.getX(), original.getY(), 0);
+
+ double absXScale = buildContext.getAbsBounds().getWidth() / buildContext.getSize().getWidth();
+ double absYScale = buildContext.getAbsBounds().getHeight() / buildContext.getSize().getHeight();
+
+ Rect elementABSBound = new Rect(
+ (buildContext.getAbsBounds().getX() + original.getX() * absXScale),
+ (buildContext.getAbsBounds().getY() + original.getY() * absYScale),
+ (original.getWidth() * absXScale),
+ (original.getHeight() * absYScale)
+ );
+ value.setAbsBounds(elementABSBound);
+
+ value.getRenderer().doRender(absMouseX, absMouseY,
+ relMouseX - original.getX(),
+ relMouseY - original.getY(), partialTicks, context, value);
+ }
+
+ @Override
+ public Size layout(DomElement buildContext, ConstraintBox constraintBox) {
+ return SingleChildPassingLayouter.INSTANCE.layout(buildContext, constraintBox);
+ }
+
+ @Override
+ public boolean canCutRequest() {
+ return true;
+ }
+}