Make FittedBox
not throw when child has zero size. (#150430)
fix https://github.com/flutter/flutter/issues/135082 , fix https://github.com/flutter/flutter/issues/139539 , fix https://github.com/flutter/flutter/issues/142910 Before, `FittedBox` would throw when child size is zero, unless the constraint is tight and fit is not `BoxFit.scaleDown`.
This commit is contained in:
parent
a3c7094d7d
commit
f194cd3298
@ -322,10 +322,12 @@ class BoxConstraints extends Constraints {
|
||||
return result;
|
||||
}
|
||||
|
||||
if (size.isEmpty) {
|
||||
return constrain(size);
|
||||
}
|
||||
|
||||
double width = size.width;
|
||||
double height = size.height;
|
||||
assert(width > 0.0);
|
||||
assert(height > 0.0);
|
||||
final double aspectRatio = width / height;
|
||||
|
||||
if (width > maxWidth) {
|
||||
|
@ -2711,24 +2711,6 @@ class RenderFittedBox extends RenderProxyBox {
|
||||
if (child != null) {
|
||||
final Size childSize = child!.getDryLayout(const BoxConstraints());
|
||||
|
||||
// During [RenderObject.debugCheckingIntrinsics] a child that doesn't
|
||||
// support dry layout may provide us with an invalid size that triggers
|
||||
// assertions if we try to work with it. Instead of throwing, we bail
|
||||
// out early in that case.
|
||||
bool invalidChildSize = false;
|
||||
assert(() {
|
||||
if (RenderObject.debugCheckingIntrinsics && childSize.width * childSize.height == 0.0) {
|
||||
invalidChildSize = true;
|
||||
}
|
||||
return true;
|
||||
}());
|
||||
if (invalidChildSize) {
|
||||
assert(debugCannotComputeDryLayout(
|
||||
reason: 'Child provided invalid size of $childSize.',
|
||||
));
|
||||
return Size.zero;
|
||||
}
|
||||
|
||||
switch (fit) {
|
||||
case BoxFit.scaleDown:
|
||||
final BoxConstraints sizeConstraints = constraints.loosen();
|
||||
|
@ -182,4 +182,17 @@ void main() {
|
||||
expect(constraints, const BoxConstraints(minWidth: 1, maxWidth: 2, minHeight: 3, maxHeight: 4));
|
||||
});
|
||||
|
||||
test('BoxConstraints.constrainSizeAndAttemptToPreserveAspectRatio can handle empty size', () {
|
||||
const BoxConstraints constraints = BoxConstraints(
|
||||
minWidth: 10.0,
|
||||
maxWidth: 20.0,
|
||||
minHeight: 10.0,
|
||||
maxHeight: 20.0,
|
||||
);
|
||||
const Size unconstrainedSize = Size(15.0, 0.0);
|
||||
final Size constrainedSize = constraints.constrainSizeAndAttemptToPreserveAspectRatio(
|
||||
unconstrainedSize,
|
||||
);
|
||||
expect(constrainedSize, const Size(15.0, 10.0));
|
||||
});
|
||||
}
|
||||
|
@ -605,6 +605,38 @@ void main() {
|
||||
await tester.tap(find.byType(FittedBox), warnIfMissed: false);
|
||||
expect(tester.takeException(), isNull);
|
||||
});
|
||||
|
||||
// Regression test for https://github.com/flutter/flutter/issues/135082
|
||||
testWidgets('FittedBox with zero size child does not throw', (WidgetTester tester) async {
|
||||
await tester.pumpWidget(
|
||||
const Center(
|
||||
child: SizedBox(
|
||||
height: 200.0,
|
||||
width: 200.0,
|
||||
child: FittedBox(
|
||||
fit: BoxFit.scaleDown,
|
||||
child: SizedBox.shrink(),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(tester.takeException(), isNull);
|
||||
|
||||
await tester.pumpWidget(
|
||||
Center(
|
||||
child: ConstrainedBox(
|
||||
constraints: const BoxConstraints(
|
||||
maxWidth: 200.0,
|
||||
maxHeight: 200.0,
|
||||
),
|
||||
child: const FittedBox(
|
||||
child: SizedBox.shrink(),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(tester.takeException(), isNull);
|
||||
});
|
||||
}
|
||||
|
||||
List<Type> getLayers() {
|
||||
|
Loading…
x
Reference in New Issue
Block a user