Commit 2bb94ec9 authored by Adam Barth's avatar Adam Barth Committed by GitHub

Remove most remaining ScrollableList clients (#8048)

parent 8d2dcc3c
......@@ -184,11 +184,12 @@ class _DropdownMenuState<T> extends State<_DropdownMenu<T>> {
textStyle: route.style,
child: new ScrollConfiguration(
delegate: new _DropdownScrollConfigurationDelegate(Theme.of(context).platform),
child: new Scrollbar(
child: new ScrollableList(
scrollableKey: config.route.scrollableKey,
child: new Scrollbar2(
child: new ListView(
controller: config.route.scrollController,
padding: _kMenuVerticalPadding,
itemExtent: _kMenuItemHeight,
shrinkWrap: true,
children: children,
),
),
......@@ -206,7 +207,7 @@ class _DropdownMenuRouteLayout<T> extends SingleChildLayoutDelegate {
Rect get buttonRect => route.buttonRect;
int get selectedIndex => route.selectedIndex;
GlobalKey<ScrollableState> get scrollableKey => route.scrollableKey;
ScrollController get scrollController => route.scrollController;
@override
BoxConstraints getConstraintsForChild(BoxConstraints constraints) {
......@@ -256,7 +257,7 @@ class _DropdownMenuRouteLayout<T> extends SingleChildLayoutDelegate {
SchedulerBinding.instance.addPostFrameCallback((Duration timeStamp) {
// TODO(ianh): Compute and set this during layout instead of being
// lagged by one frame. https://github.com/flutter/flutter/issues/5751
scrollableKey.currentState.scrollTo(scrollOffset);
scrollController.jumpTo(scrollOffset);
});
}
......@@ -299,7 +300,7 @@ class _DropdownRoute<T> extends PopupRoute<_DropdownRouteResult<T>> {
assert(style != null);
}
final GlobalKey<ScrollableState> scrollableKey = new GlobalKey<ScrollableState>(debugLabel: '_DropdownMenu');
final ScrollController scrollController = new ScrollController();
final List<DropdownMenuItem<T>> items;
final Rect buttonRect;
final int selectedIndex;
......@@ -307,8 +308,8 @@ class _DropdownRoute<T> extends PopupRoute<_DropdownRouteResult<T>> {
final ThemeData theme;
final TextStyle style;
// The layout gets this route's scrollableKey so that it can scroll the
/// selected item into position, but only on the initial layout.
// The layout gets this route's scrollController so that it can scroll the
// selected item into position, but only on the initial layout.
bool initialLayout = true;
@override
......
......@@ -63,6 +63,9 @@ class BouncingScrollPhysics extends ScrollPhysics {
return total + delta;
}
@override
double applyBoundaryConditions(ScrollPosition position, double value) => 0.0;
@override
Simulation createBallisticSimulation(ScrollPosition position, double velocity) {
final Tolerance tolerance = this.tolerance;
......
......@@ -8,27 +8,28 @@ import 'package:flutter/widgets.dart';
const List<int> items = const <int>[0, 1, 2, 3, 4, 5];
Widget buildFrame(ViewportAnchor scrollAnchor) {
Widget buildFrame({ bool reverse: false }) {
return new Center(
child: new Container(
height: 50.0,
child: new ScrollableList(
child: new ListView(
itemExtent: 290.0,
scrollDirection: Axis.horizontal,
scrollAnchor: scrollAnchor,
reverse: reverse,
physics: const BouncingScrollPhysics(),
children: items.map((int item) {
return new Container(
child: new Text('$item')
);
})
)
)
}).toList(),
),
),
);
}
void main() {
testWidgets('Drag horizontally with scroll anchor at start', (WidgetTester tester) async {
await tester.pumpWidget(buildFrame(ViewportAnchor.start));
await tester.pumpWidget(buildFrame());
await tester.pump(const Duration(seconds: 1));
await tester.scroll(find.text('1'), const Offset(-300.0, 0.0));
......@@ -116,7 +117,7 @@ void main() {
expect(find.text('5'), findsOneWidget);
await tester.pumpWidget(new Container());
await tester.pumpWidget(buildFrame(ViewportAnchor.start), const Duration(seconds: 1));
await tester.pumpWidget(buildFrame(), const Duration(seconds: 1));
await tester.scroll(find.text('2'), const Offset(-280.0, 0.0));
await tester.pump(const Duration(seconds: 1));
// screen is 800px wide, and has the following items:
......@@ -147,74 +148,74 @@ void main() {
});
testWidgets('Drag horizontally with scroll anchor at end', (WidgetTester tester) async {
await tester.pumpWidget(buildFrame(ViewportAnchor.end));
await tester.pumpWidget(buildFrame(reverse: true));
await tester.pump(const Duration(seconds: 1));
// screen is 800px wide, and has the following items:
// -70..220 = 3
// 220..510 = 4
// 510..800 = 5
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsNothing);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsOneWidget);
// -70..220 = 2
// 220..510 = 1
// 510..800 = 0
expect(find.text('0'), findsOneWidget);
expect(find.text('1'), findsOneWidget);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsNothing);
expect(find.text('4'), findsNothing);
expect(find.text('5'), findsNothing);
await tester.scroll(find.text('5'), const Offset(300.0, 0.0));
await tester.scroll(find.text('0'), const Offset(300.0, 0.0));
await tester.pump(const Duration(seconds: 1));
// screen is 800px wide, and has the following items:
// -80..210 = 2
// 230..520 = 3
// 520..810 = 4
// -80..210 = 3
// 230..520 = 2
// 520..810 = 1
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsNothing);
expect(find.text('1'), findsOneWidget);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsOneWidget);
expect(find.text('4'), findsNothing);
expect(find.text('5'), findsNothing);
// the center of item 3 is visible, so this works;
// if item 3 was a bit wider, such that its center was past the 800px mark, this would fail,
// because it wouldn't be hit tested when scrolling from its center, as scroll() does.
await tester.pump(const Duration(seconds: 1));
await tester.scroll(find.text('3'), const Offset(290.0, 0.0));
await tester.scroll(find.text('2'), const Offset(290.0, 0.0));
await tester.pump(const Duration(seconds: 1));
// screen is 800px wide, and has the following items:
// -10..280 = 1
// 280..570 = 2
// 570..860 = 3
// -10..280 = 4
// 280..570 = 3
// 570..860 = 2
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsOneWidget);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsNothing);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsNothing);
await tester.pump(const Duration(seconds: 1));
await tester.scroll(find.text('3'), const Offset(0.0, 290.0));
await tester.scroll(find.text('2'), const Offset(0.0, 290.0));
await tester.pump(const Duration(seconds: 1));
// unchanged
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsOneWidget);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsNothing);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsNothing);
await tester.pump(const Duration(seconds: 1));
await tester.scroll(find.text('2'), const Offset(290.0, 0.0));
await tester.scroll(find.text('3'), const Offset(290.0, 0.0));
await tester.pump(const Duration(seconds: 1));
// screen is 800px wide, and has the following items:
// -10..280 = 0
// 280..570 = 1
// 570..860 = 2
expect(find.text('0'), findsOneWidget);
expect(find.text('1'), findsOneWidget);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsNothing);
expect(find.text('4'), findsNothing);
expect(find.text('5'), findsNothing);
// -10..280 = 5
// 280..570 = 4
// 570..860 = 3
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsNothing);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsOneWidget);
await tester.pump(const Duration(seconds: 1));
// at this point we can drag 60 pixels further before we hit the friction zone
......@@ -222,27 +223,27 @@ void main() {
// to move item 3 entirely off screen therefore takes:
// 60 + (290-60)*2 = 520 pixels
// plus a couple more to be sure
await tester.scroll(find.text('1'), const Offset(522.0, 0.0));
await tester.scroll(find.text('4'), const Offset(522.0, 0.0));
await tester.pump(); // just after release
// screen is 800px wide, and has the following items:
// 280..570 = 0
// 570..860 = 1
expect(find.text('0'), findsOneWidget);
expect(find.text('1'), findsOneWidget);
// 280..570 = 5
// 570..860 = 4
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsNothing);
expect(find.text('3'), findsNothing);
expect(find.text('4'), findsNothing);
expect(find.text('5'), findsNothing);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsOneWidget);
await tester.pump(const Duration(seconds: 1)); // a second after release
// screen is 800px wide, and has the following items:
// 0..290 = 0
// 290..580 = 1
// 580..870 = 2
expect(find.text('0'), findsOneWidget);
expect(find.text('1'), findsOneWidget);
expect(find.text('2'), findsOneWidget);
expect(find.text('3'), findsNothing);
expect(find.text('4'), findsNothing);
expect(find.text('5'), findsNothing);
// 0..290 = 5
// 290..580 = 4
// 580..870 = 3
expect(find.text('0'), findsNothing);
expect(find.text('1'), findsNothing);
expect(find.text('2'), findsNothing);
expect(find.text('3'), findsOneWidget);
expect(find.text('4'), findsOneWidget);
expect(find.text('5'), findsOneWidget);
});
}
......@@ -6,6 +6,10 @@ import 'package:flutter_test/flutter_test.dart';
import 'package:flutter/widgets.dart';
void main() {
testWidgets('ListView default control', (WidgetTester tester) async {
await tester.pumpWidget(new Center(child: new ListView(itemExtent: 100.0)));
});
testWidgets('ListView itemExtent control test', (WidgetTester tester) async {
await tester.pumpWidget(
new ListView(
......
......@@ -8,14 +8,14 @@ import 'package:flutter/widgets.dart';
const List<int> items = const <int>[0, 1, 2, 3, 4, 5];
Widget buildFrame() {
return new ScrollableList(
itemExtent: 290.0,
scrollDirection: Axis.vertical,
children: items.map((int item) {
return new Container(
child: new Text('$item')
);
})
return new ListView(
itemExtent: 290.0,
scrollDirection: Axis.vertical,
children: items.map((int item) {
return new Container(
child: new Text('$item')
);
}).toList(),
);
}
......@@ -65,7 +65,7 @@ void main() {
testWidgets('Drag vertically', (WidgetTester tester) async {
await tester.pumpWidget(
new ScrollableList(
new ListView(
itemExtent: 290.0,
padding: const EdgeInsets.only(top: 250.0),
scrollDirection: Axis.vertical,
......@@ -73,8 +73,8 @@ void main() {
return new Container(
child: new Text('$item')
);
})
)
}).toList(),
),
);
await tester.pump();
......
......@@ -14,20 +14,19 @@ void main() {
await tester.pumpWidget(new Center(
child: new Container(
height: 50.0,
child: new ScrollableList(
key: new GlobalKey(),
child: new ListView(
itemExtent: 290.0,
scrollDirection: Axis.horizontal,
children: items.map((int item) {
return new Container(
child: new GestureDetector(
onTap: () { tapped.add(item); },
child: new Text('$item')
)
child: new Text('$item'),
),
);
})
)
)
}).toList(),
),
),
));
await tester.scroll(find.text('2'), const Offset(-280.0, 0.0));
await tester.pump(const Duration(seconds: 1));
......@@ -52,20 +51,19 @@ void main() {
await tester.pumpWidget(new Center(
child: new Container(
width: 50.0,
child: new ScrollableList(
key: new GlobalKey(),
child: new ListView(
itemExtent: 290.0,
scrollDirection: Axis.vertical,
children: items.map((int item) {
return new Container(
child: new GestureDetector(
onTap: () { tapped.add(item); },
child: new Text('$item')
)
child: new Text('$item'),
),
);
})
)
)
}).toList(),
),
),
));
await tester.scroll(find.text('1'), const Offset(0.0, -280.0));
await tester.pump(const Duration(seconds: 1));
......@@ -91,19 +89,18 @@ void main() {
List<int> tapped = <int>[];
await tester.pumpWidget(
new ScrollableList(
key: new GlobalKey(),
new ListView(
itemExtent: 290.0,
padding: const EdgeInsets.fromLTRB(5.0, 20.0, 15.0, 10.0),
children: items.map((int item) {
return new Container(
child: new GestureDetector(
onTap: () { tapped.add(item); },
child: new Text('$item')
)
child: new Text('$item'),
),
);
})
)
}).toList(),
),
);
await tester.tapAt(const Point(200.0, 19.0));
expect(tapped, equals(<int>[]));
......@@ -157,26 +154,22 @@ void main() {
List<int> tapped = <int>[];
await tester.pumpWidget(
new ClampOverscrolls(
edge: ScrollableEdge.both,
child: new ScrollableList(
itemExtent: 200.0,
children: items.map((int item) {
return new Container(
child: new GestureDetector(
onTap: () { tapped.add(item); },
child: new Text('$item')
)
);
})
)
)
new ListView(
itemExtent: 200.0,
children: items.map((int item) {
return new Container(
child: new GestureDetector(
onTap: () { tapped.add(item); },
child: new Text('$item'),
),
);
}).toList(),
),
);
await tester.fling(find.text('0'), const Offset(0.0, 400.0), 1000.0);
final ScrollableState scrollable = tester.state(find.byType(Scrollable));
expect(scrollable.scrollOffset, equals(0.0));
expect(scrollable.virtualScrollOffset, lessThan(0.0));
final Scrollable2State scrollable = tester.state(find.byType(Scrollable2));
expect(scrollable.position.pixels, equals(0.0));
await tester.tapAt(const Point(200.0, 100.0));
expect(tapped, equals(<int>[0]));
......
// Copyright 2016 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart';
void main() {
testWidgets('ScrollableList default control', (WidgetTester tester) async {
await tester.pumpWidget(new Center(child: new ScrollableList(itemExtent: 100.0)));
});
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment