diff --git a/packages/imgui/src/behaviors/button.ts b/packages/imgui/src/behaviors/button.ts index 55a029f22e..079fb44f01 100644 --- a/packages/imgui/src/behaviors/button.ts +++ b/packages/imgui/src/behaviors/button.ts @@ -1,6 +1,15 @@ +import { pointInside } from "@thi.ng/geom"; +import { IShape } from "@thi.ng/geom-api"; import { Key } from "../api"; import { IMGUI } from "../gui"; +export const isHoverButton = (gui: IMGUI, id: string, shape: IShape) => { + const aid = gui.activeID; + const hover = (aid === "" || aid === id) && pointInside(shape, gui.mouse); + hover && (gui.hotID = id); + return hover; +}; + export const handleButtonKeys = (gui: IMGUI) => { switch (gui.key) { case Key.TAB: diff --git a/packages/imgui/src/behaviors/slider.ts b/packages/imgui/src/behaviors/slider.ts index e0bb7c17cb..e7c68840e2 100644 --- a/packages/imgui/src/behaviors/slider.ts +++ b/packages/imgui/src/behaviors/slider.ts @@ -1,3 +1,5 @@ +import { pointInside } from "@thi.ng/geom"; +import { IShape } from "@thi.ng/geom-api"; import { clamp, roundTo } from "@thi.ng/math"; import { add2, @@ -8,6 +10,13 @@ import { import { Key } from "../api"; import { IMGUI } from "../gui"; +export const isHoverSlider = (gui: IMGUI, id: string, shape: IShape) => { + const aid = gui.activeID; + const hover = aid === id || (aid === "" && pointInside(shape, gui.mouse)); + hover && (gui.hotID = id); + return hover; +}; + export const slider1Val = (x: number, min: number, max: number, prec: number) => clamp(roundTo(x, prec), min, max); diff --git a/packages/imgui/src/components/button.ts b/packages/imgui/src/components/button.ts index 7208c87d26..c460100383 100644 --- a/packages/imgui/src/components/button.ts +++ b/packages/imgui/src/components/button.ts @@ -2,7 +2,7 @@ import { rect } from "@thi.ng/geom"; import { IShape } from "@thi.ng/geom-api"; import { hash, ZERO2 } from "@thi.ng/vectors"; import { Color, IGridLayout, LayoutBox } from "../api"; -import { handleButtonKeys } from "../behaviors/button"; +import { handleButtonKeys, isHoverButton } from "../behaviors/button"; import { IMGUI } from "../gui"; import { isLayout } from "../layout"; import { textLabelRaw, textTransformH, textTransformV } from "./textlabel"; @@ -98,7 +98,7 @@ export const buttonRaw = ( info?: string ) => { gui.registerID(id, hash); - const hover = gui.isHover(id, shape); + const hover = isHoverButton(gui, id, shape); if (hover) { gui.isMouseDown() && (gui.activeID = id); info && tooltipRaw(gui, info); diff --git a/packages/imgui/src/components/dial.ts b/packages/imgui/src/components/dial.ts index 54efe6d249..dd2c0f0e42 100644 --- a/packages/imgui/src/components/dial.ts +++ b/packages/imgui/src/components/dial.ts @@ -1,6 +1,5 @@ import { Fn } from "@thi.ng/api"; import { circle, line } from "@thi.ng/geom"; -import { pointInCircle } from "@thi.ng/geom-isec"; import { HALF_PI, norm, @@ -10,7 +9,7 @@ import { import { cartesian2, hash } from "@thi.ng/vectors"; import { LayoutBox } from "../api"; import { dialVal } from "../behaviors/dial"; -import { handleSlider1Keys } from "../behaviors/slider"; +import { handleSlider1Keys, isHoverSlider } from "../behaviors/slider"; import { IMGUI } from "../gui"; import { GridLayout, isLayout } from "../layout"; import { textLabelRaw } from "./textlabel"; @@ -74,9 +73,8 @@ export const dialRaw = ( const startTheta = HALF_PI + thetaGap / 2; const key = hash([x, y, r]); gui.registerID(id, key); - const aid = gui.activeID; - const hover = - aid === id || (aid === "" && pointInCircle(gui.mouse, pos, r)); + const bgShape = gui.resource(id, key, () => circle(pos, r, {})); + const hover = isHoverSlider(gui, id, bgShape); if (hover) { gui.hotID = id; if (gui.isMouseDown()) { @@ -96,9 +94,6 @@ export const dialRaw = ( } const focused = gui.requestFocus(id); const v = val[i]; - const bgShape = gui.resource(id, key, () => circle(pos, r, {})); - bgShape.attribs.fill = gui.bgColor(hover || focused); - bgShape.attribs.stroke = gui.focusColor(id); const valShape = gui.resource(id, v, () => line( cartesian2( @@ -110,8 +105,6 @@ export const dialRaw = ( {} ) ); - valShape.attribs.stroke = gui.fgColor(hover); - valShape.attribs.weight = 2; const valLabel = gui.resource(id, "l" + v, () => textLabelRaw( [x + lx, y + ly], @@ -119,6 +112,10 @@ export const dialRaw = ( (label ? label + " " : "") + (fmt ? fmt(v) : v) ) ); + bgShape.attribs.fill = gui.bgColor(hover || focused); + bgShape.attribs.stroke = gui.focusColor(id); + valShape.attribs.stroke = gui.fgColor(hover); + valShape.attribs.weight = 2; gui.add(bgShape, valShape, valLabel); if (focused && handleSlider1Keys(gui, min, max, prec, val, i)) { return true; diff --git a/packages/imgui/src/components/ring.ts b/packages/imgui/src/components/ring.ts index 0b2834e929..7b71142163 100644 --- a/packages/imgui/src/components/ring.ts +++ b/packages/imgui/src/components/ring.ts @@ -134,8 +134,6 @@ export const ringRaw = ( {} ) ); - bgShape.attribs.fill = gui.bgColor(hover || focused); - bgShape.attribs.stroke = gui.focusColor(id); const valShape = gui.resource(id, v, () => polygon( [ @@ -145,7 +143,6 @@ export const ringRaw = ( {} ) ); - valShape.attribs.fill = gui.fgColor(hover); const valLabel = gui.resource(id, "l" + v, () => textLabelRaw( [x + lx, y + ly], @@ -153,6 +150,9 @@ export const ringRaw = ( (label ? label + " " : "") + (fmt ? fmt(v) : v) ) ); + bgShape.attribs.fill = gui.bgColor(hover || focused); + bgShape.attribs.stroke = gui.focusColor(id); + valShape.attribs.fill = gui.fgColor(hover); gui.add(bgShape, valShape, valLabel); if (focused && handleSlider1Keys(gui, min, max, prec, val, i)) { return true; diff --git a/packages/imgui/src/components/sliderh.ts b/packages/imgui/src/components/sliderh.ts index 33edf71eef..b555e41f88 100644 --- a/packages/imgui/src/components/sliderh.ts +++ b/packages/imgui/src/components/sliderh.ts @@ -3,7 +3,7 @@ import { rect } from "@thi.ng/geom"; import { fit, norm } from "@thi.ng/math"; import { hash } from "@thi.ng/vectors"; import { IGridLayout, LayoutBox } from "../api"; -import { handleSlider1Keys, slider1Val } from "../behaviors/slider"; +import { handleSlider1Keys, isHoverSlider, slider1Val } from "../behaviors/slider"; import { IMGUI } from "../gui"; import { isLayout } from "../layout"; import { textLabelRaw } from "./textlabel"; @@ -70,7 +70,7 @@ export const sliderHRaw = ( const key = hash([x, y, w, h]); gui.registerID(id, key); const box = gui.resource(id, key, () => rect([x, y], [w, h], {})); - const hover = gui.isHover(id, box); + const hover = isHoverSlider(gui, id, box); if (hover) { if (gui.isMouseDown()) { gui.activeID = id; @@ -86,13 +86,9 @@ export const sliderHRaw = ( } const focused = gui.requestFocus(id); const v = val[i]; - const normVal = norm(v, min, max); const valueBox = gui.resource(id, v, () => - rect([x, y], [1 + normVal * (w - 1), h], {}) + rect([x, y], [1 + norm(v, min, max) * (w - 1), h], {}) ); - valueBox.attribs.fill = gui.fgColor(hover); - box.attribs.fill = gui.bgColor(hover || focused); - box.attribs.stroke = gui.focusColor(id); const valLabel = gui.resource(id, "l" + v, () => textLabelRaw( [x + theme.pad, y + h / 2 + theme.baseLine], @@ -100,6 +96,9 @@ export const sliderHRaw = ( (label ? label + " " : "") + (fmt ? fmt(v) : v) ) ); + box.attribs.fill = gui.bgColor(hover || focused); + box.attribs.stroke = gui.focusColor(id); + valueBox.attribs.fill = gui.fgColor(hover); gui.add(box, valueBox, valLabel); if (focused && handleSlider1Keys(gui, min, max, prec, val, i)) { return true; diff --git a/packages/imgui/src/components/sliderv.ts b/packages/imgui/src/components/sliderv.ts index d27360318c..bad14f6a48 100644 --- a/packages/imgui/src/components/sliderv.ts +++ b/packages/imgui/src/components/sliderv.ts @@ -3,7 +3,7 @@ import { rect } from "@thi.ng/geom"; import { fit, norm } from "@thi.ng/math"; import { hash, ZERO2 } from "@thi.ng/vectors"; import { IGridLayout, LayoutBox } from "../api"; -import { handleSlider1Keys, slider1Val } from "../behaviors/slider"; +import { handleSlider1Keys, isHoverSlider, slider1Val } from "../behaviors/slider"; import { IMGUI } from "../gui"; import { isLayout } from "../layout"; import { textLabelRaw, textTransformV } from "./textlabel"; @@ -72,7 +72,7 @@ export const sliderVRaw = ( gui.registerID(id, key); const box = gui.resource(id, key, () => rect([x, y], [w, h], {})); const ymax = y + h; - const hover = gui.isHover(id, box); + const hover = isHoverSlider(gui, id, box); if (hover) { if (gui.isMouseDown()) { gui.activeID = id; @@ -88,14 +88,10 @@ export const sliderVRaw = ( } const focused = gui.requestFocus(id); const v = val[i]; - const normVal = norm(v, min, max); const valueBox = gui.resource(id, v, () => { - const nh = normVal * (h - 1); + const nh = norm(v, min, max) * (h - 1); return rect([x, ymax - nh], [w, nh], {}); }); - valueBox.attribs.fill = gui.fgColor(hover); - box.attribs.fill = gui.bgColor(hover || focused); - box.attribs.stroke = gui.focusColor(id); const valLabel = gui.resource(id, "l" + v, () => textLabelRaw( ZERO2, @@ -106,6 +102,9 @@ export const sliderVRaw = ( (label ? label + " " : "") + (fmt ? fmt(v) : v) ) ); + valueBox.attribs.fill = gui.fgColor(hover); + box.attribs.fill = gui.bgColor(hover || focused); + box.attribs.stroke = gui.focusColor(id); gui.add(box, valueBox, valLabel); if (focused && handleSlider1Keys(gui, min, max, prec, val, i)) { return true; diff --git a/packages/imgui/src/components/textfield.ts b/packages/imgui/src/components/textfield.ts index 4bea37d09e..c4f7e5ed1a 100644 --- a/packages/imgui/src/components/textfield.ts +++ b/packages/imgui/src/components/textfield.ts @@ -3,6 +3,7 @@ import { rect } from "@thi.ng/geom"; import { fitClamped } from "@thi.ng/math"; import { hash } from "@thi.ng/vectors"; import { IGridLayout, Key, LayoutBox } from "../api"; +import { isHoverSlider } from "../behaviors/slider"; import { IMGUI } from "../gui"; import { isLayout } from "../layout"; import { textLabelRaw } from "./textlabel"; @@ -43,7 +44,7 @@ export const textFieldRaw = ( const key = hash([x, y, w, h]); gui.registerID(id, key); const box = gui.resource(id, key, () => rect([x, y], [w, h], {})); - const hover = gui.isHover(id, box); + const hover = isHoverSlider(gui, id, box); if (hover) { if (gui.isMouseDown()) { gui.activeID = id; diff --git a/packages/imgui/src/components/toggle.ts b/packages/imgui/src/components/toggle.ts index b3338fa9b5..01d8775dcb 100644 --- a/packages/imgui/src/components/toggle.ts +++ b/packages/imgui/src/components/toggle.ts @@ -1,7 +1,7 @@ import { rect } from "@thi.ng/geom"; import { hash } from "@thi.ng/vectors"; import { IGridLayout, LayoutBox } from "../api"; -import { handleButtonKeys } from "../behaviors/button"; +import { handleButtonKeys, isHoverButton } from "../behaviors/button"; import { IMGUI } from "../gui"; import { isLayout } from "../layout"; import { textLabelRaw } from "./textlabel"; @@ -63,7 +63,7 @@ export const toggleRaw = ( const key = hash([x, y, w, h]); gui.registerID(id, key); const box = gui.resource(id, key, () => rect([x, y], [w, h])); - const hover = gui.isHover(id, box); + const hover = isHoverButton(gui, id, box); if (hover) { gui.isMouseDown() && (gui.activeID = id); info && tooltipRaw(gui, info); diff --git a/packages/imgui/src/components/xypad.ts b/packages/imgui/src/components/xypad.ts index 4ba8c07363..7c7e9e65a4 100644 --- a/packages/imgui/src/components/xypad.ts +++ b/packages/imgui/src/components/xypad.ts @@ -2,7 +2,7 @@ import { Fn } from "@thi.ng/api"; import { line, rect } from "@thi.ng/geom"; import { fit2, hash, Vec } from "@thi.ng/vectors"; import { IGridLayout, LayoutBox } from "../api"; -import { handleSlider2Keys, slider2Val } from "../behaviors/slider"; +import { handleSlider2Keys, isHoverSlider, slider2Val } from "../behaviors/slider"; import { IMGUI } from "../gui"; import { textLabelRaw } from "./textlabel"; import { tooltipRaw } from "./tooltip"; @@ -97,7 +97,7 @@ export const xyPadRaw = ( gui.registerID(id, key); const box = gui.resource(id, key, () => rect([x, y], [w, h])); const col = gui.textColor(false); - const hover = gui.isHover(id, box); + const hover = isHoverSlider(gui, id, box); if (hover) { if (gui.isMouseDown()) { gui.activeID = id; diff --git a/packages/imgui/src/gui.ts b/packages/imgui/src/gui.ts index 37e751e2c4..70e2953dcb 100644 --- a/packages/imgui/src/gui.ts +++ b/packages/imgui/src/gui.ts @@ -1,6 +1,4 @@ import { Fn0, IToHiccup } from "@thi.ng/api"; -import { pointInside } from "@thi.ng/geom"; -import { IShape } from "@thi.ng/geom-api"; import { set2, Vec } from "@thi.ng/vectors"; import { DEFAULT_THEME, @@ -87,14 +85,6 @@ export class IMGUI implements IToHiccup { this.key = ""; } - isHover(id: string, shape: IShape) { - const aid = this.activeID; - const hover = - aid === id || (aid === "" && pointInside(shape, this.mouse)); - hover && (this.hotID = id); - return hover; - } - isMouseDown() { return this.buttons & MouseButton.LEFT; }