From 999356b776f70132d569a37f13f65333a1bb0779 Mon Sep 17 00:00:00 2001 From: Michael Goderbauer Date: Thu, 22 Dec 2022 13:54:09 -0800 Subject: [PATCH] Remove single-view assumption from ScrollPhysics (#117503) * Remove single-view assumption from ScrollPhysics * fix scrollable_dispose_test.dart * add deprecated method back --- .../lib/demo/animation/home.dart | 16 ++++----- .../widgets/draggable_scrollable_sheet.dart | 8 ++--- .../src/widgets/list_wheel_scroll_view.dart | 13 ++++--- .../lib/src/widgets/nested_scroll_view.dart | 4 +++ .../flutter/lib/src/widgets/page_view.dart | 7 +++- .../lib/src/widgets/scroll_metrics.dart | 10 ++++++ .../lib/src/widgets/scroll_physics.dart | 34 +++++++++++++------ .../lib/src/widgets/scroll_position.dart | 5 +++ .../scroll_position_with_single_context.dart | 2 +- .../flutter/lib/src/widgets/scrollable.dart | 6 ++++ .../flutter/test/material/scrollbar_test.dart | 1 + .../flutter/test/widgets/page_view_test.dart | 1 + .../test/widgets/scroll_physics_test.dart | 29 ++++++++++------ .../widgets/scrollable_animations_test.dart | 4 +-- .../flutter/test/widgets/scrollbar_test.dart | 1 + .../test/widgets/slivers_evil_test.dart | 2 +- 16 files changed, 102 insertions(+), 41 deletions(-) diff --git a/dev/integration_tests/flutter_gallery/lib/demo/animation/home.dart b/dev/integration_tests/flutter_gallery/lib/demo/animation/home.dart index ce08027c61413..593e55db54301 100644 --- a/dev/integration_tests/flutter_gallery/lib/demo/animation/home.dart +++ b/dev/integration_tests/flutter_gallery/lib/demo/animation/home.dart @@ -371,14 +371,14 @@ class _SnappingScrollPhysics extends ClampingScrollPhysics { return _SnappingScrollPhysics(parent: buildParent(ancestor), midScrollOffset: midScrollOffset); } - Simulation _toMidScrollOffsetSimulation(double offset, double dragVelocity) { + Simulation _toMidScrollOffsetSimulation(double offset, double dragVelocity, ScrollMetrics metrics) { final double velocity = math.max(dragVelocity, minFlingVelocity); - return ScrollSpringSimulation(spring, offset, midScrollOffset, velocity, tolerance: tolerance); + return ScrollSpringSimulation(spring, offset, midScrollOffset, velocity, tolerance: toleranceFor(metrics)); } - Simulation _toZeroScrollOffsetSimulation(double offset, double dragVelocity) { + Simulation _toZeroScrollOffsetSimulation(double offset, double dragVelocity, ScrollMetrics metrics) { final double velocity = math.max(dragVelocity, minFlingVelocity); - return ScrollSpringSimulation(spring, offset, 0.0, velocity, tolerance: tolerance); + return ScrollSpringSimulation(spring, offset, 0.0, velocity, tolerance: toleranceFor(metrics)); } @override @@ -396,10 +396,10 @@ class _SnappingScrollPhysics extends ClampingScrollPhysics { return simulation; } if (dragVelocity > 0.0) { - return _toMidScrollOffsetSimulation(offset, dragVelocity); + return _toMidScrollOffsetSimulation(offset, dragVelocity, position); } if (dragVelocity < 0.0) { - return _toZeroScrollOffsetSimulation(offset, dragVelocity); + return _toZeroScrollOffsetSimulation(offset, dragVelocity, position); } } else { // The user ended the drag with little or no velocity. If they @@ -408,10 +408,10 @@ class _SnappingScrollPhysics extends ClampingScrollPhysics { // otherwise snap to zero. final double snapThreshold = midScrollOffset / 2.0; if (offset >= snapThreshold && offset < midScrollOffset) { - return _toMidScrollOffsetSimulation(offset, dragVelocity); + return _toMidScrollOffsetSimulation(offset, dragVelocity, position); } if (offset > 0.0 && offset < snapThreshold) { - return _toZeroScrollOffsetSimulation(offset, dragVelocity); + return _toZeroScrollOffsetSimulation(offset, dragVelocity, position); } } return simulation; diff --git a/packages/flutter/lib/src/widgets/draggable_scrollable_sheet.dart b/packages/flutter/lib/src/widgets/draggable_scrollable_sheet.dart index 7df9c4934dbfe..c2d55783c71f4 100644 --- a/packages/flutter/lib/src/widgets/draggable_scrollable_sheet.dart +++ b/packages/flutter/lib/src/widgets/draggable_scrollable_sheet.dart @@ -902,7 +902,7 @@ class _DraggableScrollableSheetScrollPosition extends ScrollPositionWithSingleCo bool get _isAtSnapSize { return extent.snapSizes.any( (double snapSize) { - return (extent.currentSize - snapSize).abs() <= extent.pixelsToSize(physics.tolerance.distance); + return (extent.currentSize - snapSize).abs() <= extent.pixelsToSize(physics.toleranceFor(this).distance); }, ); } @@ -937,7 +937,7 @@ class _DraggableScrollableSheetScrollPosition extends ScrollPositionWithSingleCo initialVelocity: velocity, pixelSnapSize: extent.pixelSnapSizes, snapAnimationDuration: extent.snapAnimationDuration, - tolerance: physics.tolerance, + tolerance: physics.toleranceFor(this), ); } else { // The iOS bouncing simulation just isn't right here - once we delegate @@ -946,7 +946,7 @@ class _DraggableScrollableSheetScrollPosition extends ScrollPositionWithSingleCo // Run the simulation in terms of pixels, not extent. position: extent.currentPixels, velocity: velocity, - tolerance: physics.tolerance, + tolerance: physics.toleranceFor(this), ); } @@ -965,7 +965,7 @@ class _DraggableScrollableSheetScrollPosition extends ScrollPositionWithSingleCo // Make sure we pass along enough velocity to keep scrolling - otherwise // we just "bounce" off the top making it look like the list doesn't // have more to scroll. - velocity = ballisticController.velocity + (physics.tolerance.velocity * ballisticController.velocity.sign); + velocity = ballisticController.velocity + (physics.toleranceFor(this).velocity * ballisticController.velocity.sign); super.goBallistic(velocity); ballisticController.stop(); } else if (ballisticController.isCompleted) { diff --git a/packages/flutter/lib/src/widgets/list_wheel_scroll_view.dart b/packages/flutter/lib/src/widgets/list_wheel_scroll_view.dart index caff1e9dab87d..8481bf471774d 100644 --- a/packages/flutter/lib/src/widgets/list_wheel_scroll_view.dart +++ b/packages/flutter/lib/src/widgets/list_wheel_scroll_view.dart @@ -316,6 +316,7 @@ class FixedExtentMetrics extends FixedScrollMetrics { required super.viewportDimension, required super.axisDirection, required this.itemIndex, + required super.devicePixelRatio, }); @override @@ -326,6 +327,7 @@ class FixedExtentMetrics extends FixedScrollMetrics { double? viewportDimension, AxisDirection? axisDirection, int? itemIndex, + double? devicePixelRatio, }) { return FixedExtentMetrics( minScrollExtent: minScrollExtent ?? (hasContentDimensions ? this.minScrollExtent : null), @@ -334,6 +336,7 @@ class FixedExtentMetrics extends FixedScrollMetrics { viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, itemIndex: itemIndex ?? this.itemIndex, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, ); } @@ -399,6 +402,7 @@ class _FixedExtentScrollPosition extends ScrollPositionWithSingleContext impleme double? viewportDimension, AxisDirection? axisDirection, int? itemIndex, + double? devicePixelRatio, }) { return FixedExtentMetrics( minScrollExtent: minScrollExtent ?? (hasContentDimensions ? this.minScrollExtent : null), @@ -407,6 +411,7 @@ class _FixedExtentScrollPosition extends ScrollPositionWithSingleContext impleme viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, itemIndex: itemIndex ?? this.itemIndex, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, ); } } @@ -505,8 +510,8 @@ class FixedExtentScrollPhysics extends ScrollPhysics { // Scenario 3: // If there's no velocity and we're already at where we intend to land, // do nothing. - if (velocity.abs() < tolerance.velocity - && (settlingPixels - metrics.pixels).abs() < tolerance.distance) { + if (velocity.abs() < toleranceFor(position).velocity + && (settlingPixels - metrics.pixels).abs() < toleranceFor(position).distance) { return null; } @@ -519,7 +524,7 @@ class FixedExtentScrollPhysics extends ScrollPhysics { metrics.pixels, settlingPixels, velocity, - tolerance: tolerance, + tolerance: toleranceFor(position), ); } @@ -530,7 +535,7 @@ class FixedExtentScrollPhysics extends ScrollPhysics { metrics.pixels, settlingPixels, velocity, - tolerance.velocity * velocity.sign, + toleranceFor(position).velocity * velocity.sign, ); } } diff --git a/packages/flutter/lib/src/widgets/nested_scroll_view.dart b/packages/flutter/lib/src/widgets/nested_scroll_view.dart index 2987b2b04c423..822f59888d6d1 100644 --- a/packages/flutter/lib/src/widgets/nested_scroll_view.dart +++ b/packages/flutter/lib/src/widgets/nested_scroll_view.dart @@ -526,6 +526,7 @@ class _NestedScrollMetrics extends FixedScrollMetrics { required super.pixels, required super.viewportDimension, required super.axisDirection, + required super.devicePixelRatio, required this.minRange, required this.maxRange, required this.correctionOffset, @@ -538,6 +539,7 @@ class _NestedScrollMetrics extends FixedScrollMetrics { double? pixels, double? viewportDimension, AxisDirection? axisDirection, + double? devicePixelRatio, double? minRange, double? maxRange, double? correctionOffset, @@ -548,6 +550,7 @@ class _NestedScrollMetrics extends FixedScrollMetrics { pixels: pixels ?? (hasPixels ? this.pixels : null), viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, minRange: minRange ?? this.minRange, maxRange: maxRange ?? this.maxRange, correctionOffset: correctionOffset ?? this.correctionOffset, @@ -815,6 +818,7 @@ class _NestedScrollCoordinator implements ScrollActivityDelegate, ScrollHoldCont minRange: minRange, maxRange: maxRange, correctionOffset: correctionOffset, + devicePixelRatio: _outerPosition!.devicePixelRatio, ); } diff --git a/packages/flutter/lib/src/widgets/page_view.dart b/packages/flutter/lib/src/widgets/page_view.dart index f8ef1c1cfa649..4ef93eed89090 100644 --- a/packages/flutter/lib/src/widgets/page_view.dart +++ b/packages/flutter/lib/src/widgets/page_view.dart @@ -273,6 +273,7 @@ class PageMetrics extends FixedScrollMetrics { required super.viewportDimension, required super.axisDirection, required this.viewportFraction, + required super.devicePixelRatio, }); @override @@ -283,6 +284,7 @@ class PageMetrics extends FixedScrollMetrics { double? viewportDimension, AxisDirection? axisDirection, double? viewportFraction, + double? devicePixelRatio, }) { return PageMetrics( minScrollExtent: minScrollExtent ?? (hasContentDimensions ? this.minScrollExtent : null), @@ -291,6 +293,7 @@ class PageMetrics extends FixedScrollMetrics { viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, viewportFraction: viewportFraction ?? this.viewportFraction, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, ); } @@ -493,6 +496,7 @@ class _PagePosition extends ScrollPositionWithSingleContext implements PageMetri double? viewportDimension, AxisDirection? axisDirection, double? viewportFraction, + double? devicePixelRatio, }) { return PageMetrics( minScrollExtent: minScrollExtent ?? (hasContentDimensions ? this.minScrollExtent : null), @@ -501,6 +505,7 @@ class _PagePosition extends ScrollPositionWithSingleContext implements PageMetri viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, viewportFraction: viewportFraction ?? this.viewportFraction, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, ); } } @@ -573,7 +578,7 @@ class PageScrollPhysics extends ScrollPhysics { (velocity >= 0.0 && position.pixels >= position.maxScrollExtent)) { return super.createBallisticSimulation(position, velocity); } - final Tolerance tolerance = this.tolerance; + final Tolerance tolerance = toleranceFor(position); final double target = _getTargetPixels(position, tolerance, velocity); if (target != position.pixels) { return ScrollSpringSimulation(spring, position.pixels, target, velocity, tolerance: tolerance); diff --git a/packages/flutter/lib/src/widgets/scroll_metrics.dart b/packages/flutter/lib/src/widgets/scroll_metrics.dart index 10c20da60c46b..ca7cf48ce3cf0 100644 --- a/packages/flutter/lib/src/widgets/scroll_metrics.dart +++ b/packages/flutter/lib/src/widgets/scroll_metrics.dart @@ -46,6 +46,7 @@ mixin ScrollMetrics { double? pixels, double? viewportDimension, AxisDirection? axisDirection, + double? devicePixelRatio, }) { return FixedScrollMetrics( minScrollExtent: minScrollExtent ?? (hasContentDimensions ? this.minScrollExtent : null), @@ -53,6 +54,7 @@ mixin ScrollMetrics { pixels: pixels ?? (hasPixels ? this.pixels : null), viewportDimension: viewportDimension ?? (hasViewportDimension ? this.viewportDimension : null), axisDirection: axisDirection ?? this.axisDirection, + devicePixelRatio: devicePixelRatio ?? this.devicePixelRatio, ); } @@ -124,6 +126,10 @@ mixin ScrollMetrics { /// The quantity of content conceptually "below" the viewport in the scrollable. /// This is the content below the content described by [extentInside]. double get extentAfter => math.max(maxScrollExtent - pixels, 0.0); + + /// The [FlutterView.devicePixelRatio] of the view that the [Scrollable] + /// associated with this metrics object is drawn into. + double get devicePixelRatio; } /// An immutable snapshot of values associated with a [Scrollable] viewport. @@ -137,6 +143,7 @@ class FixedScrollMetrics with ScrollMetrics { required double? pixels, required double? viewportDimension, required this.axisDirection, + required this.devicePixelRatio, }) : _minScrollExtent = minScrollExtent, _maxScrollExtent = maxScrollExtent, _pixels = pixels, @@ -170,6 +177,9 @@ class FixedScrollMetrics with ScrollMetrics { @override final AxisDirection axisDirection; + @override + final double devicePixelRatio; + @override String toString() { return '${objectRuntimeType(this, 'FixedScrollMetrics')}(${extentBefore.toStringAsFixed(1)}..[${extentInside.toStringAsFixed(1)}]..${extentAfter.toStringAsFixed(1)})'; diff --git a/packages/flutter/lib/src/widgets/scroll_physics.dart b/packages/flutter/lib/src/widgets/scroll_physics.dart index d4519035104dd..3c1d259f2bdf5 100644 --- a/packages/flutter/lib/src/widgets/scroll_physics.dart +++ b/packages/flutter/lib/src/widgets/scroll_physics.dart @@ -6,6 +6,7 @@ import 'dart:math' as math; import 'package:flutter/foundation.dart'; import 'package:flutter/gestures.dart'; +import 'package:flutter/painting.dart' show AxisDirection; import 'package:flutter/physics.dart'; import 'binding.dart' show WidgetsBinding; @@ -382,16 +383,29 @@ class ScrollPhysics { /// The spring to use for ballistic simulations. SpringDescription get spring => parent?.spring ?? _kDefaultSpring; - /// The default accuracy to which scrolling is computed. - static final Tolerance _kDefaultTolerance = Tolerance( - // TODO(ianh): Handle the case of the device pixel ratio changing. - // TODO(ianh): Get this from the local MediaQuery not dart:ui's window object. - velocity: 1.0 / (0.050 * WidgetsBinding.instance.window.devicePixelRatio), // logical pixels per second - distance: 1.0 / WidgetsBinding.instance.window.devicePixelRatio, // logical pixels - ); + /// Deprecated. Call [toleranceFor] instead. + @Deprecated( + 'Call toleranceFor instead. ' + 'This feature was deprecated after v3.7.0-13.0.pre.', + ) + Tolerance get tolerance { + return toleranceFor(FixedScrollMetrics( + minScrollExtent: null, + maxScrollExtent: null, + pixels: null, + viewportDimension: null, + axisDirection: AxisDirection.down, + devicePixelRatio: WidgetsBinding.instance.window.devicePixelRatio, + )); + } /// The tolerance to use for ballistic simulations. - Tolerance get tolerance => parent?.tolerance ?? _kDefaultTolerance; + Tolerance toleranceFor(ScrollMetrics metrics) { + return parent?.toleranceFor(metrics) ?? Tolerance( + velocity: 1.0 / (0.050 * metrics.devicePixelRatio), // logical pixels per second + distance: 1.0 / metrics.devicePixelRatio, // logical pixels + ); + } /// The minimum distance an input pointer drag must have moved to /// to be considered a scroll fling gesture. @@ -695,7 +709,7 @@ class BouncingScrollPhysics extends ScrollPhysics { @override Simulation? createBallisticSimulation(ScrollMetrics position, double velocity) { - final Tolerance tolerance = this.tolerance; + final Tolerance tolerance = toleranceFor(position); if (velocity.abs() >= tolerance.velocity || position.outOfRange) { double constantDeceleration; switch (decelerationRate) { @@ -839,7 +853,7 @@ class ClampingScrollPhysics extends ScrollPhysics { @override Simulation? createBallisticSimulation(ScrollMetrics position, double velocity) { - final Tolerance tolerance = this.tolerance; + final Tolerance tolerance = toleranceFor(position); if (position.outOfRange) { double? end; if (position.pixels > position.maxScrollExtent) { diff --git a/packages/flutter/lib/src/widgets/scroll_position.dart b/packages/flutter/lib/src/widgets/scroll_position.dart index db363517c3725..9eb723d23b625 100644 --- a/packages/flutter/lib/src/widgets/scroll_position.dart +++ b/packages/flutter/lib/src/widgets/scroll_position.dart @@ -12,6 +12,7 @@ import 'package:flutter/scheduler.dart'; import 'basic.dart'; import 'framework.dart'; +import 'media_query.dart'; import 'notification_listener.dart'; import 'page_storage.dart'; import 'scroll_activity.dart'; @@ -19,6 +20,7 @@ import 'scroll_context.dart'; import 'scroll_metrics.dart'; import 'scroll_notification.dart'; import 'scroll_physics.dart'; +import 'view.dart'; export 'scroll_activity.dart' show ScrollHoldController; @@ -242,6 +244,9 @@ abstract class ScrollPosition extends ViewportOffset with ScrollMetrics { isScrollingNotifier.value = activity!.isScrolling; } + @override + double get devicePixelRatio => MediaQuery.maybeDevicePixelRatioOf(context.storageContext) ?? View.of(context.storageContext).devicePixelRatio; + /// Update the scroll position ([pixels]) to a given pixel value. /// /// This should only be called by the current [ScrollActivity], either during diff --git a/packages/flutter/lib/src/widgets/scroll_position_with_single_context.dart b/packages/flutter/lib/src/widgets/scroll_position_with_single_context.dart index 86ef6966d8f3e..06e7325f5d21a 100644 --- a/packages/flutter/lib/src/widgets/scroll_position_with_single_context.dart +++ b/packages/flutter/lib/src/widgets/scroll_position_with_single_context.dart @@ -176,7 +176,7 @@ class ScrollPositionWithSingleContext extends ScrollPosition implements ScrollAc required Duration duration, required Curve curve, }) { - if (nearEqual(to, pixels, physics.tolerance.distance)) { + if (nearEqual(to, pixels, physics.toleranceFor(this).distance)) { // Skip the animation, go straight to the position as we are already close. jumpTo(to); return Future.value(); diff --git a/packages/flutter/lib/src/widgets/scrollable.dart b/packages/flutter/lib/src/widgets/scrollable.dart index 5f32d8ffd3183..fca3892d321a7 100644 --- a/packages/flutter/lib/src/widgets/scrollable.dart +++ b/packages/flutter/lib/src/widgets/scrollable.dart @@ -727,6 +727,12 @@ class ScrollableState extends State with TickerProviderStateMixin, R } void _handleDragCancel() { + if (_gestureDetectorKey.currentContext == null) { + // The cancel was caused by the GestureDetector getting disposed, which + // means we will get disposed momentarily as well and shouldn't do + // any work. + return; + } // _hold might be null if the drag started. // _drag might be null if the drag activity ended and called _disposeDrag. assert(_hold == null || _drag == null); diff --git a/packages/flutter/test/material/scrollbar_test.dart b/packages/flutter/test/material/scrollbar_test.dart index eb0aa6811d896..bcf7f7de2b0be 100644 --- a/packages/flutter/test/material/scrollbar_test.dart +++ b/packages/flutter/test/material/scrollbar_test.dart @@ -148,6 +148,7 @@ void main() { pixels: 0.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: tester.binding.window.devicePixelRatio, ); scrollPainter!.update(metrics, AxisDirection.down); diff --git a/packages/flutter/test/widgets/page_view_test.dart b/packages/flutter/test/widgets/page_view_test.dart index 37716e120d387..971422d838374 100644 --- a/packages/flutter/test/widgets/page_view_test.dart +++ b/packages/flutter/test/widgets/page_view_test.dart @@ -1048,6 +1048,7 @@ void main() { viewportDimension: 25.0, axisDirection: AxisDirection.right, viewportFraction: 1.0, + devicePixelRatio: tester.binding.window.devicePixelRatio, ); expect(page.page, 6); final PageMetrics page2 = page.copyWith( diff --git a/packages/flutter/test/widgets/scroll_physics_test.dart b/packages/flutter/test/widgets/scroll_physics_test.dart index 91c42aa937e6a..e24f2e8db2528 100644 --- a/packages/flutter/test/widgets/scroll_physics_test.dart +++ b/packages/flutter/test/widgets/scroll_physics_test.dart @@ -107,6 +107,7 @@ void main() { pixels: 20.0, viewportDimension: 500.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); const BouncingScrollPhysics bounce = BouncingScrollPhysics(); @@ -129,11 +130,12 @@ void main() { test('overscroll is progressively harder', () { final ScrollMetrics lessOverscrolledPosition = FixedScrollMetrics( - minScrollExtent: 0.0, - maxScrollExtent: 1000.0, - pixels: -20.0, - viewportDimension: 100.0, - axisDirection: AxisDirection.down, + minScrollExtent: 0.0, + maxScrollExtent: 1000.0, + pixels: -20.0, + viewportDimension: 100.0, + axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final ScrollMetrics moreOverscrolledPosition = FixedScrollMetrics( @@ -142,6 +144,7 @@ void main() { pixels: -40.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final double lessOverscrollApplied = @@ -170,6 +173,7 @@ void main() { pixels: -20.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final double easingApplied = @@ -186,6 +190,7 @@ void main() { pixels: 300.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); expect( @@ -205,6 +210,7 @@ void main() { pixels: -20.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final double easingApplied = @@ -217,11 +223,12 @@ void main() { test('overscroll a small list and a big list works the same way', () { final ScrollMetrics smallListOverscrolledPosition = FixedScrollMetrics( - minScrollExtent: 0.0, - maxScrollExtent: 10.0, - pixels: -20.0, - viewportDimension: 100.0, - axisDirection: AxisDirection.down, + minScrollExtent: 0.0, + maxScrollExtent: 10.0, + pixels: -20.0, + viewportDimension: 100.0, + axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final ScrollMetrics bigListOverscrolledPosition = FixedScrollMetrics( @@ -230,6 +237,7 @@ void main() { pixels: -20.0, viewportDimension: 100.0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); final double smallListOverscrollApplied = @@ -254,6 +262,7 @@ void main() { maxScrollExtent: 1000, viewportDimension: 0, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); expect(position.pixels, pixels); late FlutterError error; diff --git a/packages/flutter/test/widgets/scrollable_animations_test.dart b/packages/flutter/test/widgets/scrollable_animations_test.dart index 117fceeaeb466..b055f6a635fe8 100644 --- a/packages/flutter/test/widgets/scrollable_animations_test.dart +++ b/packages/flutter/test/widgets/scrollable_animations_test.dart @@ -41,7 +41,7 @@ void main() { expectNoAnimation(); - final double halfTolerance = controller.position.physics.tolerance.distance / 2; + final double halfTolerance = controller.position.physics.toleranceFor(controller.position).distance / 2; expect(halfTolerance, isNonZero); final double targetPosition = controller.position.pixels + halfTolerance; controller.position.animateTo(targetPosition, duration: const Duration(seconds: 10), curve: Curves.linear); @@ -64,7 +64,7 @@ void main() { expectNoAnimation(); - final double doubleTolerance = controller.position.physics.tolerance.distance * 2; + final double doubleTolerance = controller.position.physics.toleranceFor(controller.position).distance * 2; expect(doubleTolerance, isNonZero); final double targetPosition = controller.position.pixels + doubleTolerance; controller.position.animateTo(targetPosition, duration: const Duration(seconds: 10), curve: Curves.linear); diff --git a/packages/flutter/test/widgets/scrollbar_test.dart b/packages/flutter/test/widgets/scrollbar_test.dart index 0d4881afb17be..5e020cf646402 100644 --- a/packages/flutter/test/widgets/scrollbar_test.dart +++ b/packages/flutter/test/widgets/scrollbar_test.dart @@ -83,6 +83,7 @@ void main() { pixels: 0, viewportDimension: 100, axisDirection: AxisDirection.down, + devicePixelRatio: 3.0, ); test( diff --git a/packages/flutter/test/widgets/slivers_evil_test.dart b/packages/flutter/test/widgets/slivers_evil_test.dart index cf88354494a38..2c9aa0ef35366 100644 --- a/packages/flutter/test/widgets/slivers_evil_test.dart +++ b/packages/flutter/test/widgets/slivers_evil_test.dart @@ -53,7 +53,7 @@ class TestScrollPhysics extends ClampingScrollPhysics { } @override - Tolerance get tolerance => const Tolerance(velocity: 20.0, distance: 1.0); + Tolerance toleranceFor(ScrollMetrics metrics) => const Tolerance(velocity: 20.0, distance: 1.0); } void main() {