Index: sky/sdk/lib/framework/rendering/box.dart |
diff --git a/sky/sdk/lib/framework/rendering/box.dart b/sky/sdk/lib/framework/rendering/box.dart |
index abc6c65e399108590b5862507c5365213fde5863..3d54eae0e6da565fa1986d23a027baab2f4764c0 100644 |
--- a/sky/sdk/lib/framework/rendering/box.dart |
+++ b/sky/sdk/lib/framework/rendering/box.dart |
@@ -53,7 +53,8 @@ class BoxConstraints { |
this.minWidth: 0.0, |
this.maxWidth: double.INFINITY, |
this.minHeight: 0.0, |
- this.maxHeight: double.INFINITY}); |
+ this.maxHeight: double.INFINITY |
+ }); |
BoxConstraints.tight(Size size) |
: minWidth = size.width, |
@@ -79,6 +80,15 @@ class BoxConstraints { |
); |
} |
+ BoxConstraints loosen() { |
+ return new BoxConstraints( |
+ minWidth: 0.0, |
+ maxWidth: maxWidth, |
+ minHeight: 0.0, |
+ maxHeight: maxHeight |
+ ); |
+ } |
+ |
BoxConstraints apply(BoxConstraints constraints) { |
return new BoxConstraints( |
minWidth: math.max(minWidth, constraints.minWidth), |
@@ -243,6 +253,8 @@ abstract class RenderBox extends RenderObject { |
class RenderProxyBox extends RenderBox with RenderObjectWithChildMixin<RenderBox> { |
+ // ProxyBox assumes the child will be at 0,0 and will have the same size |
+ |
RenderProxyBox([RenderBox child = null]) { |
this.child = child; |
} |
@@ -503,12 +515,37 @@ class RenderClipOval extends RenderProxyBox { |
} |
} |
-class RenderPadding extends RenderBox with RenderObjectWithChildMixin<RenderBox> { |
+abstract class RenderShiftedBox extends RenderBox with RenderObjectWithChildMixin<RenderBox> { |
+ |
+ // Abstract class for one-child-layout render boxes |
+ |
+ RenderShiftedBox(RenderBox child) { |
+ this.child = child; |
+ } |
+ |
+ void paint(RenderObjectDisplayList canvas) { |
+ if (child != null) |
+ canvas.paintChild(child, child.parentData.position); |
+ } |
- RenderPadding({ EdgeDims padding, RenderBox child }) { |
+ void hitTestChildren(HitTestResult result, { Point position }) { |
+ if (child != null) { |
+ assert(child.parentData is BoxParentData); |
+ Rect childBounds = new Rect.fromPointAndSize(child.parentData.position, child.size); |
+ if (childBounds.contains(position)) { |
+ child.hitTest(result, position: new Point(position.x - child.parentData.position.x, |
+ position.y - child.parentData.position.y)); |
+ } |
+ } |
+ } |
+ |
+} |
+ |
+class RenderPadding extends RenderShiftedBox { |
+ |
+ RenderPadding({ EdgeDims padding, RenderBox child }) : super(child) { |
assert(padding != null); |
this.padding = padding; |
- this.child = child; |
} |
EdgeDims _padding; |
@@ -564,23 +601,79 @@ class RenderPadding extends RenderBox with RenderObjectWithChildMixin<RenderBox> |
padding.top + child.size.height + padding.bottom)); |
} |
- void paint(RenderObjectDisplayList canvas) { |
+ String debugDescribeSettings(String prefix) => '${super.debugDescribeSettings(prefix)}${prefix}padding: ${padding}\n'; |
+} |
+ |
+class RenderPositionedBox extends RenderShiftedBox { |
+ |
+ RenderPositionedBox({ |
+ RenderBox child, |
+ double horizontal: 0.5, |
+ double vertical: 0.5 |
+ }) : _horizontal = horizontal, |
+ _vertical = vertical, |
+ super(child) { |
+ assert(horizontal != null); |
+ assert(vertical != null); |
+ } |
+ |
+ double _horizontal; |
+ double get horizontal => _horizontal; |
+ void set horizontal (double value) { |
+ assert(value != null); |
+ if (_horizontal == value) |
+ return; |
+ _horizontal = value; |
+ markNeedsLayout(); |
+ } |
+ |
+ double _vertical; |
+ double get vertical => _vertical; |
+ void set vertical (double value) { |
+ assert(value != null); |
+ if (_vertical == value) |
+ return; |
+ _vertical = value; |
+ markNeedsLayout(); |
+ } |
+ |
+ double getMinIntrinsicWidth(BoxConstraints constraints) { |
if (child != null) |
- canvas.paintChild(child, child.parentData.position); |
+ return child.getMinIntrinsicWidth(constraints); |
+ return super.getMinIntrinsicWidth(constraints); |
} |
- void hitTestChildren(HitTestResult result, { Point position }) { |
+ double getMaxIntrinsicWidth(BoxConstraints constraints) { |
+ if (child != null) |
+ return child.getMaxIntrinsicWidth(constraints); |
+ return super.getMaxIntrinsicWidth(constraints); |
+ } |
+ |
+ double getMinIntrinsicHeight(BoxConstraints constraints) { |
+ if (child != null) |
+ return child.getMinIntrinsicHeight(constraints); |
+ return super.getMinIntrinsicHeight(constraints); |
+ } |
+ |
+ double getMaxIntrinsicHeight(BoxConstraints constraints) { |
+ if (child != null) |
+ return child.getMaxIntrinsicHeight(constraints); |
+ return super.getMaxIntrinsicHeight(constraints); |
+ } |
+ |
+ void performLayout() { |
if (child != null) { |
+ child.layout(constraints.loosen()); |
+ size = constraints.constrain(child.size); |
assert(child.parentData is BoxParentData); |
- Rect childBounds = new Rect.fromPointAndSize(child.parentData.position, child.size); |
- if (childBounds.contains(position)) { |
- child.hitTest(result, position: new Point(position.x - child.parentData.position.x, |
- position.y - child.parentData.position.y)); |
- } |
+ Size delta = size - child.size; |
+ child.parentData.position = new Point(delta.width * horizontal, delta.height * vertical); |
+ } else { |
+ performResize(); |
} |
} |
- String debugDescribeSettings(String prefix) => '${super.debugDescribeSettings(prefix)}${prefix}padding: ${padding}\n'; |
+ String debugDescribeSettings(String prefix) => '${super.debugDescribeSettings(prefix)}${prefix}horizontal: ${horizontal}\n${prefix}vertical: ${vertical}\n'; |
} |
class RenderImage extends RenderBox { |
@@ -608,6 +701,8 @@ class RenderImage extends RenderBox { |
Size _requestedSize; |
Size get requestedSize => _requestedSize; |
void set requestedSize (Size value) { |
+ if (value == null) |
+ value = const Size(null, null); |
if (value == _requestedSize) |
return; |
_requestedSize = value; |