layout method
layout API.
Implementation
@override
PwBox layout(Context context, BoxConstraints incoming) {
final EdgeInsets outer = (margin ?? EdgeInsets.zero).resolve(
context.textDirection,
);
final EdgeInsets pad = (padding ?? EdgeInsets.zero).resolve(
context.textDirection,
);
BoxConstraints inner = incoming.deflate(outer);
final BoxConstraints? extra = constraints;
if (extra != null) {
inner = BoxConstraints(
minWidth: extra.minWidth.clamp(inner.minWidth, inner.maxWidth),
maxWidth: extra.maxWidth.clamp(inner.minWidth, inner.maxWidth),
minHeight: extra.minHeight.clamp(inner.minHeight, inner.maxHeight),
maxHeight: extra.maxHeight.clamp(inner.minHeight, inner.maxHeight),
);
}
inner = inner.tighten(width: width, height: height);
final BoxConstraints padded = inner.deflate(pad);
final Widget? kid = child;
PwBox? childBox;
if (kid != null) {
childBox = kid.layout(context, padded.loosen());
}
final PwSize childSize = childBox?.size ?? PwSize.zero;
final double contentW = childSize.width + pad.horizontal;
final double contentH = childSize.height + pad.vertical;
final bool hasFill = color != null || decoration != null;
// Match Flutter / package:pdf: alignment (or a painted fill) expands to the
// parent's max width. Height expands only when the parent tightens it
// (table cells) or sets a minHeight — never to an unbounded page leftover.
final bool expandW =
inner.hasBoundedWidth && (alignment != null || hasFill || kid == null);
final bool heightTight =
inner.hasBoundedHeight && (inner.maxHeight - inner.minHeight) < 1e-9;
final bool expandH = heightTight || inner.minHeight > contentH;
final double w = width ?? (expandW ? inner.maxWidth : contentW);
final double h = height ??
(expandH
? inner.constrainHeight(
contentH < inner.minHeight ? inner.minHeight : contentH,
)
: contentH);
final PwSize boxSize = inner.constrain(PwSize(w, h));
final PwOffset childOff;
if (childBox != null) {
final PwSize padBox = PwSize(
(boxSize.width - pad.horizontal).clamp(0, boxSize.width),
(boxSize.height - pad.vertical).clamp(0, boxSize.height),
);
final Alignment resolved =
alignment?.resolve(context.textDirection) ?? _startTop(context);
final PwOffset aligned = resolved.alongOffset(
padBox,
childSize,
);
childOff = PwOffset(pad.left + aligned.dx, pad.top + aligned.dy);
} else {
childOff = PwOffset(pad.left, pad.top);
}
return ProxyBox(
PwSize(
incoming.constrainWidth(boxSize.width + outer.horizontal),
incoming.constrainHeight(boxSize.height + outer.vertical),
),
child: childBox,
childOffset: PwOffset(outer.left + childOff.dx, outer.top + childOff.dy),
decoration: decoration ?? (color == null ? null : BoxDecoration(color: color)),
);
}