From 51814e143bfa2f254eb057daa28489180e42164a Mon Sep 17 00:00:00 2001 From: CrushedPixel Date: Sun, 19 Jul 2015 12:44:21 +0200 Subject: [PATCH] Created dummy GuiOverlayElement interface for ComposedElement to determine which Elements to draw last Added methods to retrieve position and size from a GuiElement Added draw() method with option to override hovered boolean to GuiElement interface and implemented it. This is required for GuiAdvancedButtons which would be tinted blue (as if hovered) even though an overlying GuiElement (e.g. GuiDropdown) was hovered --- .../gui/elements/ComposedElement.java | 45 +++++++++++++-- .../gui/elements/DelegatingElement.java | 25 +++++++++ .../gui/elements/GuiAdvancedButton.java | 56 ++++++++++++++++++- .../gui/elements/GuiAdvancedCheckBox.java | 25 +++++++++ .../gui/elements/GuiAdvancedTextField.java | 25 +++++++++ .../gui/elements/GuiArrowButton.java | 4 +- .../gui/elements/GuiColorPicker.java | 40 ++++++++++--- .../replaymod/gui/elements/GuiDropdown.java | 2 +- .../replaymod/gui/elements/GuiElement.java | 8 +++ .../gui/elements/GuiOverlayElement.java | 8 +++ .../replaymod/gui/elements/GuiScrollbar.java | 25 +++++++++ .../replaymod/gui/elements/GuiString.java | 25 +++++++++ .../replaymod/gui/elements/GuiTextArea.java | 25 +++++++++ .../gui/elements/GuiTexturedButton.java | 4 +- .../gui/elements/timelines/GuiTimeline.java | 26 +++++++++ .../gui/overlay/GuiReplayOverlay.java | 2 +- 16 files changed, 323 insertions(+), 22 deletions(-) create mode 100644 src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiOverlayElement.java diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/ComposedElement.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/ComposedElement.java index 4916eded..bf9188b3 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/ComposedElement.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/ComposedElement.java @@ -22,10 +22,25 @@ public class ComposedElement implements GuiElement { Collections.sort(parts, COMPOSED_ELEMENT_COMPARATOR); } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { - for (GuiElement part : parts) { - part.draw(mc, mouseX, mouseY); + GuiElement hovered = null; + + for (int i=parts.size()-1; i>=0; i--) { + GuiElement part = parts.get(i); + if(part.isHovering(mouseX, mouseY)) { + hovered = part; + break; + } + } + + for(GuiElement part : parts) { + part.draw(mc, mouseX, mouseY, hovered == part); } } @@ -96,11 +111,11 @@ public class ComposedElement implements GuiElement { @Override public int compare(GuiElement o1, GuiElement o2) { - Boolean d1 = o1 instanceof GuiDropdown; - Boolean d2 = o2 instanceof GuiDropdown; + Boolean d1 = o1 instanceof GuiOverlayElement; + Boolean d2 = o2 instanceof GuiOverlayElement; if(d1 && d2) { - return -new Integer(((GuiDropdown)o1).yPosition).compareTo(((GuiDropdown)o2).yPosition); + return -new Integer(o1.yPos()).compareTo(o2.yPos()); } return d1.compareTo(d2); @@ -111,4 +126,24 @@ public class ComposedElement implements GuiElement { return false; } } + + @Override + public int xPos() { + return 0; + } + + @Override + public int yPos() { + return 0; + } + + @Override + public int width() { + return 0; + } + + @Override + public int height() { + return 0; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/DelegatingElement.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/DelegatingElement.java index 48a30468..ec5f36f6 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/DelegatingElement.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/DelegatingElement.java @@ -17,6 +17,11 @@ public abstract class DelegatingElement implements GuiElement { public abstract GuiElement delegate(); + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + delegate().draw(mc, mouseX, mouseY, hovered); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { delegate().draw(mc, mouseX, mouseY); @@ -61,4 +66,24 @@ public abstract class DelegatingElement implements GuiElement { public void setElementEnabled(boolean enabled) { this.enabled = enabled; } + + @Override + public int xPos() { + return delegate().xPos(); + } + + @Override + public int yPos() { + return delegate().yPos(); + } + + @Override + public int width() { + return delegate().width(); + } + + @Override + public int height() { + return delegate().height(); + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedButton.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedButton.java index 2f7f910d..536d1238 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedButton.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedButton.java @@ -2,7 +2,9 @@ package eu.crushedpixel.replaymod.gui.elements; import eu.crushedpixel.replaymod.ReplayMod; import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.renderer.GlStateManager; import org.apache.commons.lang3.StringUtils; import java.awt.*; @@ -33,7 +35,35 @@ public class GuiAdvancedButton extends GuiButton implements GuiElement { @Override public void draw(Minecraft mc, int mouseX, int mouseY) { - drawButton(mc, mouseX, mouseY); + this.draw(mc, mouseX, mouseY, isHovering(mouseX, mouseY)); + } + + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovering) { + if (this.visible) { + FontRenderer fontrenderer = mc.fontRendererObj; + mc.getTextureManager().bindTexture(buttonTextures); + GlStateManager.color(1.0F, 1.0F, 1.0F, 1.0F); + this.hovered = isHovering(mouseX, mouseY); + int k = this.getHoverState(hovering); + GlStateManager.enableBlend(); + GlStateManager.tryBlendFuncSeparate(770, 771, 1, 0); + GlStateManager.blendFunc(770, 771); + this.drawTexturedModalRect(this.xPosition, this.yPosition, 0, 46 + k * 20, this.width / 2, this.height); + this.drawTexturedModalRect(this.xPosition + this.width / 2, this.yPosition, 200 - this.width / 2, 46 + k * 20, this.width / 2, this.height); + this.mouseDragged(mc, mouseX, mouseY); + int l = 14737632; + + if (packedFGColour != 0) { + l = packedFGColour; + } else if (!this.enabled) { + l = 10526880; + } else if (hovering) { + l = 16777120; + } + + this.drawCenteredString(fontrenderer, this.displayString, this.xPosition + this.width / 2, this.yPosition + (this.height - 8) / 2, l); + } } @Override @@ -48,8 +78,8 @@ public class GuiAdvancedButton extends GuiButton implements GuiElement { public boolean isHovering(int mouseX, int mouseY) { return mouseX >= xPosition && mouseY >= yPosition - && mouseX < xPosition + width - && mouseY < yPosition + height; + && mouseX <= xPosition + width + && mouseY <= yPosition + height; } @Override @@ -91,4 +121,24 @@ public class GuiAdvancedButton extends GuiButton implements GuiElement { action.run(); } } + + @Override + public int xPos() { + return xPosition; + } + + @Override + public int yPos() { + return yPosition; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return height; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedCheckBox.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedCheckBox.java index c256077f..d04038bc 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedCheckBox.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedCheckBox.java @@ -23,6 +23,11 @@ public class GuiAdvancedCheckBox extends GuiCheckBox implements GuiElement { this.listeners.add(listener); } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { drawButton(mc, mouseX, mouseY); @@ -84,4 +89,24 @@ public class GuiAdvancedCheckBox extends GuiCheckBox implements GuiElement { listener.onCheck(isChecked()); } } + + @Override + public int xPos() { + return xPosition; + } + + @Override + public int yPos() { + return yPosition; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return height; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedTextField.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedTextField.java index 9c96ec76..d1346079 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedTextField.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiAdvancedTextField.java @@ -46,6 +46,11 @@ public class GuiAdvancedTextField extends GuiTextField implements GuiElement { drawTextBox(); } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void drawTextBox() { if (text.isEmpty() && !isFocused() && !Strings.isNullOrEmpty(hint)) { @@ -112,4 +117,24 @@ public class GuiAdvancedTextField extends GuiTextField implements GuiElement { public boolean isFocused() { return isEnabled ? super.isFocused() : false; } + + @Override + public int xPos() { + return xPosition; + } + + @Override + public int yPos() { + return yPosition; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return height; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiArrowButton.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiArrowButton.java index 3c17eab0..5781cc62 100755 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiArrowButton.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiArrowButton.java @@ -21,9 +21,9 @@ public class GuiArrowButton extends GuiAdvancedButton { } @Override - public void drawButton(Minecraft mc, int mouseX, int mouseY) { + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovering) { try { - super.drawButton(mc, mouseX, mouseY); + super.draw(mc, mouseX, mouseY, hovering); if(dir == Direction.UP) { for(int i = 0; i <= Math.ceil(height / 2) - 5; i++) { drawHorizontalLine(xPosition + width - height + i + 4, xPosition + width - i - 6, yPosition + height - ((height / 3) + i + 2), Color.BLACK.getRGB()); diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiColorPicker.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiColorPicker.java index ce11ab94..f91fe558 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiColorPicker.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiColorPicker.java @@ -9,7 +9,7 @@ import org.lwjgl.util.Point; import java.awt.*; -public class GuiColorPicker extends GuiAdvancedButton { +public class GuiColorPicker extends GuiAdvancedButton implements GuiOverlayElement { private final int PICKER_SIZE = 100; @@ -25,12 +25,12 @@ public class GuiColorPicker extends GuiAdvancedButton { } @Override - public void drawButton(Minecraft mc, int mouseX, int mouseY) { + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovering) { if(this.visible) { FontRenderer fontrenderer = mc.fontRendererObj; mc.getTextureManager().bindTexture(buttonTextures); GlStateManager.color(1.0F, 1.0F, 1.0F, 1.0F); - this.hovered = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height; + this.hovered = isHovering(mouseX, mouseY) && !hoveringPicker(mouseX, mouseY); int k = this.getHoverState(this.hovered); GlStateManager.enableBlend(); GlStateManager.tryBlendFuncSeparate(770, 771, 1, 0); @@ -46,7 +46,7 @@ public class GuiColorPicker extends GuiAdvancedButton { else if (!this.enabled) { l = 10526880; } - else if (this.hovered) { + else if(this.hovered) { l = 16777120; } @@ -72,20 +72,25 @@ public class GuiColorPicker extends GuiAdvancedButton { @Override public boolean mousePressed(Minecraft mc, int mouseX, int mouseY) { + boolean click = false; if(pickerVisible && this.enabled) { if(MouseUtils.isMouseWithinBounds(pickerX, pickerY, PICKER_SIZE, PICKER_SIZE)) { Point mousePoint = MouseUtils.getMousePos(); setPickerColor(getColorAtPosition(mousePoint.getX() - pickerX, mousePoint.getY() - pickerY)); + click = true; } } - return super.mousePressed(mc, mouseX, mouseY); + return click; } @Override public boolean mouseClick(Minecraft mc, int mouseX, int mouseY, int button) { - boolean clicked = super.mouseClick(mc, mouseX, mouseY, button); - if(clicked) pickerToggled(); - return clicked; + if(super.mouseClick(mc, mouseX, mouseY, button)) { + if(!hoveringPicker(mouseX, mouseY)) pickerToggled(); + return true; + } + + return mousePressed(mc, mouseX, mouseY); } @Override @@ -116,4 +121,23 @@ public class GuiColorPicker extends GuiAdvancedButton { public int getPickedColor() { return pickedColor & 0xffffff; } + + @Override + public void setElementEnabled(boolean enabled) { + super.setElementEnabled(enabled); + if(!enabled) pickerVisible = false; + } + + @Override + public boolean isHovering(int mouseX, int mouseY) { + if(!pickerVisible) return super.isHovering(mouseX, mouseY); + return super.isHovering(mouseX, mouseY) || hoveringPicker(mouseX, mouseY); + } + + public boolean hoveringPicker(int mouseX, int mouseY) { + return mouseX >= pickerX + && mouseY >= pickerY + && mouseX <= pickerX+PICKER_SIZE + && mouseY <= pickerY+PICKER_SIZE; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiDropdown.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiDropdown.java index e20b1cfb..3bd553c2 100755 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiDropdown.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiDropdown.java @@ -14,7 +14,7 @@ import java.util.ArrayList; import java.util.HashMap; import java.util.List; -public class GuiDropdown extends GuiAdvancedTextField { +public class GuiDropdown extends GuiAdvancedTextField implements GuiOverlayElement { private final int visibleDropout; private final int dropoutElementHeight = 14; diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiElement.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiElement.java index 172757c7..5fb8b266 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiElement.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiElement.java @@ -5,10 +5,18 @@ import net.minecraft.client.Minecraft; public interface GuiElement { void draw(Minecraft mc, int mouseX, int mouseY); + + void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered); + void drawOverlay(Minecraft mc, int mouseX, int mouseY); boolean isHovering(int mouseX, int mouseY); + int xPos(); + int yPos(); + int width(); + int height(); + boolean mouseClick(Minecraft mc, int mouseX, int mouseY, int button); void mouseDrag(Minecraft mc, int mouseX, int mouseY, int button); void mouseRelease(Minecraft mc, int mouseX, int mouseY, int button); diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiOverlayElement.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiOverlayElement.java new file mode 100644 index 00000000..466c449b --- /dev/null +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiOverlayElement.java @@ -0,0 +1,8 @@ +package eu.crushedpixel.replaymod.gui.elements; + +/** + * A dummy interface which all GuiElements that should be drawn over + * other GuiElements should implement. + */ +public interface GuiOverlayElement { +} diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiScrollbar.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiScrollbar.java index 1a42da0a..5f7fd83e 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiScrollbar.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiScrollbar.java @@ -97,6 +97,11 @@ public class GuiScrollbar extends Gui implements GuiElement { } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { GlStateManager.resetColor(); @@ -181,4 +186,24 @@ public class GuiScrollbar extends Gui implements GuiElement { public void setElementEnabled(boolean enabled) { this.enabled = enabled; } + + @Override + public int xPos() { + return positionX; + } + + @Override + public int yPos() { + return positionY; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return SLIDER_HEIGHT; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiString.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiString.java index 141b5a88..f214b615 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiString.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiString.java @@ -28,6 +28,11 @@ public class GuiString extends Gui implements GuiElement { this.getContent = getContent; } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { String text; @@ -87,4 +92,24 @@ public class GuiString extends Gui implements GuiElement { return 0; } } + + @Override + public int xPos() { + return positionX; + } + + @Override + public int yPos() { + return positionY; + } + + @Override + public int width() { + return getWidth(); + } + + @Override + public int height() { + return Minecraft.getMinecraft().fontRendererObj.FONT_HEIGHT; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTextArea.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTextArea.java index d902974a..ad427edb 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTextArea.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTextArea.java @@ -374,6 +374,11 @@ public class GuiTextArea extends Gui implements GuiElement { return isFocused || alwaysFocused; } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { // Draw black rect once pixel smaller than gray rect @@ -634,4 +639,24 @@ public class GuiTextArea extends Gui implements GuiElement { this.width = width; updateCurrentXOffset(); } + + @Override + public int xPos() { + return positionX; + } + + @Override + public int yPos() { + return positionY; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return height; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTexturedButton.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTexturedButton.java index 293fd7de..03b5e875 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTexturedButton.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/GuiTexturedButton.java @@ -23,7 +23,7 @@ public class GuiTexturedButton extends GuiAdvancedButton implements GuiElement { } @Override - public void drawButton(Minecraft mc, int mouseX, int mouseY) { + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovering) { if (visible) { hovered = isHovering(mouseX, mouseY) && enabled; @@ -35,7 +35,7 @@ public class GuiTexturedButton extends GuiAdvancedButton implements GuiElement { mc.renderEngine.bindTexture(texture); - int u = this.u + (hovered ? width : 0); + int u = this.u + (hovering ? width : 0); Gui.drawModalRectWithCustomSizedTexture(xPosition, yPosition, u, v, width, height, textureWidth, textureHeight); } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/elements/timelines/GuiTimeline.java b/src/main/java/eu/crushedpixel/replaymod/gui/elements/timelines/GuiTimeline.java index 9c8f0604..1396f519 100644 --- a/src/main/java/eu/crushedpixel/replaymod/gui/elements/timelines/GuiTimeline.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/elements/timelines/GuiTimeline.java @@ -87,6 +87,12 @@ public class GuiTimeline extends Gui implements GuiElement { } } + @Override + public void draw(Minecraft mc, int mouseX, int mouseY, boolean hovered) { + draw(mc, mouseX, mouseY); + } + + @Override public void draw(Minecraft mc, int mouseX, int mouseY) { int bodyLeft = positionX + BORDER_LEFT; int bodyRight = positionX + width - BORDER_RIGHT; @@ -291,4 +297,24 @@ public class GuiTimeline extends Gui implements GuiElement { public void setElementEnabled(boolean enabled) { this.enabled = enabled; } + + @Override + public int xPos() { + return positionX; + } + + @Override + public int yPos() { + return positionY; + } + + @Override + public int width() { + return width; + } + + @Override + public int height() { + return height; + } } diff --git a/src/main/java/eu/crushedpixel/replaymod/gui/overlay/GuiReplayOverlay.java b/src/main/java/eu/crushedpixel/replaymod/gui/overlay/GuiReplayOverlay.java index bfb5bcc1..89541779 100755 --- a/src/main/java/eu/crushedpixel/replaymod/gui/overlay/GuiReplayOverlay.java +++ b/src/main/java/eu/crushedpixel/replaymod/gui/overlay/GuiReplayOverlay.java @@ -256,7 +256,7 @@ public class GuiReplayOverlay extends Gui { } }; - private final GuiReplaySpeedSlider speedSlider = new GuiReplaySpeedSlider(1, SPEED_X, TOP_ROW, I18n.format("replaymod.gui.speed")); + private final GuiReplaySpeedSlider speedSlider = new GuiReplaySpeedSlider(SPEED_X, TOP_ROW, I18n.format("replaymod.gui.speed")); private boolean toolbarOpen = false;