Commit 90574b04 authored by Adam Barth's avatar Adam Barth Committed by GitHub

Remove Scrollable1 (#8225)

All the clients have migrated to Scrollable2.
parent 9ec5330f
......@@ -321,7 +321,7 @@ class CardCollectionState extends State<CardCollection> {
Widget background = new Positioned.fill(
child: new Container(
margin: const EdgeInsets.all(4.0),
child: new Viewport(
child: new SingleChildScrollView(
child: new Container(
height: cardModel.height,
decoration: new BoxDecoration(backgroundColor: theme.primaryColor),
......
......@@ -53,7 +53,6 @@ export 'src/rendering/stack.dart';
export 'src/rendering/table.dart';
export 'src/rendering/tweens.dart';
export 'src/rendering/view.dart';
export 'src/rendering/viewport.dart';
export 'src/rendering/viewport_offset.dart';
export 'package:flutter/foundation.dart' show
......
......@@ -167,32 +167,6 @@ class MaterialApp extends StatefulWidget {
_MaterialAppState createState() => new _MaterialAppState();
}
class _ScrollLikeCupertinoDelegate extends ScrollConfigurationDelegate {
const _ScrollLikeCupertinoDelegate();
@override
TargetPlatform get platform => TargetPlatform.iOS;
@override
ExtentScrollBehavior createScrollBehavior() => new OverscrollWhenScrollableBehavior(platform: TargetPlatform.iOS);
@override
bool updateShouldNotify(ScrollConfigurationDelegate old) => false;
}
class _ScrollLikeMountainViewDelegate extends ScrollConfigurationDelegate {
const _ScrollLikeMountainViewDelegate(this.platform);
@override
final TargetPlatform platform;
@override
ExtentScrollBehavior createScrollBehavior() => new OverscrollWhenScrollableBehavior(platform: TargetPlatform.android);
@override
bool updateShouldNotify(ScrollConfigurationDelegate old) => false;
}
class _MaterialScrollBehavior extends ScrollBehavior2 {
@override
TargetPlatform getPlatform(BuildContext context) {
......@@ -233,18 +207,6 @@ class _MaterialAppState extends State<MaterialApp> {
return null;
}
ScrollConfigurationDelegate _getScrollDelegate(TargetPlatform platform) {
switch (platform) {
case TargetPlatform.android:
return const _ScrollLikeMountainViewDelegate(TargetPlatform.android);
case TargetPlatform.fuchsia:
return const _ScrollLikeMountainViewDelegate(TargetPlatform.fuchsia);
case TargetPlatform.iOS:
return const _ScrollLikeCupertinoDelegate();
}
return null;
}
@override
Widget build(BuildContext context) {
ThemeData theme = config.theme ?? new ThemeData.fallback();
......@@ -283,11 +245,6 @@ class _MaterialAppState extends State<MaterialApp> {
return true;
});
result = new ScrollConfiguration(
delegate: _getScrollDelegate(theme.platform),
child: result
);
return new ScrollConfiguration2(
behavior: new _MaterialScrollBehavior(),
child: result
......
......@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:flutter/foundation.dart';
import 'package:flutter/widgets.dart';
import 'package:meta/meta.dart';
......
This diff is collapsed.
......@@ -11,6 +11,7 @@ import 'package:flutter/services.dart';
import 'debug.dart';
import 'framework.dart';
export 'package:flutter/foundation.dart' show TargetPlatform;
export 'package:flutter/animation.dart';
export 'package:flutter/painting.dart';
export 'package:flutter/rendering.dart' show
......@@ -43,10 +44,7 @@ export 'package:flutter/rendering.dart' show
SingleChildLayoutDelegate,
TextOverflow,
ValueChanged,
ValueGetter,
ViewportAnchor,
ViewportDimensions,
ViewportDimensionsChangeCallback;
ValueGetter;
// PAINTING NODES
......@@ -1375,72 +1373,6 @@ class Baseline extends SingleChildRenderObjectWidget {
}
}
/// A widget that's bigger on the inside.
///
/// The child of a viewport can layout to a larger size along the viewport's
/// [mainAxis] than the viewport itself. If that happens, only a portion of the
/// child will be visible through the viewport. The portion of the child that is
/// visible is controlled by the scroll offset.
///
/// Viewport is the core scrolling primitive in the system, but it can be used
/// in other situations.
class Viewport extends SingleChildRenderObjectWidget {
/// Creates a widget that's bigger on the inside.
///
/// The [mainAxis] and [paintOffset] arguments must not be null.
Viewport({
Key key,
this.paintOffset: Offset.zero,
this.mainAxis: Axis.vertical,
this.anchor: ViewportAnchor.start,
this.onPaintOffsetUpdateNeeded,
Widget child
}) : super(key: key, child: child) {
assert(mainAxis != null);
assert(paintOffset != null);
}
/// The offset at which to paint the child.
///
/// The offset can be non-zero only in the [mainAxis].
final Offset paintOffset;
/// The direction in which the child is permitted to be larger than the viewport.
///
/// The child is given layout constraints that are fully unconstrained along
/// the main axis (e.g., the child can be as tall as it wants if the main axis
/// is vertical).
final Axis mainAxis;
/// The end of the viewport from which the paint offset is computed.
///
/// See [ViewportAnchor] for more detail.
final ViewportAnchor anchor;
/// Called when the interior or exterior dimensions of the viewport change.
final ViewportDimensionsChangeCallback onPaintOffsetUpdateNeeded;
@override
RenderViewport createRenderObject(BuildContext context) {
return new RenderViewport(
paintOffset: paintOffset,
mainAxis: mainAxis,
anchor: anchor,
onPaintOffsetUpdateNeeded: onPaintOffsetUpdateNeeded
);
}
@override
void updateRenderObject(BuildContext context, RenderViewport renderObject) {
// Order dependency: RenderViewport validates scrollOffset based on mainAxis.
renderObject
..mainAxis = mainAxis
..anchor = anchor
..paintOffset = paintOffset
..onPaintOffsetUpdateNeeded = onPaintOffsetUpdateNeeded;
}
}
// SLIVERS
......
// 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.
////////////////////////////////////////////////////////////////////////////////
// DELETE THIS FILE WHEN REMOVING LEGACY SCROLLING CODE
////////////////////////////////////////////////////////////////////////////////
import 'package:flutter/foundation.dart';
import 'framework.dart';
import 'scrollable.dart';
/// A widget that controls whether viewport descendants will overscroll their contents.
/// Overscrolling is clamped at the beginning or end or both according to the
/// [edge] parameter.
///
/// Scroll offset limits are defined by the enclosing Scrollable's [ScrollBehavior].
class ClampOverscrolls extends InheritedWidget {
/// Creates a widget that controls whether viewport descendants will overscroll
/// their contents.
///
/// The [edge] and [child] arguments must not be null.
ClampOverscrolls({
Key key,
this.edge: ScrollableEdge.none,
@required Widget child,
}) : super(key: key, child: child) {
assert(edge != null);
assert(child != null);
}
/// Creates a widget that controls whether viewport descendants will overscroll
/// based on the given [edge] and the inherited ClampOverscrolls widget for
/// the given [context]. For example if edge is ScrollableEdge.leading
/// and a ClampOverscrolls ancestor exists that specified ScrollableEdge.trailing,
/// then this widget would clamp both scrollable edges.
///
/// The [context], [edge] and [child] arguments must not be null.
factory ClampOverscrolls.inherit({
Key key,
@required BuildContext context,
@required ScrollableEdge edge: ScrollableEdge.none,
@required Widget child
}) {
assert(context != null);
assert(edge != null);
assert(child != null);
// The child's clamped edge is the union of the given edge and the
// parent's clamped edge.
ScrollableEdge parentEdge = ClampOverscrolls.of(context)?.edge ?? ScrollableEdge.none;
ScrollableEdge childEdge = edge;
switch (parentEdge) {
case ScrollableEdge.leading:
if (edge == ScrollableEdge.trailing || edge == ScrollableEdge.both)
childEdge = ScrollableEdge.both;
break;
case ScrollableEdge.trailing:
if (edge == ScrollableEdge.leading || edge == ScrollableEdge.both)
childEdge = ScrollableEdge.both;
break;
case ScrollableEdge.both:
childEdge = ScrollableEdge.both;
break;
case ScrollableEdge.none:
break;
}
return new ClampOverscrolls(
key: key,
edge: childEdge,
child: child
);
}
/// Defines when viewport scrollOffsets are clamped in terms of the scrollDirection.
/// If edge is `leading` the viewport's scrollOffset will be clamped at its minimum
/// value (often 0.0). If edge is `trailing` then the scrollOffset will be clamped
/// to its maximum value. If edge is `both` then both the leading and trailing
/// constraints are applied.
final ScrollableEdge edge;
/// Return the [newScrollOffset] clamped according to [edge] and [scrollable]'s
/// scroll behavior. The value of [newScrollOffset] defaults to `scrollable.scrollOffset`.
double clampScrollOffset(ScrollableState scrollable, [double newScrollOffset]) {
final double scrollOffset = newScrollOffset ?? scrollable.scrollOffset;
final double minScrollOffset = scrollable.scrollBehavior.minScrollOffset;
final double maxScrollOffset = scrollable.scrollBehavior.maxScrollOffset;
switch (edge) {
case ScrollableEdge.both:
return scrollOffset.clamp(minScrollOffset, maxScrollOffset);
case ScrollableEdge.leading:
return scrollOffset.clamp(minScrollOffset, double.INFINITY);
case ScrollableEdge.trailing:
return scrollOffset.clamp(double.NEGATIVE_INFINITY, maxScrollOffset);
case ScrollableEdge.none:
return scrollOffset;
}
return scrollOffset;
}
/// The closest instance of this class that encloses the given context.
///
/// Typical usage is as follows:
///
/// ```dart
/// ScrollableEdge edge = ClampOverscrolls.of(context).edge;
/// ```
static ClampOverscrolls of(BuildContext context) {
return context.inheritFromWidgetOfExactType(ClampOverscrolls);
}
@override
bool updateShouldNotify(ClampOverscrolls old) => edge != old.edge;
@override
void debugFillDescription(List<String> description) {
super.debugFillDescription(description);
description.add('edge: $edge');
}
}
......@@ -192,7 +192,6 @@ class Focus extends StatefulWidget {
_FocusScope focusScope = key.currentContext.ancestorWidgetOfExactType(_FocusScope);
if (focusScope != null) {
focusScope.focusState._setFocusedWidget(key);
Scrollable.ensureVisible(focusedContext); // ignore: DEPRECATED_MEMBER_USE
Scrollable2.ensureVisible(focusedContext);
}
}
......@@ -360,7 +359,6 @@ class _FocusState extends State<Focus> {
BuildContext focusedContext = _focusedWidget?.currentContext;
if (focusedContext == null)
return;
Scrollable.ensureVisible(focusedContext); // ignore: DEPRECATED_MEMBER_USE
Scrollable2.ensureVisible(focusedContext);
}
......
This diff is collapsed.
......@@ -6,7 +6,6 @@ import 'package:flutter/foundation.dart';
import 'package:flutter/rendering.dart';
import 'framework.dart';
import 'scroll_behavior.dart';
import 'scroll_physics.dart';
import 'overscroll_indicator.dart';
......@@ -78,101 +77,3 @@ class ScrollConfiguration2 extends InheritedWidget {
|| behavior.shouldNotify(old.behavior);
}
}
////////////////////////////////////////////////////////////////////////////////
// DELETE EVERYTHING BELOW THIS LINE WHEN REMOVING LEGACY SCROLLING CODE
////////////////////////////////////////////////////////////////////////////////
/// Controls how [Scrollable] widgets in a subtree behave.
///
/// Used by [ScrollConfiguration].
abstract class ScrollConfigurationDelegate {
/// Abstract const constructor. This constructor enables subclasses to provide
/// const constructors so that they can be used in const expressions.
const ScrollConfigurationDelegate();
/// Returns the platform whose scroll physics should be approximated. See
/// [ScrollBehavior.platform].
TargetPlatform get platform;
/// Returns the ScrollBehavior to be used by generic scrolling containers like
/// [Block].
ExtentScrollBehavior createScrollBehavior();
/// Generic scrolling containers like [Block] will apply this function to the
/// Scrollable they create. It can be used to add widgets that wrap the
/// Scrollable, like scrollbars or overscroll indicators. By default the
/// [scrollWidget] parameter is returned unchanged.
Widget wrapScrollWidget(BuildContext context, Widget scrollWidget) => scrollWidget;
/// Overrides should return true if this ScrollConfigurationDelegate differs
/// from the provided old delegate in a way that requires rebuilding its
/// scrolling container descendants.
bool updateShouldNotify(@checked ScrollConfigurationDelegate old);
}
class _DefaultScrollConfigurationDelegate extends ScrollConfigurationDelegate {
const _DefaultScrollConfigurationDelegate();
@override
TargetPlatform get platform => defaultTargetPlatform;
@override
ExtentScrollBehavior createScrollBehavior() => new OverscrollWhenScrollableBehavior(platform: platform);
@override
bool updateShouldNotify(ScrollConfigurationDelegate old) => false;
}
/// A widget that controls descendant [Scrollable] widgets.
///
/// Classes that create Scrollables are not required to depend on this
/// Widget. The following general purpose scrolling widgets do depend
/// on [ScrollConfiguration]: [Block], [LazyBlock], [ScrollableViewport],
/// [ScrollableList], [ScrollableLazyList]. The [Scrollable] base class uses
/// [ScrollConfiguration] to create its [ScrollBehavior].
class ScrollConfiguration extends InheritedWidget {
/// Creates a widget that controls descendant [Scrollable] widgets.
///
/// If the [delegate] argument is null, the scroll configuration for this
/// subtree is controlled by the default implementation of
/// [ScrollConfigurationDelegate].
ScrollConfiguration({
Key key,
this.delegate,
@required Widget child
}) : super(key: key, child: child);
static const ScrollConfigurationDelegate _defaultDelegate = const _DefaultScrollConfigurationDelegate();
/// Defines the ScrollBehavior and scrollable wrapper for descendants.
final ScrollConfigurationDelegate delegate;
/// The delegate property of the closest instance of this class that encloses
/// the given context.
///
/// If no such instance exists, returns a default
/// [ScrollConfigurationDelegate] that approximates the scrolling physics of
/// the current platform (see [defaultTargetPlatform]) using a
/// [OverscrollWhenScrollableBehavior] behavior model.
///
/// Typical usage is as follows:
///
/// ```dart
/// ScrollConfigurationDelegate scrollConfiguration = ScrollConfiguration.of(context);
/// ```
static ScrollConfigurationDelegate of(BuildContext context) {
ScrollConfiguration configuration = context.inheritFromWidgetOfExactType(ScrollConfiguration);
return configuration?.delegate ?? _defaultDelegate;
}
/// A utility function that calls [ScrollConfigurationDelegate.wrapScrollWidget].
static Widget wrap(BuildContext context, Widget scrollWidget) {
return ScrollConfiguration.of(context).wrapScrollWidget(context, scrollWidget);
}
@override
bool updateShouldNotify(ScrollConfiguration old) {
return delegate?.updateShouldNotify(old.delegate) ?? false;
}
}
......@@ -73,7 +73,7 @@ class BouncingScrollPhysics extends ScrollPhysics {
return new BouncingScrollSimulation(
spring: spring,
position: position.pixels,
velocity: velocity,
velocity: velocity * 0.91, // TODO(abarth): We should move this constant closer to the drag end.
leadingExtent: position.minScrollExtent,
trailingExtent: position.maxScrollExtent,
)..tolerance = tolerance;
......
......@@ -81,7 +81,7 @@ class BouncingScrollSimulation extends SimulationGroup {
_currentSimulation = new ScrollSpringSimulation(_spring, position, _leadingExtent, velocity);
return true;
} else if (_currentSimulation == null) {
_currentSimulation = new FrictionSimulation(0.135, position, velocity * 0.91);
_currentSimulation = new FrictionSimulation(0.135, position, velocity);
return true;
}
}
......@@ -196,139 +196,3 @@ class ClampingScrollSimulation extends Simulation {
return time >= _duration;
}
}
////////////////////////////////////////////////////////////////////////////////
// DELETE EVERYTHING BELOW THIS LINE WHEN REMOVING LEGACY SCROLLING CODE
////////////////////////////////////////////////////////////////////////////////
final SpringDescription _kScrollSpring = new SpringDescription.withDampingRatio(mass: 0.5, springConstant: 100.0, ratio: 1.1);
final double _kDrag = 0.025;
class _CupertinoSimulation extends FrictionSimulation {
static const double drag = 0.135;
_CupertinoSimulation({ double position, double velocity })
: super(drag, position, velocity * 0.91);
}
class _MountainViewSimulation extends ClampingScrollSimulation {
_MountainViewSimulation({
double position,
double velocity,
double friction: 0.015,
}) : super(
position: position,
velocity: velocity,
friction: friction,
);
}
/// Composite simulation for scrollable interfaces.
///
/// Simulates kinetic scrolling behavior between a leading and trailing
/// boundary. Friction is applied within the extents and a spring action is
/// applied at the boundaries. This simulation can only step forward.
class ScrollSimulation extends SimulationGroup {
/// Creates a [ScrollSimulation] with the given parameters.
///
/// The position and velocity arguments must use the same units as will be
/// expected from the [x] and [dx] methods respectively.
///
/// The leading and trailing extents must use the unit of length, the same
/// unit as used for the position argument and as expected from the [x]
/// method.
///
/// The units used with the provided [SpringDescription] must similarly be
/// consistent with the other arguments.
///
/// The final argument is the coefficient of friction, which is unitless.
ScrollSimulation({
@required double position,
@required double velocity,
@required double leadingExtent,
@required double trailingExtent,
SpringDescription spring,
double drag,
TargetPlatform platform,
}) : _leadingExtent = leadingExtent,
_trailingExtent = trailingExtent,
_spring = spring ?? _kScrollSpring,
_drag = drag ?? _kDrag,
_platform = platform {
assert(position != null);
assert(velocity != null);
assert(_leadingExtent != null);
assert(_trailingExtent != null);
assert(_spring != null);
_chooseSimulation(position, velocity, 0.0);
}
final double _leadingExtent;
final double _trailingExtent;
final SpringDescription _spring;
final double _drag;
final TargetPlatform _platform;
bool _isSpringing = false;
Simulation _currentSimulation;
double _offset = 0.0;
@override
bool step(double time) => _chooseSimulation(
_currentSimulation.x(time - _offset),
_currentSimulation.dx(time - _offset), time);
@override
Simulation get currentSimulation => _currentSimulation;
@override
double get currentIntervalOffset => _offset;
bool _chooseSimulation(double position, double velocity, double intervalOffset) {
if (_spring == null && (position > _trailingExtent || position < _leadingExtent))
return false;
// This simulation can only step forward.
if (!_isSpringing) {
if (position > _trailingExtent) {
_isSpringing = true;
_offset = intervalOffset;
_currentSimulation = new ScrollSpringSimulation(_spring, position, _trailingExtent, velocity);
return true;
} else if (position < _leadingExtent) {
_isSpringing = true;
_offset = intervalOffset;
_currentSimulation = new ScrollSpringSimulation(_spring, position, _leadingExtent, velocity);
return true;
}
}
if (_currentSimulation == null) {
switch (_platform) {
case TargetPlatform.android:
case TargetPlatform.fuchsia:
_currentSimulation = new _MountainViewSimulation(
position: position,
velocity: velocity,
);
break;
case TargetPlatform.iOS:
_currentSimulation = new _CupertinoSimulation(
position: position,
velocity: velocity,
);
break;
}
// No platform specified
_currentSimulation ??= new FrictionSimulation(_drag, position, velocity);
return true;
}
return false;
}
@override
String toString() {
return 'ScrollSimulation(leadingExtent: $_leadingExtent, trailingExtent: $_trailingExtent)';
}
}
......@@ -14,7 +14,6 @@ export 'src/widgets/async.dart';
export 'src/widgets/banner.dart';
export 'src/widgets/basic.dart';
export 'src/widgets/binding.dart';
export 'src/widgets/clamp_overscrolls.dart';
export 'src/widgets/container.dart';
export 'src/widgets/debug.dart';
export 'src/widgets/dismissable.dart';
......@@ -45,7 +44,6 @@ export 'src/widgets/placeholder.dart';
export 'src/widgets/primary_scroll_controller.dart';
export 'src/widgets/raw_keyboard_listener.dart';
export 'src/widgets/routes.dart';
export 'src/widgets/scroll_behavior.dart';
export 'src/widgets/scroll_configuration.dart';
export 'src/widgets/scroll_controller.dart';
export 'src/widgets/scroll_notification.dart';
......
......@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart';
......
......@@ -78,8 +78,7 @@ void main() {
});
testWidgets('Drawer scrolling', (WidgetTester tester) async {
GlobalKey<ScrollableState<Scrollable>> drawerKey =
new GlobalKey<ScrollableState<Scrollable>>(debugLabel: 'drawer');
Key drawerKey = new UniqueKey();
const double appBarHeight = 256.0;
ScrollController scrollOffset = new ScrollController();
......
......@@ -313,7 +313,7 @@ void main() {
await tester.pump(const Duration(milliseconds: 100));
expect(scrollableState.position.pixels, greaterThan(0.0));
}, skip: Scrollable != Scrollable2); // TODO(abarth): re-enable when ensureVisible is implemented
});
testWidgets('Stepper index test', (WidgetTester tester) async {
await tester.pumpWidget(
......
......@@ -33,7 +33,7 @@ void main() {
final Map<String, WidgetBuilder> routes = <String, WidgetBuilder>{
'/': (_) {
return new Material(
child: new Viewport(
child: new SingleChildScrollView(
child: new TwoLevelList(
children: <Widget>[
new TwoLevelListItem(title: new Text('Top'), key: topKey),
......@@ -91,7 +91,7 @@ void main() {
final Map<String, WidgetBuilder> routes = <String, WidgetBuilder>{
'/': (_) {
return new Material(
child: new Viewport(
child: new SingleChildScrollView(
child: new TwoLevelList(
children: <Widget>[
new TwoLevelSublist(
......
......@@ -206,26 +206,24 @@ void main() {
SpringDescription spring = new SpringDescription.withDampingRatio(
mass: 1.0, springConstant: 50.0, ratio: 0.5);
ScrollSimulation scroll = new ScrollSimulation(
BouncingScrollSimulation scroll = new BouncingScrollSimulation(
position: 100.0,
velocity: 800.0,
leadingExtent: 0.0,
trailingExtent: 300.0,
spring: spring,
drag: 0.3
);
scroll.tolerance = const Tolerance(velocity: 0.5, distance: 0.1);
expect(scroll.isDone(0.0), false);
expect(scroll.isDone(0.5), false); // switch from friction to spring
expect(scroll.isDone(3.5), true);
ScrollSimulation scroll2 = new ScrollSimulation(
BouncingScrollSimulation scroll2 = new BouncingScrollSimulation(
position: 100.0,
velocity: -800.0,
leadingExtent: 0.0,
trailingExtent: 300.0,
spring: spring,
drag: 0.3
);
scroll2.tolerance = const Tolerance(velocity: 0.5, distance: 0.1);
expect(scroll2.isDone(0.0), false);
......@@ -237,13 +235,12 @@ void main() {
SpringDescription spring = new SpringDescription.withDampingRatio(
mass: 1.0, springConstant: 50.0, ratio: 0.5);
ScrollSimulation scroll = new ScrollSimulation(
BouncingScrollSimulation scroll = new BouncingScrollSimulation(
position: 100.0,
velocity: 400.0,
leadingExtent: 0.0,
trailingExtent: double.INFINITY,
spring: spring,
drag: 0.3,
);
scroll.tolerance = const Tolerance(velocity: 1.0);
......@@ -251,15 +248,14 @@ void main() {
expect(scroll.x(0.0), 100);
expect(scroll.dx(0.0), 400.0);
expect(scroll.x(1.0) > 330 && scroll.x(1.0) < 335, true);
expect(scroll.x(1.0), closeTo(272.0, 1.0));
expect(scroll.dx(1.0), 120.0);
expect(scroll.dx(2.0), 36.0);
expect(scroll.dx(3.0), 10.8);
expect(scroll.dx(4.0) < 3.5, true);
expect(scroll.dx(1.0), closeTo(54.0, 1.0));
expect(scroll.dx(2.0), closeTo(7.0, 1.0));
expect(scroll.dx(3.0), lessThan(1.0));
expect(scroll.isDone(5.0), true);
expect(scroll.x(5.0) > 431 && scroll.x(5.0) < 432, true);
expect(scroll.x(5.0), closeTo(300.0, 1.0));
// We should never switch
expect(scroll.currentIntervalOffset, 0.0);
......@@ -267,13 +263,12 @@ void main() {
test('over/under scroll spring', () {
SpringDescription spring = new SpringDescription.withDampingRatio(mass: 1.0, springConstant: 170.0, ratio: 1.1);
ScrollSimulation scroll = new ScrollSimulation(
BouncingScrollSimulation scroll = new BouncingScrollSimulation(
position: 500.0,
velocity: -7500.0,
leadingExtent: 0.0,
trailingExtent: 1000.0,
spring: spring,
drag: 0.025,
);
scroll.tolerance = const Tolerance(velocity: 45.0, distance: 1.5);
......@@ -282,8 +277,8 @@ void main() {
expect(scroll.dx(0.0), closeTo(-7500.0, .0001));
expect(scroll.isDone(0.025), false);
expect(scroll.x(0.025), closeTo(320.0, 1.0));
expect(scroll.dx(0.25), closeTo(-2982, 1.0));
expect(scroll.x(0.025), closeTo(317.0, 1.0));
expect(scroll.dx(0.25), closeTo(-4546, 1.0));
expect(scroll.isDone(2.0), true);
expect(scroll.x(2.0), 0.0);
......
......@@ -10,17 +10,19 @@ import 'rendering_tester.dart';
class TestLayout {
TestLayout() {
// viewport incoming constraints are tight 800x600
// viewport is vertical by default
root = new RenderViewport(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; }
// incoming constraints are tight 800x600
root = new RenderPositionedBox(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(width: 800.0),
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; }
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 10.0, width: 10.0),
),
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 10.0, width: 10.0)
)
)
),
);
}
RenderBox root;
......
......@@ -12,19 +12,21 @@ void main() {
test("offstage", () {
RenderBox child;
bool painted = false;
// viewport incoming constraints are tight 800x600
// viewport is vertical by default
RenderBox root = new RenderViewport(
child: new RenderOffstage(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; }
// incoming constraints are tight 800x600
RenderBox root = new RenderPositionedBox(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(width: 800.0),
child: new RenderOffstage(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; },
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 10.0, width: 10.0),
),
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 10.0, width: 10.0)
)
)
)
),
),
);
expect(child.hasSize, isFalse);
expect(painted, isFalse);
......
......@@ -10,30 +10,32 @@ import 'rendering_tester.dart';
class TestTree {
TestTree() {
// viewport incoming constraints are tight 800x600
// viewport is vertical by default
root = new RenderViewport(
// Place the child to be evaluated within both a repaint boundary and a
// layout-root element (in this case a tightly constrained box). Otherwise
// the act of transplanting the root into a new container will cause the
// relayout/repaint of the new parent node to satisfy the test.
child: new RenderRepaintBoundary(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0),
child: new RenderRepaintBoundary(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; }
// incoming constraints are tight 800x600
root = new RenderPositionedBox(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(width: 800.0),
// Place the child to be evaluated within both a repaint boundary and a
// layout-root element (in this case a tightly constrained box). Otherwise
// the act of transplanting the root into a new container will cause the
// relayout/repaint of the new parent node to satisfy the test.
child: new RenderRepaintBoundary(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0),
child: new RenderRepaintBoundary(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; },
),
child: new RenderPositionedBox(
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0),
),
),
),
child: new RenderPositionedBox(
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0)
)
)
)
)
)
)
),
),
),
),
);
}
RenderObject root;
......@@ -50,24 +52,26 @@ class MutableCompositor extends RenderProxyBox {
class TestCompositingBitsTree {
TestCompositingBitsTree() {
// viewport incoming constraints are tight 800x600
// viewport is vertical by default
root = new RenderViewport(
// Place the child to be evaluated within a repaint boundary. Otherwise
// the act of transplanting the root into a new container will cause the
// repaint of the new parent node to satisfy the test.
child: new RenderRepaintBoundary(
child: compositor = new MutableCompositor(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; }
// incoming constraints are tight 800x600
root = new RenderPositionedBox(
child: new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(width: 800.0),
// Place the child to be evaluated within a repaint boundary. Otherwise
// the act of transplanting the root into a new container will cause the
// repaint of the new parent node to satisfy the test.
child: new RenderRepaintBoundary(
child: compositor = new MutableCompositor(
child: new RenderCustomPaint(
painter: new TestCallbackPainter(
onPaint: () { painted = true; },
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0)
),
),
child: child = new RenderConstrainedBox(
additionalConstraints: const BoxConstraints.tightFor(height: 20.0, width: 20.0)
)
)
)
)
),
),
),
);
}
RenderObject root;
......
// Copyright 2015 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/rendering.dart';
import 'package:test/test.dart';
import 'rendering_tester.dart';
void main() {
test('Should be able to hit with positive paint offset', () {
RenderBox green = new RenderDecoratedBox(
decoration: const BoxDecoration(
backgroundColor: const Color(0xFF00FF00)
));
RenderBox size = new RenderConstrainedBox(
additionalConstraints: new BoxConstraints.tight(const Size(100.0, 100.0)),
child: green);
RenderBox red = new RenderDecoratedBox(
decoration: const BoxDecoration(
backgroundColor: const Color(0xFFFF0000)
),
child: size);
RenderViewport viewport = new RenderViewport(child: red, paintOffset: const Offset(0.0, 10.0));
layout(viewport);
HitTestResult result;
result = new HitTestResult();
renderer.renderView.hitTest(result, position: const Point(15.0, 0.0));
expect(result.path.first.target.runtimeType, equals(RenderView));
result = new HitTestResult();
renderer.renderView.hitTest(result, position: const Point(15.0, 15.0));
expect(result.path.first.target, equals(green));
});
}
......@@ -35,8 +35,8 @@ void main() {
Key childKey = new UniqueKey();
await tester.pumpWidget(
new Center(
child: new Viewport(
mainAxis: Axis.horizontal,
child: new SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: new AspectRatio(
aspectRatio: 2.0,
child: new Container(
......
......@@ -248,7 +248,6 @@ class _FlutterDriverExtension {
Future<ScrollResult> _scrollIntoView(Command command) async {
ScrollIntoView scrollIntoViewCommand = command;
Finder target = await _waitForElement(_createFinder(scrollIntoViewCommand.finder));
await Scrollable.ensureVisible(target.evaluate().single, duration: const Duration(milliseconds: 100));
await Scrollable2.ensureVisible(target.evaluate().single, duration: const Duration(milliseconds: 100), alignment: scrollIntoViewCommand.alignment ?? 0.0);
return new ScrollResult();
}
......
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