From 3b18d099fbc4758cc69f99a8dc046822395e6aa4 Mon Sep 17 00:00:00 2001 From: Juuxel Date: Tue, 27 Aug 2019 20:59:17 +0300 Subject: Add focusing and support for background painters --- .../cotton/gui/client/modmenu/ConfigGui.java | 2 +- .../github/cottonmc/cotton/gui/widget/WSlider.java | 88 +++++++++++++++------- 2 files changed, 62 insertions(+), 28 deletions(-) (limited to 'src/main/java/io') diff --git a/src/main/java/io/github/cottonmc/cotton/gui/client/modmenu/ConfigGui.java b/src/main/java/io/github/cottonmc/cotton/gui/client/modmenu/ConfigGui.java index 61d5d36..1b5bf42 100644 --- a/src/main/java/io/github/cottonmc/cotton/gui/client/modmenu/ConfigGui.java +++ b/src/main/java/io/github/cottonmc/cotton/gui/client/modmenu/ConfigGui.java @@ -27,7 +27,7 @@ public class ConfigGui extends LightweightGuiDescription { WTextField testField = new WTextField(); testField.setSuggestion("test"); root.add(testField, 0, 3, 4, 1); - root.add(new WSlider(50, 100, Axis.VERTICAL).setValueChangeListener(System.out::println), 0, 4, 1, 4); + root.add(new WSlider(50, 100, Axis.VERTICAL).setValueChangeListener(System.out::println), 6, 0, 1, 3); root.add(new WSlider(0, 123, Axis.HORIZONTAL).setValueChangeListener(System.out::println), 1, 4, 4, 1); root.add(new WKirbSprite(), 5, 4); diff --git a/src/main/java/io/github/cottonmc/cotton/gui/widget/WSlider.java b/src/main/java/io/github/cottonmc/cotton/gui/widget/WSlider.java index c63b5ee..65ef7e3 100644 --- a/src/main/java/io/github/cottonmc/cotton/gui/widget/WSlider.java +++ b/src/main/java/io/github/cottonmc/cotton/gui/widget/WSlider.java @@ -1,6 +1,9 @@ package io.github.cottonmc.cotton.gui.widget; +import io.github.cottonmc.cotton.gui.client.BackgroundPainter; import io.github.cottonmc.cotton.gui.client.ScreenDrawing; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; import net.minecraft.client.MinecraftClient; import net.minecraft.util.Identifier; import net.minecraft.util.math.MathHelper; @@ -16,13 +19,12 @@ import java.util.function.IntConsumer; * */ -// TODO: Fix the blocked pixel at the top of vertical sliders public class WSlider extends WWidget { private static final int TRACK_WIDTH = 6; private static final int THUMB_SIZE = 8; @@ -35,11 +37,15 @@ public class WSlider extends WWidget { private int value; private float valueToCoordRatio, coordToValueRatio; @Nullable private IntConsumer valueChangeListener = null; - @Nullable private Runnable mouseReleaseListener = null; + @Nullable private Runnable focusReleaseListener = null; + + @Environment(EnvType.CLIENT) + @Nullable + private BackgroundPainter backgroundPainter = null; // Used for visuals and detecting dragging after the user starts dragging // on top of the slider, but then moves the mouse out but still within the widget's boundary. - private boolean dragging = false; +// private boolean dragging = false; public WSlider(int min, int max, Axis axis) { if (max <= min) @@ -70,15 +76,28 @@ public class WSlider extends WWidget { } @Override - public void onMouseDrag(int x, int y, int button) { - // a = mouse coordinate on slider axis + public boolean canFocus() { + return true; + } + + @Override + public WWidget onMouseDown(int x, int y, int button) { // ao = axis-opposite mouse coordinate, aoCenter = center of ao's axis - int a = axis == Axis.HORIZONTAL ? x : y; int ao = axis == Axis.HORIZONTAL ? y : x; int aoCenter = (axis == Axis.HORIZONTAL ? height : width) / 2; - if (dragging || ao >= aoCenter - TRACK_WIDTH / 2 - 2 && ao <= aoCenter + TRACK_WIDTH / 2 + 2) { - dragging = true; - int pos = (axis == Axis.VERTICAL ? (height - a) : a) - THUMB_SIZE / 2; + + // Check if cursor is inside or <=2px away from track + if (ao >= aoCenter - TRACK_WIDTH / 2 - 2 && ao <= aoCenter + TRACK_WIDTH / 2 + 2) { + requestFocus(); + } + return super.onMouseDown(x, y, button); + } + + @Override + public void onMouseDrag(int x, int y, int button) { + if (isFocused()) { + //dragging = true; + int pos = (axis == Axis.VERTICAL ? (height - y) : x) - THUMB_SIZE / 2; int futureValue = min + (int) (valueToCoordRatio * pos); value = MathHelper.clamp(futureValue, min, max); if (valueChangeListener != null) valueChangeListener.accept(value); @@ -93,31 +112,40 @@ public class WSlider extends WWidget { @Override public WWidget onMouseUp(int x, int y, int button) { - dragging = false; - if (mouseReleaseListener != null) mouseReleaseListener.run(); - + releaseFocus(); return super.onMouseUp(x, y, button); } + @Override + public void onFocusLost() { + if (focusReleaseListener != null) focusReleaseListener.run(); + } + + @Environment(EnvType.CLIENT) @Override public void paintBackground(int x, int y) { - float px = 1 / 32f; + if (backgroundPainter != null) { + backgroundPainter.paintBackground(x, y, this); + } else { + float px = 1 / 32f; - if (axis == Axis.VERTICAL) { - int trackX = x + width / 2 - TRACK_WIDTH / 2; + if (axis == Axis.VERTICAL) { + int trackX = x + width / 2 - TRACK_WIDTH / 2; - ScreenDrawing.rect(TEXTURE, trackX, y + 1, TRACK_WIDTH, 1, 16*px, 0*px, 22*px, 1*px, 0xFFFFFFFF); - ScreenDrawing.rect(TEXTURE, trackX, y + 2, TRACK_WIDTH, height - 2, 16*px, 1*px, 22*px, 2*px, 0xFFFFFFFF); - ScreenDrawing.rect(TEXTURE, trackX, y + height, TRACK_WIDTH, 1, 16*px, 2*px, 22*px, 3*px, 0xFFFFFFFF); - } else { - int trackY = y + height / 2 - TRACK_WIDTH / 2; + ScreenDrawing.rect(TEXTURE, trackX, y + 1, TRACK_WIDTH, 1, 16 * px, 0 * px, 22 * px, 1 * px, 0xFFFFFFFF); + ScreenDrawing.rect(TEXTURE, trackX, y + 2, TRACK_WIDTH, height - 2, 16 * px, 1 * px, 22 * px, 2 * px, 0xFFFFFFFF); + ScreenDrawing.rect(TEXTURE, trackX, y + height, TRACK_WIDTH, 1, 16 * px, 2 * px, 22 * px, 3 * px, 0xFFFFFFFF); + } else { + int trackY = y + height / 2 - TRACK_WIDTH / 2; - ScreenDrawing.rect(TEXTURE, x, trackY, 1, TRACK_WIDTH, 16*px, 3*px, 17*px, 9*px, 0xFFFFFFFF); - ScreenDrawing.rect(TEXTURE, x + 1, trackY, width - 2, TRACK_WIDTH, 17*px, 3*px, 18*px, 9*px, 0xFFFFFFFF); - ScreenDrawing.rect(TEXTURE, x + width - 1, trackY, 1, TRACK_WIDTH, 18*px, 3*px, 19*px, 9*px, 0xFFFFFFFF); + ScreenDrawing.rect(TEXTURE, x, trackY, 1, TRACK_WIDTH, 16 * px, 3 * px, 17 * px, 9 * px, 0xFFFFFFFF); + ScreenDrawing.rect(TEXTURE, x + 1, trackY, width - 2, TRACK_WIDTH, 17 * px, 3 * px, 18 * px, 9 * px, 0xFFFFFFFF); + ScreenDrawing.rect(TEXTURE, x + width - 1, trackY, 1, TRACK_WIDTH, 18 * px, 3 * px, 19 * px, 9 * px, 0xFFFFFFFF); + } } } + @Environment(EnvType.CLIENT) @Override public void paintForeground(int x, int y, int mouseX, int mouseY) { float px = 1 / 32f; @@ -133,7 +161,8 @@ public class WSlider extends WWidget { thumbXOffset = 8; } - // FIXME: Ugly, I really should remove this + boolean dragging = isFocused(); + // TODO: Replace with proper mouse events if (dragging) { if (GLFW.glfwGetMouseButton(MinecraftClient.getInstance().window.getHandle(), GLFW.GLFW_MOUSE_BUTTON_1) == GLFW.GLFW_PRESS) { onMouseDrag(mouseX - x, mouseY - y, 0); @@ -163,8 +192,13 @@ public class WSlider extends WWidget { return this; } - public WSlider setMouseReleaseListener(@Nullable Runnable mouseReleaseListener) { - this.mouseReleaseListener = mouseReleaseListener; + public WSlider setFocusReleaseListener(@Nullable Runnable focusReleaseListener) { + this.focusReleaseListener = focusReleaseListener; return this; } + + @Environment(EnvType.CLIENT) + public void setBackgroundPainter(BackgroundPainter backgroundPainter) { + this.backgroundPainter = backgroundPainter; + } } -- cgit