From c8c37fcc85ea10453d10c02b1dcfa9574180f4a5 Mon Sep 17 00:00:00 2001 From: Chris Bracken Date: Mon, 27 Feb 2017 16:10:57 -0800 Subject: [PATCH] Primary scroll view support for SingleChildScrollView (#8437) --- .../src/widgets/single_child_scroll_view.dart | 11 +++++++++- .../single_child_scroll_view_test.dart | 20 +++++++++++++++++++ 2 files changed, 30 insertions(+), 1 deletion(-) diff --git a/packages/flutter/lib/src/widgets/single_child_scroll_view.dart b/packages/flutter/lib/src/widgets/single_child_scroll_view.dart index 91975d76fe..9bc8047831 100644 --- a/packages/flutter/lib/src/widgets/single_child_scroll_view.dart +++ b/packages/flutter/lib/src/widgets/single_child_scroll_view.dart @@ -8,6 +8,7 @@ import 'package:flutter/rendering.dart'; import 'basic.dart'; import 'framework.dart'; +import 'primary_scroll_controller.dart'; import 'scroll_controller.dart'; import 'scroll_physics.dart'; import 'scrollable.dart'; @@ -42,11 +43,17 @@ class SingleChildScrollView extends StatelessWidget { this.scrollDirection: Axis.vertical, this.reverse: false, this.padding, + this.primary: false, this.physics, this.controller, this.child, }) : super(key: key) { assert(scrollDirection != null); + assert(primary != null); + assert(controller == null || !primary, + 'Primary ScrollViews obtain their ScrollController via inheritance from a PrimaryScrollController widget. ' + 'You cannot both set primary to true and pass an explicit controller.' + ); } final Axis scrollDirection; @@ -57,6 +64,8 @@ class SingleChildScrollView extends StatelessWidget { final ScrollController controller; + final bool primary; + final ScrollPhysics physics; final Widget child; @@ -80,7 +89,7 @@ class SingleChildScrollView extends StatelessWidget { contents = new Padding(padding: padding, child: contents); return new Scrollable( axisDirection: axisDirection, - controller: controller, + controller: controller ?? (primary ? PrimaryScrollController.of(context) : null), physics: physics, viewportBuilder: (BuildContext context, ViewportOffset offset) { return new _SingleChildViewport( diff --git a/packages/flutter/test/widgets/single_child_scroll_view_test.dart b/packages/flutter/test/widgets/single_child_scroll_view_test.dart index b5a640a543..5ae04f25c9 100644 --- a/packages/flutter/test/widgets/single_child_scroll_view_test.dart +++ b/packages/flutter/test/widgets/single_child_scroll_view_test.dart @@ -76,6 +76,26 @@ void main() { expect(scrollable.position, const isInstanceOf()); }); + testWidgets('Sets PrimaryScrollController when primary', (WidgetTester tester) async { + ScrollController primaryScrollController = new ScrollController(); + await tester.pumpWidget(new PrimaryScrollController( + controller: primaryScrollController, + child: new SingleChildScrollView( + primary: true, + child: new Container( + height: 2000.0, + decoration: const BoxDecoration( + backgroundColor: const Color(0xFF00FF00), + ), + ), + ), + )); + + Scrollable scrollable = tester.widget(find.byType(Scrollable)); + expect(scrollable.controller, primaryScrollController); + }); + + testWidgets('Changing scroll controller inside dirty layout builder does not assert', (WidgetTester tester) async { ScrollController controller = new ScrollController();