From 03da339ffe1fa1f45beac136725cb6560514c67e Mon Sep 17 00:00:00 2001 From: Kate Lovett Date: Mon, 24 Jan 2022 16:25:15 -0600 Subject: [PATCH] Deprecate Scrollbar isAlwaysShown -> thumbVisibility (#96957) --- .../scrollbar/cupertino_scrollbar.1.dart | 2 +- .../lib/material/scrollbar/scrollbar.1.dart | 2 +- .../scroll_metrics_notification.0.dart | 2 +- .../widgets/scrollbar/raw_scrollbar.0.dart | 4 +- .../widgets/scrollbar/raw_scrollbar.2.dart | 2 +- .../scrollbar/raw_scrollbar.shape.0.dart | 2 +- packages/flutter/lib/fix_data.yaml | 104 +++++++++++++ .../flutter/lib/src/cupertino/scrollbar.dart | 19 ++- .../flutter/lib/src/material/dropdown.dart | 2 +- .../flutter/lib/src/material/scrollbar.dart | 72 ++++++--- .../lib/src/material/scrollbar_theme.dart | 51 +++++-- .../flutter/lib/src/widgets/scrollbar.dart | 130 ++++++++++++++-- .../test/cupertino/scrollbar_test.dart | 143 ++++++++++++++++-- .../flutter/test/material/scrollbar_test.dart | 106 +++++++++++++ .../test/material/scrollbar_theme_test.dart | 14 +- .../flutter/test/widgets/scrollbar_test.dart | 38 +++++ packages/flutter/test_fixes/cupertino.dart | 6 + .../flutter/test_fixes/cupertino.dart.expect | 6 + packages/flutter/test_fixes/material.dart | 9 ++ .../flutter/test_fixes/material.dart.expect | 9 ++ packages/flutter/test_fixes/widgets.dart | 4 + .../flutter/test_fixes/widgets.dart.expect | 4 + 22 files changed, 657 insertions(+), 74 deletions(-) diff --git a/examples/api/lib/cupertino/scrollbar/cupertino_scrollbar.1.dart b/examples/api/lib/cupertino/scrollbar/cupertino_scrollbar.1.dart index 3297223001..9a75e9044b 100644 --- a/examples/api/lib/cupertino/scrollbar/cupertino_scrollbar.1.dart +++ b/examples/api/lib/cupertino/scrollbar/cupertino_scrollbar.1.dart @@ -45,7 +45,7 @@ class _MyStatefulWidgetState extends State { radius: const Radius.circular(34.0), radiusWhileDragging: Radius.zero, controller: _controllerOne, - isAlwaysShown: true, + thumbVisibility: true, child: ListView.builder( controller: _controllerOne, itemCount: 120, diff --git a/examples/api/lib/material/scrollbar/scrollbar.1.dart b/examples/api/lib/material/scrollbar/scrollbar.1.dart index 5ede5bd537..8e6896b1e7 100644 --- a/examples/api/lib/material/scrollbar/scrollbar.1.dart +++ b/examples/api/lib/material/scrollbar/scrollbar.1.dart @@ -39,7 +39,7 @@ class _MyStatefulWidgetState extends State { Widget build(BuildContext context) { return Scrollbar( controller: _controllerOne, - isAlwaysShown: true, + thumbVisibility: true, child: GridView.builder( controller: _controllerOne, itemCount: 120, diff --git a/examples/api/lib/widgets/scroll_position/scroll_metrics_notification.0.dart b/examples/api/lib/widgets/scroll_position/scroll_metrics_notification.0.dart index 496015fea8..5f4925ff34 100644 --- a/examples/api/lib/widgets/scroll_position/scroll_metrics_notification.0.dart +++ b/examples/api/lib/widgets/scroll_position/scroll_metrics_notification.0.dart @@ -41,7 +41,7 @@ class ScrollMetricsDemoState extends State { return false; }, child: Scrollbar( - isAlwaysShown: true, + thumbVisibility: true, child: SizedBox( height: windowSize, width: double.infinity, diff --git a/examples/api/lib/widgets/scrollbar/raw_scrollbar.0.dart b/examples/api/lib/widgets/scrollbar/raw_scrollbar.0.dart index 0d5bdcfb62..1c2c20117b 100644 --- a/examples/api/lib/widgets/scrollbar/raw_scrollbar.0.dart +++ b/examples/api/lib/widgets/scrollbar/raw_scrollbar.0.dart @@ -50,7 +50,7 @@ class _MyStatefulWidgetState extends State { // unique scroll controller to this scroll view prevents it // from attaching to the PrimaryScrollController. child: Scrollbar( - isAlwaysShown: true, + thumbVisibility: true, controller: _firstController, child: ListView.builder( controller: _firstController, @@ -68,7 +68,7 @@ class _MyStatefulWidgetState extends State { // ScrollController, so it is using the // PrimaryScrollController. child: Scrollbar( - isAlwaysShown: true, + thumbVisibility: true, child: ListView.builder( itemCount: 100, itemBuilder: (BuildContext context, int index) { diff --git a/examples/api/lib/widgets/scrollbar/raw_scrollbar.2.dart b/examples/api/lib/widgets/scrollbar/raw_scrollbar.2.dart index 8e9debd94a..40784c69ca 100644 --- a/examples/api/lib/widgets/scrollbar/raw_scrollbar.2.dart +++ b/examples/api/lib/widgets/scrollbar/raw_scrollbar.2.dart @@ -39,7 +39,7 @@ class _MyStatefulWidgetState extends State { Widget build(BuildContext context) { return RawScrollbar( controller: _controllerOne, - isAlwaysShown: true, + thumbVisibility: true, child: GridView.builder( controller: _controllerOne, itemCount: 120, diff --git a/examples/api/lib/widgets/scrollbar/raw_scrollbar.shape.0.dart b/examples/api/lib/widgets/scrollbar/raw_scrollbar.shape.0.dart index f6355694f3..32a7a35db4 100644 --- a/examples/api/lib/widgets/scrollbar/raw_scrollbar.shape.0.dart +++ b/examples/api/lib/widgets/scrollbar/raw_scrollbar.shape.0.dart @@ -33,7 +33,7 @@ class MyStatelessWidget extends StatelessWidget { side: BorderSide(color: Colors.brown, width: 3.0)), thickness: 15.0, thumbColor: Colors.blue, - isAlwaysShown: true, + thumbVisibility: true, child: ListView( physics: const BouncingScrollPhysics(), children: List.generate( diff --git a/packages/flutter/lib/fix_data.yaml b/packages/flutter/lib/fix_data.yaml index 255e62085e..953844bfcb 100644 --- a/packages/flutter/lib/fix_data.yaml +++ b/packages/flutter/lib/fix_data.yaml @@ -14,6 +14,110 @@ version: 1 transforms: + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'cupertino.dart' ] + field: 'isAlwaysShown' + inClass: 'CupertinoScrollbar' + changes: + - kind: 'rename' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'cupertino.dart' ] + constructor: '' + inClass: 'CupertinoScrollbar' + changes: + - kind: 'renameParameter' + oldName: 'isAlwaysShown' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart' ] + field: 'isAlwaysShown' + inClass: 'Scrollbar' + changes: + - kind: 'rename' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart' ] + constructor: '' + inClass: 'Scrollbar' + changes: + - kind: 'renameParameter' + oldName: 'isAlwaysShown' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart' ] + field: 'isAlwaysShown' + inClass: 'ScrollbarThemeData' + changes: + - kind: 'rename' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart' ] + constructor: '' + inClass: 'ScrollbarThemeData' + changes: + - kind: 'renameParameter' + oldName: 'isAlwaysShown' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart' ] + method: 'copyWith' + inClass: 'ScrollbarThemeData' + changes: + - kind: 'renameParameter' + oldName: 'isAlwaysShown' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart', 'widgets.dart', 'cupertino.dart' ] + field: 'isAlwaysShown' + inClass: 'RawScrollbar' + changes: + - kind: 'rename' + newName: 'thumbVisibility' + + # Changes made in https://github.com/flutter/flutter/pull/96957 + - title: "Migrate to 'thumbVisibility'" + date: 2022-01-20 + element: + uris: [ 'material.dart', 'widgets.dart', 'cupertino.dart' ] + constructor: '' + inClass: 'RawScrollbar' + changes: + - kind: 'renameParameter' + oldName: 'isAlwaysShown' + newName: 'thumbVisibility' + # Changes made in https://github.com/flutter/flutter/pull/96115 - title: "Migrate 'Icons.pie_chart_outlined' to 'Icons.pie_chart_outline'" date: 2022-01-04 diff --git a/packages/flutter/lib/src/cupertino/scrollbar.dart b/packages/flutter/lib/src/cupertino/scrollbar.dart index 30dfa519ad..8f6607562d 100644 --- a/packages/flutter/lib/src/cupertino/scrollbar.dart +++ b/packages/flutter/lib/src/cupertino/scrollbar.dart @@ -51,9 +51,10 @@ const double _kScrollbarCrossAxisMargin = 3.0; /// {@end-tool} /// /// {@tool dartpad} -/// When `isAlwaysShown` is true, the scrollbar thumb will remain visible without the +/// When [thumbVisibility] is true, the scrollbar thumb will remain visible without the /// fade animation. This requires that a [ScrollController] is provided to controller, -/// or that the [PrimaryScrollController] is available. +/// or that the [PrimaryScrollController] is available. [isAlwaysShown] is +/// deprecated in favor of `thumbVisibility`. /// /// ** See code in examples/api/lib/cupertino/scrollbar/cupertino_scrollbar.1.dart ** /// {@end-tool} @@ -74,24 +75,34 @@ class CupertinoScrollbar extends RawScrollbar { Key? key, required Widget child, ScrollController? controller, - bool isAlwaysShown = false, + bool? thumbVisibility, double thickness = defaultThickness, this.thicknessWhileDragging = defaultThicknessWhileDragging, Radius radius = defaultRadius, this.radiusWhileDragging = defaultRadiusWhileDragging, ScrollNotificationPredicate? notificationPredicate, ScrollbarOrientation? scrollbarOrientation, + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) + bool? isAlwaysShown, }) : assert(thickness != null), assert(thickness < double.infinity), assert(thicknessWhileDragging != null), assert(thicknessWhileDragging < double.infinity), assert(radius != null), assert(radiusWhileDragging != null), + assert( + isAlwaysShown == null || thumbVisibility == null, + 'Scrollbar thumb appearance should only be controlled with thumbVisibility, ' + 'isAlwaysShown is deprecated.' + ), super( key: key, child: child, controller: controller, - isAlwaysShown: isAlwaysShown, + thumbVisibility: isAlwaysShown ?? thumbVisibility ?? false, thickness: thickness, radius: radius, fadeDuration: _kScrollbarFadeDuration, diff --git a/packages/flutter/lib/src/material/dropdown.dart b/packages/flutter/lib/src/material/dropdown.dart index 88fcda234e..76e13ede7a 100644 --- a/packages/flutter/lib/src/material/dropdown.dart +++ b/packages/flutter/lib/src/material/dropdown.dart @@ -303,7 +303,7 @@ class _DropdownMenuState extends State<_DropdownMenu> { child: PrimaryScrollController( controller: widget.route.scrollController!, child: Scrollbar( - isAlwaysShown: true, + thumbVisibility: true, child: ListView( padding: kMaterialListPadding, shrinkWrap: true, diff --git a/packages/flutter/lib/src/material/scrollbar.dart b/packages/flutter/lib/src/material/scrollbar.dart index 98aac54e88..76359e4de3 100644 --- a/packages/flutter/lib/src/material/scrollbar.dart +++ b/packages/flutter/lib/src/material/scrollbar.dart @@ -27,26 +27,30 @@ const Duration _kScrollbarTimeToFade = Duration(milliseconds: 600); /// /// {@macro flutter.widgets.Scrollbar} /// -/// Dynamically changes to an iOS style scrollbar that looks like -/// [CupertinoScrollbar] on the iOS platform. +/// Dynamically changes to a [CupertinoScrollbar], an iOS style scrollbar, by +/// default on the iOS platform. /// -/// The color of the Scrollbar will change when dragged. A hover animation is -/// also triggered when used on web and desktop platforms. A scrollbar track -/// can also been drawn when triggered by a hover event, which is controlled by -/// [showTrackOnHover]. The thickness of the track and scrollbar thumb will -/// become larger when hovering, unless overridden by [hoverThickness]. +/// The color of the Scrollbar thumb will change when [MaterialState.dragged], +/// or [MaterialState.hovered] on desktop and web platforms. These stateful +/// color choices can be changed using [ScrollbarThemeData.thumbColor]. +/// +/// A scrollbar track can been drawn when triggered by a hover event, which is +/// controlled by [showTrackOnHover]. The thickness of the track and scrollbar +/// thumb will become larger when hovering, unless overridden by +/// [hoverThickness]. /// /// {@tool dartpad} -/// This sample shows a [Scrollbar] that executes a fade animation as scrolling occurs. -/// The Scrollbar will fade into view as the user scrolls, and fade out when scrolling stops. +/// This sample shows a [Scrollbar] that executes a fade animation as scrolling +/// occurs. The Scrollbar will fade into view as the user scrolls, and fade out +/// when scrolling stops. /// /// ** See code in examples/api/lib/material/scrollbar/scrollbar.0.dart ** /// {@end-tool} /// /// {@tool dartpad} -/// When isAlwaysShown is true, the scrollbar thumb will remain visible without the -/// fade animation. This requires that a ScrollController is provided to controller, -/// or that the PrimaryScrollController is available. +/// When [thumbVisibility] is true, the scrollbar thumb will remain visible +/// without the fade animation. This requires that a [ScrollController] is +/// provided to controller, or that the [PrimaryScrollController] is available. /// /// ** See code in examples/api/lib/material/scrollbar/scrollbar.1.dart ** /// {@end-tool} @@ -78,7 +82,7 @@ class Scrollbar extends StatelessWidget { Key? key, required this.child, this.controller, - this.isAlwaysShown, + this.thumbVisibility, this.trackVisibility, this.showTrackOnHover, this.hoverThickness, @@ -87,7 +91,17 @@ class Scrollbar extends StatelessWidget { this.notificationPredicate, this.interactive, this.scrollbarOrientation, - }) : super(key: key); + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) + this.isAlwaysShown, + }) : assert( + thumbVisibility == null || isAlwaysShown == null, + 'Scrollbar thumb appearance should only be controlled with thumbVisibility, ' + 'isAlwaysShown is deprecated.' + ), + super(key: key); /// {@macro flutter.widgets.Scrollbar.child} final Widget child; @@ -95,7 +109,27 @@ class Scrollbar extends StatelessWidget { /// {@macro flutter.widgets.Scrollbar.controller} final ScrollController? controller; + /// {@macro flutter.widgets.Scrollbar.thumbVisibility} + /// + /// If this property is null, then [ScrollbarThemeData.thumbVisibility] of + /// [ThemeData.scrollbarTheme] is used. If that is also null, the default value + /// is false. + /// + /// If the thumb visibility is related to the scrollbar's material state, + /// use the global [ScrollbarThemeData.thumbVisibility] or override the + /// sub-tree's theme data. + /// + /// Replaces deprecated [isAlwaysShown]. + final bool? thumbVisibility; + /// {@macro flutter.widgets.Scrollbar.isAlwaysShown} + /// + /// To show the scrollbar thumb based on a [MaterialState], use + /// [ScrollbarThemeData.thumbVisibility]. + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) final bool? isAlwaysShown; /// Controls the track visibility. @@ -157,7 +191,7 @@ class Scrollbar extends StatelessWidget { Widget build(BuildContext context) { if (Theme.of(context).platform == TargetPlatform.iOS) { return CupertinoScrollbar( - isAlwaysShown: isAlwaysShown ?? false, + thumbVisibility: isAlwaysShown ?? thumbVisibility ?? false, thickness: thickness ?? CupertinoScrollbar.defaultThickness, thicknessWhileDragging: thickness ?? CupertinoScrollbar.defaultThicknessWhileDragging, radius: radius ?? CupertinoScrollbar.defaultRadius, @@ -170,7 +204,7 @@ class Scrollbar extends StatelessWidget { } return _MaterialScrollbar( controller: controller, - isAlwaysShown: isAlwaysShown, + thumbVisibility: isAlwaysShown ?? thumbVisibility, trackVisibility: trackVisibility, showTrackOnHover: showTrackOnHover, hoverThickness: hoverThickness, @@ -189,7 +223,7 @@ class _MaterialScrollbar extends RawScrollbar { Key? key, required Widget child, ScrollController? controller, - bool? isAlwaysShown, + bool? thumbVisibility, this.trackVisibility, this.showTrackOnHover, this.hoverThickness, @@ -202,7 +236,7 @@ class _MaterialScrollbar extends RawScrollbar { key: key, child: child, controller: controller, - isAlwaysShown: isAlwaysShown, + thumbVisibility: thumbVisibility, thickness: thickness, radius: radius, fadeDuration: _kScrollbarFadeDuration, @@ -231,7 +265,7 @@ class _MaterialScrollbarState extends RawScrollbarState<_MaterialScrollbar> { late bool _useAndroidScrollbar; @override - bool get showScrollbar => widget.isAlwaysShown ?? _scrollbarTheme.isAlwaysShown ?? false; + bool get showScrollbar => widget.thumbVisibility ?? _scrollbarTheme.thumbVisibility?.resolve(_states) ?? _scrollbarTheme.isAlwaysShown ?? false; @override bool get enableGestures => widget.interactive ?? _scrollbarTheme.interactive ?? !_useAndroidScrollbar; diff --git a/packages/flutter/lib/src/material/scrollbar_theme.dart b/packages/flutter/lib/src/material/scrollbar_theme.dart index b16b3bf074..d6e70e6641 100644 --- a/packages/flutter/lib/src/material/scrollbar_theme.dart +++ b/packages/flutter/lib/src/material/scrollbar_theme.dart @@ -13,15 +13,15 @@ import 'theme.dart'; /// Defines default property values for descendant [Scrollbar] widgets. /// /// Descendant widgets obtain the current [ScrollbarThemeData] object with -/// `ScrollbarTheme.of(context)`. Instances of [ScrollbarThemeData] can be customized -/// with [ScrollbarThemeData.copyWith]. +/// `ScrollbarTheme.of(context)`. Instances of [ScrollbarThemeData] can be +/// customized with [ScrollbarThemeData.copyWith]. /// -/// Typically the [ScrollbarThemeData] of a [ScrollbarTheme] is specified as part of the overall -/// [Theme] with [ThemeData.scrollbarTheme]. +/// Typically the [ScrollbarThemeData] of a [ScrollbarTheme] is specified as +/// part of the overall [Theme] with [ThemeData.scrollbarTheme]. /// -/// All [ScrollbarThemeData] properties are `null` by default. When null, the [Scrollbar] -/// computes its own default values, typically based on the overall theme's -/// [ThemeData.colorScheme]. +/// All [ScrollbarThemeData] properties are `null` by default. When null, the +/// [Scrollbar] computes its own default values, typically based on the overall +/// theme's [ThemeData.colorScheme]. /// /// See also: /// @@ -31,10 +31,10 @@ import 'theme.dart'; class ScrollbarThemeData with Diagnosticable { /// Creates a theme that can be used for [ThemeData.scrollbarTheme]. const ScrollbarThemeData({ + this.thumbVisibility, this.thickness, this.trackVisibility, this.showTrackOnHover, - this.isAlwaysShown, this.radius, this.thumbColor, this.trackColor, @@ -43,7 +43,22 @@ class ScrollbarThemeData with Diagnosticable { this.mainAxisMargin, this.minThumbLength, this.interactive, - }); + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) + this.isAlwaysShown, + }) : assert( + isAlwaysShown == null || thumbVisibility == null, + 'Scrollbar thumb appearance should only be controlled with thumbVisibility, ' + 'isAlwaysShown is deprecated.' + ); + + /// Overrides the default value of [Scrollbar.thumbVisibility] in all + /// descendant [Scrollbar] widgets. + /// + /// Replaces deprecated [isAlwaysShown]. + final MaterialStateProperty? thumbVisibility; /// Overrides the default value of [Scrollbar.thickness] in all /// descendant [Scrollbar] widgets. @@ -62,6 +77,12 @@ class ScrollbarThemeData with Diagnosticable { /// Overrides the default value of [Scrollbar.isAlwaysShown] in all /// descendant [Scrollbar] widgets. + /// + /// Deprecated in favor of [thumbVisibility]. + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) final bool? isAlwaysShown; /// Overrides the default value of [Scrollbar.interactive] in all @@ -126,10 +147,10 @@ class ScrollbarThemeData with Diagnosticable { /// Creates a copy of this object with the given fields replaced with the /// new values. ScrollbarThemeData copyWith({ + MaterialStateProperty? thumbVisibility, MaterialStateProperty? thickness, MaterialStateProperty? trackVisibility, bool? showTrackOnHover, - bool? isAlwaysShown, bool? interactive, Radius? radius, MaterialStateProperty? thumbColor, @@ -138,8 +159,14 @@ class ScrollbarThemeData with Diagnosticable { double? crossAxisMargin, double? mainAxisMargin, double? minThumbLength, + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) + bool? isAlwaysShown, }) { return ScrollbarThemeData( + thumbVisibility: thumbVisibility ?? this.thumbVisibility, thickness: thickness ?? this.thickness, trackVisibility: trackVisibility ?? this.trackVisibility, showTrackOnHover: showTrackOnHover ?? this.showTrackOnHover, @@ -163,6 +190,7 @@ class ScrollbarThemeData with Diagnosticable { static ScrollbarThemeData lerp(ScrollbarThemeData? a, ScrollbarThemeData? b, double t) { assert(t != null); return ScrollbarThemeData( + thumbVisibility: _lerpProperties(a?.thumbVisibility, b?.thumbVisibility, t, _lerpBool), thickness: _lerpProperties(a?.thickness, b?.thickness, t, lerpDouble), trackVisibility: _lerpProperties(a?.trackVisibility, b?.trackVisibility, t, _lerpBool), showTrackOnHover: _lerpBool(a?.showTrackOnHover, b?.showTrackOnHover, t), @@ -181,6 +209,7 @@ class ScrollbarThemeData with Diagnosticable { @override int get hashCode { return hashValues( + thumbVisibility, thickness, trackVisibility, showTrackOnHover, @@ -203,6 +232,7 @@ class ScrollbarThemeData with Diagnosticable { if (other.runtimeType != runtimeType) return false; return other is ScrollbarThemeData + && other.thumbVisibility == thumbVisibility && other.thickness == thickness && other.trackVisibility == trackVisibility && other.showTrackOnHover == showTrackOnHover @@ -220,6 +250,7 @@ class ScrollbarThemeData with Diagnosticable { @override void debugFillProperties(DiagnosticPropertiesBuilder properties) { super.debugFillProperties(properties); + properties.add(DiagnosticsProperty>('thumbVisibility', thumbVisibility, defaultValue: null)); properties.add(DiagnosticsProperty>('thickness', thickness, defaultValue: null)); properties.add(DiagnosticsProperty>('trackVisibility', trackVisibility, defaultValue: null)); properties.add(DiagnosticsProperty('showTrackOnHover', showTrackOnHover, defaultValue: null)); diff --git a/packages/flutter/lib/src/widgets/scrollbar.dart b/packages/flutter/lib/src/widgets/scrollbar.dart index 488e36df0d..57b4c98e9c 100644 --- a/packages/flutter/lib/src/widgets/scrollbar.dart +++ b/packages/flutter/lib/src/widgets/scrollbar.dart @@ -767,7 +767,7 @@ class ScrollbarPainter extends ChangeNotifier implements CustomPainter { /// visible. /// /// By default, the thumb will fade in and out as the child scroll view -/// scrolls. When [isAlwaysShown] is true, the scrollbar thumb will remain +/// scrolls. When [thumbVisibility] is true, the scrollbar thumb will remain /// visible without the fade animation. This requires that the [ScrollController] /// associated with the Scrollable widget is provided to [controller], or that /// the [PrimaryScrollController] is being used by that Scrollable widget. @@ -843,7 +843,7 @@ class ScrollbarPainter extends ChangeNotifier implements CustomPainter { /// {@end-tool} /// /// {@tool dartpad} -/// When `isAlwaysShown` is true, the scrollbar thumb will remain visible without +/// When `thumbVisibility` is true, the scrollbar thumb will remain visible without /// the fade animation. This requires that a [ScrollController] is provided to /// `controller` for both the [RawScrollbar] and the [GridView]. /// Alternatively, the [PrimaryScrollController] can be used automatically so long @@ -868,7 +868,7 @@ class RawScrollbar extends StatefulWidget { Key? key, required this.child, this.controller, - this.isAlwaysShown, + this.thumbVisibility, this.shape, this.radius, this.thickness, @@ -882,8 +882,18 @@ class RawScrollbar extends StatefulWidget { this.interactive, this.scrollbarOrientation, this.mainAxisMargin = 0.0, - this.crossAxisMargin = 0.0 + this.crossAxisMargin = 0.0, + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) + this.isAlwaysShown, }) : assert(child != null), + assert( + thumbVisibility == null || isAlwaysShown == null, + 'Scrollbar thumb appearance should only be controlled with thumbVisibility, ' + 'isAlwaysShown is deprecated.' + ), assert(minThumbLength != null), assert(minThumbLength >= 0), assert(minOverscrollLength == null || minOverscrollLength <= minThumbLength), @@ -962,9 +972,9 @@ class RawScrollbar extends StatefulWidget { /// {@endtemplate} final ScrollController? controller; - /// {@template flutter.widgets.Scrollbar.isAlwaysShown} - /// Indicates that the scrollbar should be visible, even when a scroll is not - /// underway. + /// {@template flutter.widgets.Scrollbar.thumbVisibility} + /// Indicates that the scrollbar thumb should be visible, even when a scroll + /// is not underway. /// /// When false, the scrollbar will be shown during scrolling /// and will fade out otherwise. @@ -996,7 +1006,7 @@ class RawScrollbar extends StatefulWidget { /// SizedBox( /// height: 200, /// child: Scrollbar( - /// isAlwaysShown: true, + /// thumbVisibility: true, /// controller: _controllerOne, /// child: ListView.builder( /// controller: _controllerOne, @@ -1010,7 +1020,7 @@ class RawScrollbar extends StatefulWidget { /// SizedBox( /// height: 200, /// child: CupertinoScrollbar( - /// isAlwaysShown: true, + /// thumbVisibility: true, /// controller: _controllerTwo, /// child: SingleChildScrollView( /// controller: _controllerTwo, @@ -1036,7 +1046,95 @@ class RawScrollbar extends StatefulWidget { /// scroll view associated with the parent [PrimaryScrollController]. /// * [PrimaryScrollController], which associates a [ScrollController] with /// a subtree. + /// + /// Replaces deprecated [isAlwaysShown]. /// {@endtemplate} + /// + /// Subclass [Scrollbar] can hide and show the scrollbar thumb in response to + /// [MaterialState]s by using [ScrollbarThemeData.thumbVisibility]. + final bool? thumbVisibility; + + /// {@template flutter.widgets.Scrollbar.isAlwaysShown} + /// Indicates that the scrollbar thumb should be visible, even when a scroll + /// is not underway. + /// + /// When false, the scrollbar will be shown during scrolling + /// and will fade out otherwise. + /// + /// When true, the scrollbar will always be visible and never fade out. This + /// requires that the Scrollbar can access the [ScrollController] of the + /// associated Scrollable widget. This can either be the provided [controller], + /// or the [PrimaryScrollController] of the current context. + /// + /// * When providing a controller, the same ScrollController must also be + /// provided to the associated Scrollable widget. + /// * The [PrimaryScrollController] is used by default for a [ScrollView] + /// that has not been provided a [ScrollController] and that has an + /// [Axis.vertical] [ScrollDirection]. This automatic behavior does not + /// apply to those with a ScrollDirection of Axis.horizontal. To explicitly + /// use the PrimaryScrollController, set [ScrollView.primary] to true. + /// + /// Defaults to false when null. + /// + /// {@tool snippet} + /// + /// ```dart + /// final ScrollController _controllerOne = ScrollController(); + /// final ScrollController _controllerTwo = ScrollController(); + /// + /// Widget build(BuildContext context) { + /// return Column( + /// children: [ + /// SizedBox( + /// height: 200, + /// child: Scrollbar( + /// thumbVisibility: true, + /// controller: _controllerOne, + /// child: ListView.builder( + /// controller: _controllerOne, + /// itemCount: 120, + /// itemBuilder: (BuildContext context, int index) { + /// return Text('item $index'); + /// }, + /// ), + /// ), + /// ), + /// SizedBox( + /// height: 200, + /// child: CupertinoScrollbar( + /// thumbVisibility: true, + /// controller: _controllerTwo, + /// child: SingleChildScrollView( + /// controller: _controllerTwo, + /// child: const SizedBox( + /// height: 2000, + /// width: 500, + /// child: Placeholder(), + /// ), + /// ), + /// ), + /// ), + /// ], + /// ); + /// } + /// ``` + /// {@end-tool} + /// + /// See also: + /// + /// * [RawScrollbarState.showScrollbar], an overridable getter which uses + /// this value to override the default behavior. + /// * [ScrollView.primary], which indicates whether the ScrollView is the primary + /// scroll view associated with the parent [PrimaryScrollController]. + /// * [PrimaryScrollController], which associates a [ScrollController] with + /// a subtree. + /// + /// This is deprecated, [thumbVisibility] should be used instead. + /// {@endtemplate} + @Deprecated( + 'Use thumbVisibility instead. ' + 'This feature was deprecated after v2.9.0-1.0.pre.', + ) final bool? isAlwaysShown; /// The [OutlinedBorder] of the scrollbar's thumb. @@ -1197,13 +1295,14 @@ class RawScrollbarState extends State with TickerProv /// Subclasses can override this getter to make its value depend on an inherited /// theme. /// - /// Defaults to false when [RawScrollbar.isAlwaysShown] is null. + /// Defaults to false when [RawScrollbar.isAlwaysShown] or + /// [RawScrollbar.thumbVisibility] is null. /// /// See also: /// /// * [RawScrollbar.isAlwaysShown], which overrides the default behavior. @protected - bool get showScrollbar => widget.isAlwaysShown ?? false; + bool get showScrollbar => widget.isAlwaysShown ?? widget.thumbVisibility ?? false; /// Overridable getter to indicate is gestures should be enabled on the /// scrollbar. @@ -1283,8 +1382,10 @@ class RawScrollbarState extends State with TickerProv : 'provided ScrollController'; String when = ''; - if (showScrollbar) { + if (widget.isAlwaysShown ?? false) { when = 'Scrollbar.isAlwaysShown is true'; + } else if (widget.thumbVisibility ?? false) { + when = 'Scrollbar.thumbVisibility is true'; } else if (enableGestures) { when = 'the scrollbar is interactive'; } else { @@ -1385,8 +1486,9 @@ class RawScrollbarState extends State with TickerProv @override void didUpdateWidget(T oldWidget) { super.didUpdateWidget(oldWidget); - if (widget.isAlwaysShown != oldWidget.isAlwaysShown) { - if (widget.isAlwaysShown == true) { + if (widget.isAlwaysShown != oldWidget.isAlwaysShown + || widget.thumbVisibility != oldWidget.thumbVisibility) { + if (widget.isAlwaysShown == true || widget.thumbVisibility == true) { assert(_debugScheduleCheckHasValidScrollPosition()); _fadeoutTimer?.cancel(); _fadeoutAnimationController.animateTo(1.0); diff --git a/packages/flutter/test/cupertino/scrollbar_test.dart b/packages/flutter/test/cupertino/scrollbar_test.dart index 5e1f0efc9c..33b250088d 100644 --- a/packages/flutter/test/cupertino/scrollbar_test.dart +++ b/packages/flutter/test/cupertino/scrollbar_test.dart @@ -340,9 +340,66 @@ void main() { await tester.pump(kScrollbarFadeDuration); }); - testWidgets( - 'When isAlwaysShown is true, must pass a controller or find PrimaryScrollController', - (WidgetTester tester) async { + testWidgets('When thumbVisibility is true, must pass a controller or find PrimaryScrollController', (WidgetTester tester) async { + Widget viewWithScroll() { + return const Directionality( + textDirection: TextDirection.ltr, + child: MediaQuery( + data: MediaQueryData(), + child: CupertinoScrollbar( + thumbVisibility: true, + child: SingleChildScrollView( + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + final AssertionError exception = tester.takeException() as AssertionError; + expect(exception, isAssertionError); + }, + ); + + testWidgets('When thumbVisibility is true, must pass a controller or find PrimaryScrollController that is attached to a scroll view', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return Directionality( + textDirection: TextDirection.ltr, + child: MediaQuery( + data: const MediaQueryData(), + child: CupertinoScrollbar( + controller: controller, + thumbVisibility: true, + child: const SingleChildScrollView( + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ); + } + + final FlutterExceptionHandler? handler = FlutterError.onError; + FlutterErrorDetails? error; + FlutterError.onError = (FlutterErrorDetails details) { + error = details; + }; + + await tester.pumpWidget(viewWithScroll()); + expect(error, isNotNull); + + FlutterError.onError = handler; + }, + ); + + testWidgets('When isAlwaysShown is true, must pass a controller or find PrimaryScrollController', (WidgetTester tester) async { Widget viewWithScroll() { return const Directionality( textDirection: TextDirection.ltr, @@ -367,10 +424,7 @@ void main() { }, ); - testWidgets( - 'When isAlwaysShown is true, ' - 'must pass a controller or find PrimaryScrollController that is attached to a scroll view', - (WidgetTester tester) async { + testWidgets('When isAlwaysShown is true, must pass a controller or find PrimaryScrollController that is attached to a scroll view', (WidgetTester tester) async { final ScrollController controller = ScrollController(); Widget viewWithScroll() { return Directionality( @@ -404,9 +458,74 @@ void main() { }, ); - testWidgets( - 'On first render with isAlwaysShown: true, the thumb shows with PrimaryScrollController', - (WidgetTester tester) async { + testWidgets('On first render with thumbVisibility: true, the thumb shows with PrimaryScrollController', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return Directionality( + textDirection: TextDirection.ltr, + child: MediaQuery( + data: const MediaQueryData(), + child: PrimaryScrollController( + controller: controller, + child: Builder( + builder: (BuildContext context) { + return const CupertinoScrollbar( + thumbVisibility: true, + child: SingleChildScrollView( + primary: true, + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ); + }, + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + await tester.pumpAndSettle(); + expect(find.byType(CupertinoScrollbar), paints..rect()); + }, + ); + + testWidgets('On first render with thumbVisibility: true, the thumb shows', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return Directionality( + textDirection: TextDirection.ltr, + child: MediaQuery( + data: const MediaQueryData(), + child: PrimaryScrollController( + controller: controller, + child: CupertinoScrollbar( + thumbVisibility: true, + controller: controller, + child: const SingleChildScrollView( + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + // The scrollbar measures its size on the first frame + // and renders starting in the second, + // + // so pumpAndSettle a frame to allow it to appear. + await tester.pumpAndSettle(); + expect(find.byType(CupertinoScrollbar), paints..rrect()); + }); + + testWidgets('On first render with isAlwaysShown: true, the thumb shows with PrimaryScrollController', (WidgetTester tester) async { final ScrollController controller = ScrollController(); Widget viewWithScroll() { return Directionality( @@ -501,9 +620,7 @@ void main() { expect(find.byType(CupertinoScrollbar), isNot(paints..rect())); }); - testWidgets( - 'With isAlwaysShown: true, fling a scroll. While it is still scrolling, set isAlwaysShown: false. The thumb should not fade out until the scrolling stops.', - (WidgetTester tester) async { + testWidgets('With isAlwaysShown: true, fling a scroll. While it is still scrolling, set isAlwaysShown: false. The thumb should not fade out until the scrolling stops.', (WidgetTester tester) async { final ScrollController controller = ScrollController(); bool isAlwaysShown = true; Widget viewWithScroll() { diff --git a/packages/flutter/test/material/scrollbar_test.dart b/packages/flutter/test/material/scrollbar_test.dart index 5cc72d98d7..cf9db02811 100644 --- a/packages/flutter/test/material/scrollbar_test.dart +++ b/packages/flutter/test/material/scrollbar_test.dart @@ -159,6 +159,112 @@ void main() { expect(canvas.invocations.isEmpty, isTrue); }); + testWidgets('When thumbVisibility is true, must pass a controller or find PrimaryScrollController', (WidgetTester tester) async { + Widget viewWithScroll() { + return _buildBoilerplate( + child: Theme( + data: ThemeData(), + child: const Scrollbar( + thumbVisibility: true, + child: SingleChildScrollView( + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + final AssertionError exception = tester.takeException() as AssertionError; + expect(exception, isAssertionError); + }); + + testWidgets('When thumbVisibility is true, must pass a controller that is attached to a scroll view or find PrimaryScrollController', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return _buildBoilerplate( + child: Theme( + data: ThemeData(), + child: Scrollbar( + thumbVisibility: true, + controller: controller, + child: const SingleChildScrollView( + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + final AssertionError exception = tester.takeException() as AssertionError; + expect(exception, isAssertionError); + }); + + testWidgets('On first render with thumbVisibility: true, the thumb shows', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return _buildBoilerplate( + child: Theme( + data: ThemeData(), + child: Scrollbar( + thumbVisibility: true, + controller: controller, + child: SingleChildScrollView( + controller: controller, + child: const SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + await tester.pumpAndSettle(); + expect(find.byType(Scrollbar), paints..rect()); + }); + + testWidgets('On first render with thumbVisibility: true, the thumb shows with PrimaryScrollController', (WidgetTester tester) async { + final ScrollController controller = ScrollController(); + Widget viewWithScroll() { + return _buildBoilerplate( + child: Theme( + data: ThemeData(), + child: PrimaryScrollController( + controller: controller, + child: Builder( + builder: (BuildContext context) { + return const Scrollbar( + thumbVisibility: true, + child: SingleChildScrollView( + primary: true, + child: SizedBox( + width: 4000.0, + height: 4000.0, + ), + ), + ); + }, + ), + ), + ), + ); + } + + await tester.pumpWidget(viewWithScroll()); + await tester.pumpAndSettle(); + expect(find.byType(Scrollbar), paints..rect()); + }); + testWidgets( 'When isAlwaysShown is true, must pass a controller or find PrimaryScrollController', (WidgetTester tester) async { diff --git a/packages/flutter/test/material/scrollbar_theme_test.dart b/packages/flutter/test/material/scrollbar_theme_test.dart index 1032e32e40..1a876dafe8 100644 --- a/packages/flutter/test/material/scrollbar_theme_test.dart +++ b/packages/flutter/test/material/scrollbar_theme_test.dart @@ -320,7 +320,7 @@ void main() { child: Scrollbar( thickness: thickness, hoverThickness: hoverThickness, - isAlwaysShown: true, + thumbVisibility: true, showTrackOnHover: showTrackOnHover, radius: radius, controller: scrollController, @@ -637,7 +637,7 @@ void main() { ScrollbarThemeData( thickness: MaterialStateProperty.resolveWith(_getThickness), showTrackOnHover: true, - isAlwaysShown: true, + thumbVisibility: MaterialStateProperty.resolveWith(_getThumbVisibility), radius: const Radius.circular(3.0), thumbColor: MaterialStateProperty.resolveWith(_getThumbColor), trackColor: MaterialStateProperty.resolveWith(_getTrackColor), @@ -653,16 +653,16 @@ void main() { .toList(); expect(description, [ + "thumbVisibility: Instance of '_MaterialStatePropertyWith'", "thickness: Instance of '_MaterialStatePropertyWith'", 'showTrackOnHover: true', - 'isAlwaysShown: true', 'radius: Radius.circular(3.0)', "thumbColor: Instance of '_MaterialStatePropertyWith'", "trackColor: Instance of '_MaterialStatePropertyWith'", "trackBorderColor: Instance of '_MaterialStatePropertyWith'", 'crossAxisMargin: 3.0', 'mainAxisMargin: 6.0', - 'minThumbLength: 120.0', + 'minThumbLength: 120.0' ]); // On the web, Dart doubles and ints are backed by the same kind of object because @@ -684,7 +684,7 @@ ScrollbarThemeData _scrollbarTheme({ MaterialStateProperty? thickness, MaterialStateProperty? trackVisibility, bool showTrackOnHover = true, - bool isAlwaysShown = true, + MaterialStateProperty? thumbVisibility, Radius radius = const Radius.circular(6.0), MaterialStateProperty? thumbColor, MaterialStateProperty? trackColor, @@ -697,7 +697,7 @@ ScrollbarThemeData _scrollbarTheme({ thickness: thickness ?? MaterialStateProperty.resolveWith(_getThickness), trackVisibility: trackVisibility, showTrackOnHover: showTrackOnHover, - isAlwaysShown: isAlwaysShown, + thumbVisibility: thumbVisibility, radius: radius, thumbColor: thumbColor ?? MaterialStateProperty.resolveWith(_getThumbColor), trackColor: trackColor ?? MaterialStateProperty.resolveWith(_getTrackColor), @@ -714,6 +714,8 @@ double? _getThickness(Set states) { return 10.0; } +bool? _getThumbVisibility(Set states) => true; + Color? _getThumbColor(Set states) { if (states.contains(MaterialState.dragged)) return Colors.red; diff --git a/packages/flutter/test/widgets/scrollbar_test.dart b/packages/flutter/test/widgets/scrollbar_test.dart index ed724df040..c0e3ccce4d 100644 --- a/packages/flutter/test/widgets/scrollbar_test.dart +++ b/packages/flutter/test/widgets/scrollbar_test.dart @@ -1304,6 +1304,44 @@ void main() { ); }); + testWidgets('RawScrollbar.thumbVisibility asserts that a ScrollPosition is attached', (WidgetTester tester) async { + final FlutterExceptionHandler? handler = FlutterError.onError; + FlutterErrorDetails? error; + FlutterError.onError = (FlutterErrorDetails details) { + error = details; + }; + + await tester.pumpWidget( + Directionality( + textDirection: TextDirection.ltr, + child: MediaQuery( + data: const MediaQueryData(), + child: RawScrollbar( + thumbVisibility: true, + controller: ScrollController(), + thumbColor: const Color(0x11111111), + child: const SingleChildScrollView( + child: SizedBox( + height: 1000.0, + width: 50.0, + ), + ), + ), + ), + ), + ); + await tester.pumpAndSettle(); + + expect(error, isNotNull); + final AssertionError exception = error!.exception as AssertionError; + expect( + exception.message, + contains("The Scrollbar's ScrollController has no ScrollPosition attached."), + ); + + FlutterError.onError = handler; + }); + testWidgets('RawScrollbar.isAlwaysShown asserts that a ScrollPosition is attached', (WidgetTester tester) async { final FlutterExceptionHandler? handler = FlutterError.onError; FlutterErrorDetails? error; diff --git a/packages/flutter/test_fixes/cupertino.dart b/packages/flutter/test_fixes/cupertino.dart index b8cef44190..0d2c899021 100644 --- a/packages/flutter/test_fixes/cupertino.dart +++ b/packages/flutter/test_fixes/cupertino.dart @@ -220,4 +220,10 @@ void main() { OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(leading: true); notification = OverscrollIndicatorNotification(error: ''); notification.disallowGlow(); + + // Changes made in https://github.com/flutter/flutter/pull/96957 + CupertinoScrollbar scrollbar = CupertinoScrollbar(isAlwaysShown: true); + bool nowShowing = scrollbar.isAlwaysShown; + RawScrollbar rawScrollbar = RawScrollbar(isAlwaysShown: true); + nowShowing = rawScrollbar.isAlwaysShown; } diff --git a/packages/flutter/test_fixes/cupertino.dart.expect b/packages/flutter/test_fixes/cupertino.dart.expect index b02b29d3db..2fdbadf96c 100644 --- a/packages/flutter/test_fixes/cupertino.dart.expect +++ b/packages/flutter/test_fixes/cupertino.dart.expect @@ -220,4 +220,10 @@ void main() { OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(leading: true); notification = OverscrollIndicatorNotification(error: ''); notification.disallowIndicator(); + + // Changes made in https://github.com/flutter/flutter/pull/96957 + CupertinoScrollbar scrollbar = CupertinoScrollbar(thumbVisibility: true); + bool nowShowing = scrollbar.thumbVisibility; + RawScrollbar rawScrollbar = RawScrollbar(thumbVisibility: true); + nowShowing = rawScrollbar.thumbVisibility; } diff --git a/packages/flutter/test_fixes/material.dart b/packages/flutter/test_fixes/material.dart index 73c1f71f01..b6d2871664 100644 --- a/packages/flutter/test_fixes/material.dart +++ b/packages/flutter/test_fixes/material.dart @@ -521,4 +521,13 @@ void main() { // Changes made in https://github.com/flutter/flutter/pull/96115 Icon icon = Icons.pie_chart_outlined; + + // Changes made in https://github.com/flutter/flutter/pull/96957 + Scrollbar scrollbar = Scrollbar(isAlwaysShown: true); + bool nowShowing = scrollbar.isAlwaysShown; + ScrollbarThemeData scrollbarTheme = ScrollbarThemeData(isAlwaysShown: nowShowing); + scrollbarTheme.copyWith(isAlwaysShown: nowShowing); + scrollbarTheme.isAlwaysShown; + RawScrollbar rawScrollbar = RawScrollbar(isAlwaysShown: true); + nowShowing = rawScrollbar.isAlwaysShown; } diff --git a/packages/flutter/test_fixes/material.dart.expect b/packages/flutter/test_fixes/material.dart.expect index 2cfc8bf955..3d7188fe04 100644 --- a/packages/flutter/test_fixes/material.dart.expect +++ b/packages/flutter/test_fixes/material.dart.expect @@ -494,4 +494,13 @@ void main() { // Changes made in https://github.com/flutter/flutter/pull/96115 Icon icon = Icons.pie_chart_outline; + + // Changes made in https://github.com/flutter/flutter/pull/96957 + Scrollbar scrollbar = Scrollbar(thumbVisibility: true); + bool nowShowing = scrollbar.thumbVisibility; + ScrollbarThemeData scrollbarTheme = ScrollbarThemeData(thumbVisibility: nowShowing); + scrollbarTheme.copyWith(thumbVisibility: nowShowing); + scrollbarTheme.thumbVisibility; + RawScrollbar rawScrollbar = RawScrollbar(thumbVisibility: true); + nowShowing = rawScrollbar.thumbVisibility; } diff --git a/packages/flutter/test_fixes/widgets.dart b/packages/flutter/test_fixes/widgets.dart index 7da6b52d0b..6b09422912 100644 --- a/packages/flutter/test_fixes/widgets.dart +++ b/packages/flutter/test_fixes/widgets.dart @@ -177,4 +177,8 @@ void main() { final OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(leading: true); final OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(error: ''); notification.disallowGlow(); + + // Changes made in https://github.com/flutter/flutter/pull/96957 + RawScrollbar rawScrollbar = RawScrollbar(isAlwaysShown: true); + nowShowing = rawScrollbar.isAlwaysShown; } diff --git a/packages/flutter/test_fixes/widgets.dart.expect b/packages/flutter/test_fixes/widgets.dart.expect index 1ca2865fac..df80c8883b 100644 --- a/packages/flutter/test_fixes/widgets.dart.expect +++ b/packages/flutter/test_fixes/widgets.dart.expect @@ -177,4 +177,8 @@ void main() { final OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(leading: true); final OverscrollIndicatorNotification notification = OverscrollIndicatorNotification(error: ''); notification.disallowIndicator(); + + // Changes made in https://github.com/flutter/flutter/pull/96957 + RawScrollbar rawScrollbar = RawScrollbar(thumbVisibility: true); + nowShowing = rawScrollbar.thumbVisibility; }