From b518f56f6d727b634338a106130fe0fb276b84a5 Mon Sep 17 00:00:00 2001 From: Artha Date: Mon, 23 Dec 2024 13:26:47 +0100 Subject: [PATCH] WIP WTF stack corruption --- source/fluid/separator.d | 10 +++++--- source/fluid/style.d | 30 +++++++++++++++++------- tests/legacy/separator.d | 5 +++- tests/nodes/separator.d | 49 ++++++++++++++++++++++++++++++++++++++++ 4 files changed, 82 insertions(+), 12 deletions(-) create mode 100644 tests/nodes/separator.d diff --git a/source/fluid/separator.d b/source/fluid/separator.d index 79ab8c1c..ec506493 100644 --- a/source/fluid/separator.d +++ b/source/fluid/separator.d @@ -6,6 +6,7 @@ import fluid.utils; import fluid.backend; import fluid.structs; +import fluid.io.canvas; @safe: @@ -29,6 +30,8 @@ alias hseparator = simpleConstructor!(Separator, (a) { /// ditto class Separator : Node { + CanvasIO canvasIO; + public { bool isHorizontal; @@ -37,6 +40,7 @@ class Separator : Node { override void resizeImpl(Vector2) { + use(canvasIO); minSize = Vector2(1, 1); } @@ -45,14 +49,14 @@ class Separator : Node { auto style = pickStyle(); - style.drawBackground(io, outer); + style.drawBackground(io, canvasIO, outer); if (isHorizontal) { auto start = Vector2(start(inner).x, center(inner).y); auto end = Vector2(end(inner).x, center(inner).y); - style.drawLine(io, start, end); + style.drawLine(io, canvasIO, start, end); } @@ -61,7 +65,7 @@ class Separator : Node { auto start = Vector2(center(inner).x, start(inner).y); auto end = Vector2(center(inner).x, end(inner).y); - style.drawLine(io, start, end); + style.drawLine(io, canvasIO, start, end); } diff --git a/source/fluid/style.d b/source/fluid/style.d index 2dd82f98..f9e8cf82 100644 --- a/source/fluid/style.d +++ b/source/fluid/style.d @@ -14,7 +14,7 @@ import fluid.typeface; import fluid.io.canvas; -public import fluid.theme : makeTheme, Theme, Selector, rule, Rule, when, WhenRule, children, ChildrenRule, Field, +public import fluid.theme : makeTheme, Theme, Selector, rule, Rule, when, WhenRule, children, ChildrenRule, Field, Breadcrumbs; public import fluid.border; public import fluid.default_theme; @@ -144,7 +144,7 @@ struct Style { public { - /// Breadcrumbs associated with this style. Used to keep track of tree-aware theme selectors, such as + /// Breadcrumbs associated with this style. Used to keep track of tree-aware theme selectors, such as /// `children`. Does not include breadcrumbs loaded by parent nodes. Breadcrumbs breadcrumbs; @@ -217,7 +217,7 @@ struct Style { } } - + /// ditto void drawBackground(FluidBackend backend, CanvasIO io, Rectangle rect) const { @@ -247,6 +247,20 @@ struct Style { } + /// ditto + void drawLine(FluidBackend backend, CanvasIO canvasIO, Vector2 start, Vector2 end) const { + + // New I/O system used + if (canvasIO) { + + canvasIO.drawLine(start, end, 1, lineColor); + + } + + else drawLine(backend, start, end); + + } + /// Get a side array holding both the regular margin and the border. float[4] fullMargin() const { @@ -479,7 +493,7 @@ unittest { assert(sides.sideX == 1); assert(sides.sideY == 2); - + } /// Returns a side array created from either: another side array like it, a two item array with each representing an @@ -669,7 +683,7 @@ unittest { } -/// Check if a rectangle is located above (`isAbove`), below (`isBelow`), to the left (`isToLeft`) or to the right +/// Check if a rectangle is located above (`isAbove`), below (`isBelow`), to the left (`isToLeft`) or to the right /// (`isToRight`) of another rectangle. /// /// The four functions wrap `isBeyond` which accepts a `Side` argument to specify direction at runtime. @@ -741,12 +755,12 @@ bool isBeyond(Rectangle subject, Rectangle reference, Style.Side side) { // side ↑ ↑ side.reverse side ↑ side ↑ const condition = abs(distanceInternal) > abs(distanceExternal); - // ↓ subject There is an edgecase though. If one box entirely overlaps the other on one axis, + // ↓ subject There is an edgecase though. If one box entirely overlaps the other on one axis, // +====================+ it will be simultaneously to the left, and to the right, creating an ambiguity. - // | ↓ reference | + // | ↓ reference | // | +------------+ | This is unwated in scenarios like focus switching. A scrollbar placed to the right // | | | | of the page, should be focused by the right key, not by up or down. - // +===| |===+ + // +===| |===+ // | | For this reason, we require both `distanceInternal` and `distanceExternal` to have // +------------+ the same sign, as it normally would, but not in case of an overlap. return condition diff --git a/tests/legacy/separator.d b/tests/legacy/separator.d index 97eef414..27c9666d 100644 --- a/tests/legacy/separator.d +++ b/tests/legacy/separator.d @@ -1,10 +1,13 @@ +@Migrated module legacy.separator; import fluid; +import legacy; @safe: -@("[TODO] Legacy: vseparator draws a vertical line, hseparator draws a horizontal line") +@("vseparator draws a vertical line, hseparator draws a horizontal line") +@Migrated unittest { import fluid.theme; diff --git a/tests/nodes/separator.d b/tests/nodes/separator.d new file mode 100644 index 00000000..6628fde4 --- /dev/null +++ b/tests/nodes/separator.d @@ -0,0 +1,49 @@ +module nodes.separator; + +import fluid; + +@safe: + +@("separator draws a vertical or horizontal line") +unittest { + + import fluid.theme; + + auto theme = nullTheme.derive( + rule!Separator( + lineColor = color("#000"), + ), + ); + + // Vertical + { + auto separator = vseparator(); + auto root = sizeLock!htestSpace( + .sizeLimit(100, 100), + .layout!(1, "fill"), + theme, + separator + ); + + root.isHorizontal = true; + root.drawAndAssert( + separator.drawsLine().from(50, 0).to(50, 100).ofWidth(1).ofColor("#000"), + ); + } + + // Horizontal + { + auto separator = hseparator(); + auto root = sizeLock!vtestSpace( + .sizeLimit(100, 100), + .layout!(1, "fill"), + theme, + separator + ); + + root.drawAndAssert( + separator.drawsLine().from(0, 0).to(100, 50).ofWidth(1).ofColor("#000"), + ); + } + +}