From 36cd1bfeec396fdfc4b75c20091e11222a5dd0de Mon Sep 17 00:00:00 2001 From: Sergio Martins Date: Sun, 19 Jan 2025 18:26:34 +0000 Subject: [PATCH] flutter: fix incorrect rendering due to not using keys Flutter would reuse an arbitrary GroupWidget when rebuilding the tree --- src/flutter/dart/lib/widgets/DockWidget.dart | 2 +- .../dart/lib/widgets/FloatingWidget.dart | 2 +- src/flutter/dart/lib/widgets/GroupWidget.dart | 2 +- .../dart/lib/widgets/SeparatorWidget.dart | 2 +- .../dart/lib/widgets/TabBarWidget.dart | 2 +- .../dart/lib/widgets/TitleBarWidget.dart | 2 +- tests/flutter/integration_test/ui_test.dart | 35 +++++++++++++++++++ tests/reference-images | 2 +- 8 files changed, 42 insertions(+), 7 deletions(-) diff --git a/src/flutter/dart/lib/widgets/DockWidget.dart b/src/flutter/dart/lib/widgets/DockWidget.dart index 6c3ad5d4d..b06444a52 100644 --- a/src/flutter/dart/lib/widgets/DockWidget.dart +++ b/src/flutter/dart/lib/widgets/DockWidget.dart @@ -14,7 +14,7 @@ import 'package:KDDockWidgets/KDDockWidgets.dart'; class DockWidget extends StatefulWidget { final DockItem dockItem; - DockWidget(this.dockItem, {Key? key}) : super(key: key) {} + DockWidget(this.dockItem) : super(key: ObjectKey(dockItem)) {} @override State createState() { diff --git a/src/flutter/dart/lib/widgets/FloatingWidget.dart b/src/flutter/dart/lib/widgets/FloatingWidget.dart index e9bfc2150..752b12387 100644 --- a/src/flutter/dart/lib/widgets/FloatingWidget.dart +++ b/src/flutter/dart/lib/widgets/FloatingWidget.dart @@ -20,7 +20,7 @@ import 'package:flutter/material.dart'; class FloatingWidget extends StatefulWidget { final FloatingItem floatingItem; - FloatingWidget(this.floatingItem, {Key? key}) : super(key: key); + FloatingWidget(this.floatingItem) : super(key: ObjectKey(floatingItem)); @override State createState() { diff --git a/src/flutter/dart/lib/widgets/GroupWidget.dart b/src/flutter/dart/lib/widgets/GroupWidget.dart index a660be18d..ddf98ddf5 100644 --- a/src/flutter/dart/lib/widgets/GroupWidget.dart +++ b/src/flutter/dart/lib/widgets/GroupWidget.dart @@ -21,7 +21,7 @@ import 'package:signals_slots/signals_slots.dart'; class GroupWidget extends PositionedWidget { final Group group; - GroupWidget(this.group, {Key? key}) : super(group, key: key); + GroupWidget(this.group) : super(group, key: ObjectKey(group)); @override State createState() { diff --git a/src/flutter/dart/lib/widgets/SeparatorWidget.dart b/src/flutter/dart/lib/widgets/SeparatorWidget.dart index 9a66cbe6e..07b35b22a 100644 --- a/src/flutter/dart/lib/widgets/SeparatorWidget.dart +++ b/src/flutter/dart/lib/widgets/SeparatorWidget.dart @@ -17,7 +17,7 @@ import 'PositionedWidget.dart'; class SeparatorWidget extends PositionedWidget { final Separator separator; - SeparatorWidget(this.separator, {Key? key}) : super(separator, key: key); + SeparatorWidget(this.separator) : super(separator, key: ObjectKey(separator)); @override State createState() { diff --git a/src/flutter/dart/lib/widgets/TabBarWidget.dart b/src/flutter/dart/lib/widgets/TabBarWidget.dart index 62579f2cc..2b29634be 100644 --- a/src/flutter/dart/lib/widgets/TabBarWidget.dart +++ b/src/flutter/dart/lib/widgets/TabBarWidget.dart @@ -19,7 +19,7 @@ import 'dart:ui'; class TabBarWidget extends StatefulWidget { final Group group; - TabBarWidget(this.group, {Key? key}) : super(key: key); + TabBarWidget(this.group) : super(key: ObjectKey(group)); @override State createState() { diff --git a/src/flutter/dart/lib/widgets/TitleBarWidget.dart b/src/flutter/dart/lib/widgets/TitleBarWidget.dart index 042b54b0a..cac942d40 100644 --- a/src/flutter/dart/lib/widgets/TitleBarWidget.dart +++ b/src/flutter/dart/lib/widgets/TitleBarWidget.dart @@ -16,7 +16,7 @@ import 'package:flutter/material.dart'; class TitleBarWidget extends StatefulWidget { final TitleBar titlebar; - TitleBarWidget(this.titlebar, {Key? key}) : super(key: key); + TitleBarWidget(this.titlebar) : super(key: ObjectKey(titlebar)); @override State createState() { diff --git a/tests/flutter/integration_test/ui_test.dart b/tests/flutter/integration_test/ui_test.dart index 28fe44b64..2fe9adf6c 100644 --- a/tests/flutter/integration_test/ui_test.dart +++ b/tests/flutter/integration_test/ui_test.dart @@ -95,4 +95,39 @@ void main() async { await tester.pump(); await saveScreenShot(tester, prefix: "basic"); }); + + testWidgets('TitleBar close button', (WidgetTester tester) async { + final dock1 = DockItem(uniqueName: "dw1", guestWidget: MyWidget()); + final dock2 = DockItem(uniqueName: "dw2", guestWidget: MyWidget()); + + final dropArea = DropArea(); + dropArea.addDockItem(dock1, Location.LocationOnTop); + dropArea.addDockItem(dock2, Location.LocationOnBottom); + + dropArea.setLayoutSize(700, 700); + final dropAreaWidget = DropAreaWidget(dropArea); + + // Build the widget tree + await tester.pumpWidget(MyApp( + child: dropAreaWidget, + )); + + await tester.pump(); + await saveScreenShot(tester, prefix: "titlebar-close-button"); + + expect(dropArea.groups.length, 2); + var topGroup = dropArea.groups.first; + var bottomGroup = dropArea.groups.last; + + topGroup.titlebar.onCloseClicked(); + expect(dropArea.containsGroup(topGroup), false); + expect(dropArea.containsGroup(bottomGroup), true); + expect(dropArea.groups.length, 1); + expect(dropArea.groups.first, bottomGroup); + expect(bottomGroup.numDockWidgets(), 1); + expect(bottomGroup.dockWidgetAt(0), dock2); + + await tester.pump(); + await saveScreenShot(tester, prefix: "titlebar-close-button-2"); + }); } diff --git a/tests/reference-images b/tests/reference-images index 0c8ee00e1..084260b75 160000 --- a/tests/reference-images +++ b/tests/reference-images @@ -1 +1 @@ -Subproject commit 0c8ee00e15c8c5159c4e300e3ce2823d7b12d397 +Subproject commit 084260b7571dff7cde577880b83476fc9c75f39a