layout method
layout API.
Implementation
@override
PwBox layout(Context context, BoxConstraints constraints) {
final List<(PwBox, PwOffset, Positioned?, double?, double?)> laid =
<(PwBox, PwOffset, Positioned?, double?, double?)>[];
var w = 0.0;
var h = 0.0;
final PwSize stackSizeHint = constraints.constrain(
PwSize(
constraints.hasBoundedWidth ? constraints.maxWidth : 0,
constraints.hasBoundedHeight ? constraints.maxHeight : 0,
),
);
for (final Widget child in children) {
final Positioned? pos = child is Positioned ? child : null;
final ({double? left, double? right}) pin = pos == null
? (left: null, right: null)
: pos.horizontal(context.textDirection);
final Widget inner = pos?.child ?? child;
BoxConstraints childCs = constraints.loosen();
if (pos != null) {
double? tw = pos.width;
double? th = pos.height;
if (tw == null && pin.left != null && pin.right != null) {
tw = (stackSizeHint.width - pin.left! - pin.right!).clamp(
0,
double.infinity,
);
}
if (th == null && pos.top != null && pos.bottom != null) {
th = (stackSizeHint.height - pos.top! - pos.bottom!).clamp(
0,
double.infinity,
);
}
if (tw != null || th != null) {
childCs = BoxConstraints.tightFor(width: tw, height: th);
}
}
final PwBox box = inner.layout(context, childCs);
if (box.size.width > w) {
w = box.size.width;
}
if (box.size.height > h) {
h = box.size.height;
}
laid.add((box, PwOffset.zero, pos, pin.left, pin.right));
}
if (fit == StackFit.expand && constraints.hasBoundedWidth) {
w = constraints.maxWidth;
}
if (fit == StackFit.expand && constraints.hasBoundedHeight) {
h = constraints.maxHeight;
}
// Grow stack to fit positioned right/bottom pins.
for (final (PwBox box, PwOffset _, Positioned? pos, double? left, double? right)
in laid) {
if (pos == null) {
continue;
}
if (left != null) {
final double need = left + box.size.width + (right ?? 0);
if (need > w) {
w = need;
}
}
if (pos.top != null) {
final double need = pos.top! + box.size.height + (pos.bottom ?? 0);
if (need > h) {
h = need;
}
}
}
final PwSize size = constraints.constrain(PwSize(w, h));
final List<(PwBox, PwOffset)> placed = <(PwBox, PwOffset)>[];
for (final (PwBox box, PwOffset _, Positioned? pos, double? left, double? right)
in laid) {
if (pos != null) {
final double dx =
left ??
(right != null ? size.width - box.size.width - right : 0.0);
final double dy =
pos.top ??
(pos.bottom != null
? size.height - box.size.height - pos.bottom!
: 0.0);
placed.add((box, PwOffset(dx, dy)));
} else {
placed.add((
box,
alignment.resolve(context.textDirection).alongOffset(size, box.size),
));
}
}
return GroupBox(size, placed);
}