diff --git a/packages/flutter/lib/src/cupertino/dialog.dart b/packages/flutter/lib/src/cupertino/dialog.dart index 3f025965178..7b525854f0f 100644 --- a/packages/flutter/lib/src/cupertino/dialog.dart +++ b/packages/flutter/lib/src/cupertino/dialog.dart @@ -2115,6 +2115,7 @@ class CupertinoDialogAction extends StatefulWidget { this.isDefaultAction = false, this.isDestructiveAction = false, this.textStyle, + this.mouseCursor, required this.child, }); @@ -2149,6 +2150,12 @@ class CupertinoDialogAction extends StatefulWidget { /// [_kCupertinoDialogActionStyle]. final TextStyle? textStyle; + /// The cursor that will be shown when hovering over the button. + /// + /// If null, defaults to [SystemMouseCursors.click] on web and + /// [MouseCursor.defer] on other platforms. + final MouseCursor? mouseCursor; + /// The widget below this widget in the tree. /// /// Typically a [Text] widget. @@ -2269,7 +2276,8 @@ class _CupertinoDialogActionState extends State implement ); return MouseRegion( - cursor: widget.onPressed != null && kIsWeb ? SystemMouseCursors.click : MouseCursor.defer, + cursor: + widget.mouseCursor ?? (enabled && kIsWeb ? SystemMouseCursors.click : MouseCursor.defer), child: MetaData( metaData: this, behavior: HitTestBehavior.opaque, diff --git a/packages/flutter/test/cupertino/dialog_test.dart b/packages/flutter/test/cupertino/dialog_test.dart index bbb00ae9343..f40302278e7 100644 --- a/packages/flutter/test/cupertino/dialog_test.dart +++ b/packages/flutter/test/cupertino/dialog_test.dart @@ -14,6 +14,7 @@ import 'package:flutter/cupertino.dart'; import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter/rendering.dart'; +import 'package:flutter/services.dart'; import 'package:flutter_test/flutter_test.dart'; import '../widgets/semantics_tester.dart'; @@ -2117,6 +2118,45 @@ void main() { noButton = tester.getCenter(find.text('No')); expect(yesButton.dx > noButton.dx, false); }); + + testWidgets('CupertinoDialogAction.mouseCursor can customize the mouse cursor', ( + WidgetTester tester, + ) async { + const SystemMouseCursor customCursor = SystemMouseCursors.grab; + + await tester.pumpWidget( + CupertinoApp( + home: Directionality( + textDirection: TextDirection.ltr, + child: CupertinoAlertDialog( + actions: [ + CupertinoDialogAction( + mouseCursor: customCursor, + child: const Text('Yes'), + onPressed: () {}, + ), + ], + ), + ), + ), + ); + + final TestGesture gesture = await tester.createGesture( + kind: PointerDeviceKind.mouse, + pointer: 1, + ); + await gesture.addPointer(location: const Offset(10, 10)); + await tester.pumpAndSettle(); + expect( + RendererBinding.instance.mouseTracker.debugDeviceActiveCursor(1), + SystemMouseCursors.basic, + ); + + final Offset actionSheetAction = tester.getCenter(find.text('Yes')); + await gesture.moveTo(actionSheetAction); + await tester.pumpAndSettle(); + expect(RendererBinding.instance.mouseTracker.debugDeviceActiveCursor(1), customCursor); + }); } RenderBox findActionButtonRenderBoxByTitle(WidgetTester tester, String title) {