From c1de4c9b4d6e2d5fc4796ad0f289984c8a4bf924 Mon Sep 17 00:00:00 2001 From: Leo Farias Date: Mon, 5 Oct 2026 23:05:09 -0400 Subject: [PATCH] refactor(mix): consolidate example widget modifiers --- .../lib/examples/snacks/glide_select.dart | 7 +- .../lib/examples/snacks/thought_line.dart | 3 +- .../modifiers/widget_modifier_wrap_test.dart | 140 ++++++++++++++++++ .../references/widget-modifiers-directives.md | 3 +- 4 files changed, 147 insertions(+), 6 deletions(-) create mode 100644 packages/mix/test/src/modifiers/widget_modifier_wrap_test.dart diff --git a/examples/showcase/lib/examples/snacks/glide_select.dart b/examples/showcase/lib/examples/snacks/glide_select.dart index c1d234a28..6e120e0ff 100644 --- a/examples/showcase/lib/examples/snacks/glide_select.dart +++ b/examples/showcase/lib/examples/snacks/glide_select.dart @@ -32,8 +32,11 @@ BoxStyler selectMenuStyle({required bool isOpen}) => BoxStyler() .borderRadius(.circular(10)) .padding(.all(4)) .border(.color(const Color(0x22FFFFFF)).width(1)) - .wrap(.opacity(isOpen ? 1 : 0)) - .wrap(.scale(x: isOpen ? 1 : .95, y: isOpen ? 1 : .95, alignment: .topLeft)) + .wrap( + .opacity( + isOpen ? 1 : 0, + ).scale(isOpen ? 1 : .95, isOpen ? 1 : .95, alignment: .topLeft), + ) .animate(.easeOut(isOpen ? 180.ms : 120.ms)); final selectStack = StackBoxStyler().stackAlignment(.topLeft); diff --git a/examples/showcase/lib/examples/snacks/thought_line.dart b/examples/showcase/lib/examples/snacks/thought_line.dart index 34fb1acfb..a79b3cf20 100644 --- a/examples/showcase/lib/examples/snacks/thought_line.dart +++ b/examples/showcase/lib/examples/snacks/thought_line.dart @@ -57,9 +57,8 @@ BoxStyler thoughtRevealStyle({required bool isVisible}) => BoxStyler() alignment: .topLeft, widthFactor: 1, heightFactor: isVisible ? 1 : 0, - ), + ).opacity(isVisible ? 1 : 0), ) - .wrap(.opacity(isVisible ? 1 : 0)) .animate(.easeOut(180.ms)); final thoughtInset = BoxStyler().padding(.top(6)).padding(.left(24)); diff --git a/packages/mix/test/src/modifiers/widget_modifier_wrap_test.dart b/packages/mix/test/src/modifiers/widget_modifier_wrap_test.dart new file mode 100644 index 000000000..c6d7e4ba6 --- /dev/null +++ b/packages/mix/test/src/modifiers/widget_modifier_wrap_test.dart @@ -0,0 +1,140 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_test/flutter_test.dart'; +import 'package:mix/mix.dart'; + +void main() { + test('chained modifiers preserve separate wrap calls for both states', () { + for (final active in [false, true]) { + expect( + BoxStyler().wrap( + .opacity( + active ? 1 : 0, + ).scale(active ? 1 : .95, active ? 1 : .95, alignment: .topLeft), + ), + BoxStyler() + .wrap(.opacity(active ? 1 : 0)) + .wrap( + .scale( + x: active ? 1 : .95, + y: active ? 1 : .95, + alignment: .topLeft, + ), + ), + ); + expect( + BoxStyler().wrap( + .align( + alignment: .topLeft, + widthFactor: 1, + heightFactor: active ? 1 : 0, + ).opacity(active ? 1 : 0), + ), + BoxStyler() + .wrap( + .align( + alignment: .topLeft, + widthFactor: 1, + heightFactor: active ? 1 : 0, + ), + ) + .wrap(.opacity(active ? 1 : 0)), + ); + } + expect( + BoxStyler().wrap(.opacity(0.5).rotate(radians: 0.1)), + BoxStyler().wrap(.opacity(0.5)).wrap(.rotate(radians: 0.1)), + ); + }); + + for (final customOrder in [false, true]) { + testWidgets( + 'single wrap preserves rendering with customOrder=$customOrder', + (tester) async { + final base = BoxStyler().color(Colors.white).size(200, 100); + final separate = base + .wrap(.opacity(0.9)) + .wrap(.padding(.all(16))) + .wrap(.align(alignment: .center)); + final combined = base.wrap( + .opacity(0.9).padding(.all(16)).align(alignment: .center), + ); + expect(combined, separate); + final styles = [separate, combined]; + if (customOrder) { + styles[0] = separate.wrap( + .orderOfModifiers([ + OpacityModifier, + PaddingModifier, + AlignModifier, + ]), + ); + styles[1] = base.wrap( + .opacity( + 0.9, + ).padding(.all(16)).align(alignment: .center).orderOfModifiers([ + OpacityModifier, + PaddingModifier, + AlignModifier, + ]), + ); + expect(styles[1], styles[0]); + } else { + styles.add( + base.wrap( + .align(alignment: .center).padding(.all(16)).opacity(0.9), + ), + ); + } + for (final style in styles) { + await tester.pumpWidget( + Directionality( + textDirection: TextDirection.ltr, + child: Box(style: style), + ), + ); + final context = tester.element(find.byType(Box)); + expect( + style.$modifier!.resolve(context).map((m) => m.runtimeType), + customOrder + ? [OpacityModifier, PaddingModifier, AlignModifier] + : [AlignModifier, PaddingModifier, OpacityModifier], + ); + final opacity = tester.widget(find.byType(Opacity)); + final padding = tester.widget( + find.byWidgetPredicate( + (widget) => + widget is Padding && + widget.padding == const EdgeInsets.all(16), + ), + ); + final align = tester.widget( + find.byWidgetPredicate( + (widget) => + widget is Align && + (customOrder + ? identical(padding.child, widget) + : identical(widget.child, padding)), + ), + ); + expect(opacity.opacity, 0.9); + expect(align.alignment, Alignment.center); + if (customOrder) { + expect(opacity.child, same(padding)); + expect(padding.child, same(align)); + } else { + expect(align.child, same(padding)); + expect(padding.child, same(opacity)); + } + final container = tester.widget(find.byType(Container)); + expect( + container.constraints, + BoxConstraints.tightFor(width: 200, height: 100), + ); + expect((container.decoration as BoxDecoration).color, Colors.white); + expect(tester.takeException(), isNull); + await tester.pumpWidget(const SizedBox()); + } + }, + ); + } +} diff --git a/skills/mix/references/widget-modifiers-directives.md b/skills/mix/references/widget-modifiers-directives.md index 7073fc918..60d372e95 100644 --- a/skills/mix/references/widget-modifiers-directives.md +++ b/skills/mix/references/widget-modifiers-directives.md @@ -19,8 +19,7 @@ Modifiers wrap a widget with another widget (`Transform`, `Padding`, `Opacity`, ```dart final style = BoxStyler() .color(Colors.blue) - .wrap(WidgetModifierConfig.opacity(0.5)) - .wrap(WidgetModifierConfig.rotate(radians: 0.1)); + .wrap(.opacity(0.5).rotate(radians: 0.1)); ``` ### Built-in Modifiers