Added LayoutChangedNotifier. (#5304)
Added a simple widget that automatically dispatches a LayoutChangedNotification when its child changes layout.
This commit is contained in:
parent
fd119f4f59
commit
de448c20e6
@ -656,5 +656,4 @@ class _InkHighlight extends InkFeature implements InkHighlight {
|
|||||||
_paintHighlight(canvas, rect.shift(originOffset), paint);
|
_paintHighlight(canvas, rect.shift(originOffset), paint);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,54 @@
|
|||||||
|
// 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:flutter/widgets.dart';
|
||||||
|
|
||||||
|
/// Indicates that the size of one of the descendants of the object receiving
|
||||||
|
/// this notification has changed, and that therefore any assumptions about that
|
||||||
|
/// layout are no longer valid.
|
||||||
|
///
|
||||||
|
/// See [LayoutChangedNotification].
|
||||||
|
class SizeChangedLayoutNotificaion extends LayoutChangedNotification {}
|
||||||
|
|
||||||
|
/// A widget that automatically dispatches a [SizeChangedLayoutNotifier] when
|
||||||
|
/// the layout of its child changes.
|
||||||
|
///
|
||||||
|
/// Useful especially when having some complex, layout-changing animation within
|
||||||
|
/// [Material] that is also interactive.
|
||||||
|
class SizeChangedLayoutNotifier extends SingleChildRenderObjectWidget {
|
||||||
|
/// Creates a [SizeChangedLayoutNotifier] that dispatches layout changed
|
||||||
|
/// notifications when [child] changes layout.
|
||||||
|
SizeChangedLayoutNotifier({
|
||||||
|
Key key,
|
||||||
|
Widget child
|
||||||
|
}) : super(key: key, child: child);
|
||||||
|
|
||||||
|
@override
|
||||||
|
_RenderSizeChangedWithCallback createRenderObject(BuildContext context) {
|
||||||
|
return new _RenderSizeChangedWithCallback(
|
||||||
|
onLayoutChangedCallback: () {
|
||||||
|
new SizeChangedLayoutNotificaion().dispatch(context);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class _RenderSizeChangedWithCallback extends RenderProxyBox {
|
||||||
|
_RenderSizeChangedWithCallback({
|
||||||
|
RenderBox child,
|
||||||
|
this.onLayoutChangedCallback
|
||||||
|
}) : super(child);
|
||||||
|
|
||||||
|
VoidCallback onLayoutChangedCallback;
|
||||||
|
Size _oldSize;
|
||||||
|
|
||||||
|
@override
|
||||||
|
void performLayout() {
|
||||||
|
super.performLayout();
|
||||||
|
if (onLayoutChangedCallback != null && size != _oldSize)
|
||||||
|
onLayoutChangedCallback();
|
||||||
|
_oldSize = size;
|
||||||
|
}
|
||||||
|
}
|
@ -50,6 +50,7 @@ export 'src/widgets/scrollable_grid.dart';
|
|||||||
export 'src/widgets/scrollable_list.dart';
|
export 'src/widgets/scrollable_list.dart';
|
||||||
export 'src/widgets/scrollable.dart';
|
export 'src/widgets/scrollable.dart';
|
||||||
export 'src/widgets/semantics_debugger.dart';
|
export 'src/widgets/semantics_debugger.dart';
|
||||||
|
export 'src/widgets/size_changed_layout_notifier.dart';
|
||||||
export 'src/widgets/status_transitions.dart';
|
export 'src/widgets/status_transitions.dart';
|
||||||
export 'src/widgets/table.dart';
|
export 'src/widgets/table.dart';
|
||||||
export 'src/widgets/text_selection.dart';
|
export 'src/widgets/text_selection.dart';
|
||||||
|
@ -0,0 +1,52 @@
|
|||||||
|
// 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/widgets.dart';
|
||||||
|
import 'package:flutter_test/flutter_test.dart';
|
||||||
|
|
||||||
|
class NotifyMaterial extends StatelessWidget {
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
new LayoutChangedNotification().dispatch(context);
|
||||||
|
return new Container();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void main() {
|
||||||
|
testWidgets('SizeChangedLayoutNotification test', (WidgetTester tester) async {
|
||||||
|
bool notified = false;
|
||||||
|
|
||||||
|
await tester.pumpWidget(
|
||||||
|
new NotificationListener<LayoutChangedNotification>(
|
||||||
|
onNotification: (LayoutChangedNotification notification) {
|
||||||
|
notified = true;
|
||||||
|
return true;
|
||||||
|
},
|
||||||
|
child: new SizeChangedLayoutNotifier(
|
||||||
|
child: new SizedBox(
|
||||||
|
width: 100.0,
|
||||||
|
height: 100.0
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
await tester.pumpWidget(
|
||||||
|
new NotificationListener<LayoutChangedNotification>(
|
||||||
|
onNotification: (LayoutChangedNotification notification) {
|
||||||
|
notified = true;
|
||||||
|
return true;
|
||||||
|
},
|
||||||
|
child: new SizeChangedLayoutNotifier(
|
||||||
|
child: new SizedBox(
|
||||||
|
width: 200.0,
|
||||||
|
height: 100.0
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(notified, isTrue);
|
||||||
|
});
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user