computeContentBoxLogicalHeight method
void
computeContentBoxLogicalHeight()
Implementation
void computeContentBoxLogicalHeight() {
RenderStyle renderStyle = this;
double? logicalHeight;
CSSDisplay? effectiveDisplay = renderStyle.effectiveDisplay;
// Height applies to all elements except non-replaced inline elements.
// https://drafts.csswg.org/css-sizing-3/#propdef-height
if (effectiveDisplay == CSSDisplay.inline && !renderStyle.isSelfRenderReplaced()) {
_contentBoxLogicalHeight = null;
return;
} else {
if (renderStyle.height.isNotAuto) {
logicalHeight = renderStyle.height.computedValue;
} else if (aspectRatio != null && renderStyle.width.isNotAuto) {
// Prefer aspect-ratio when width is definite and height is auto.
double contentW = renderStyle.width.computedValue - renderStyle.border.horizontal - renderStyle.padding.horizontal;
contentW = math.max(0, contentW);
final double contentH = contentW / aspectRatio!;
logicalHeight = contentH + renderStyle.border.vertical + renderStyle.padding.vertical;
} else if (renderStyle.isSelfHTMLElement()) {
logicalHeight = renderStyle.target.ownerView.viewport!.boxSize!.height;
} else if ((renderStyle.position == CSSPositionType.absolute || renderStyle.position == CSSPositionType.fixed) &&
!renderStyle.isSelfRenderReplaced() &&
renderStyle.height.isAuto &&
renderStyle.top.isNotAuto &&
renderStyle.bottom.isNotAuto) {
// The height of positioned, non-replaced element is determined as following algorithm.
// https://www.w3.org/TR/css-position-3/#abs-non-replaced-height
if (!renderStyle.isParentRenderBoxModel()) {
logicalHeight = null;
}
// Should access the renderStyle of renderBoxModel parent but not renderStyle parent
// cause the element of renderStyle parent may not equal to containing block.
// RenderBoxModel parent = current.parent as RenderBoxModel;
// Get the renderStyle of outer scrolling box cause the renderStyle of scrolling
// content box is only a fraction of the complete renderStyle.
RenderStyle parentRenderStyle = renderStyle.getParentRenderStyle()!;
// Height of positioned element should subtract its vertical margin.
logicalHeight = (parentRenderStyle.paddingBoxLogicalHeight ?? 0) -
renderStyle.top.computedValue -
renderStyle.bottom.computedValue -
renderStyle.marginTop.computedValue -
renderStyle.marginBottom.computedValue;
} else {
CSSRenderStyle? parentRenderStyle = renderStyle.getParentRenderStyle();
if (parentRenderStyle != null) {
RenderWidgetElementChild? childWrapper = target.attachedRenderer?.findWidgetElementChild();
BoxConstraints? childWrapperConstraints;
try {
childWrapperConstraints = childWrapper?.constraints;
} catch (_) {}
// Override the default logicalHeight value is the parent is RenderWidget
if (parentRenderStyle.isSelfRenderWidget() &&
childWrapper != null &&
childWrapperConstraints != null &&
(childWrapperConstraints.maxHeight.isFinite &&
childWrapperConstraints.maxHeight != renderStyle.target.ownerView.viewport!.boxSize!.height)) {
logicalHeight = childWrapperConstraints.maxHeight;
} else if (renderStyle.isHeightStretch) {
logicalHeight = parentRenderStyle.contentBoxLogicalHeight;
}
// Should subtract vertical margin of own from its parent content height.
if (logicalHeight != null) {
logicalHeight -= renderStyle.margin.vertical;
}
}
}
}
// Get height by aspect ratio if height is auto.
if (logicalHeight == null && aspectRatio != null) {
// If a definite width is specified, prefer converting via the preferred aspect-ratio.
if (renderStyle.width.isNotAuto) {
double contentW = renderStyle.width.computedValue - renderStyle.border.horizontal - renderStyle.padding.horizontal;
contentW = math.max(0, contentW);
final double contentH = contentW / aspectRatio!;
logicalHeight = contentH + renderStyle.border.vertical + renderStyle.padding.vertical;
}
// Fallback for replaced/intrinsic scenarios.
logicalHeight ??= renderStyle.getHeightByAspectRatio();
}
// Constrain height by min-height and max-height.
if (renderStyle.minHeight.isNotAuto) {
double minHeight = renderStyle.minHeight.computedValue;
if (logicalHeight != null && logicalHeight < minHeight) {
logicalHeight = minHeight;
}
}
if (renderStyle.maxHeight.isNotNone) {
double maxHeight = renderStyle.maxHeight.computedValue;
if (logicalHeight != null && logicalHeight > maxHeight) {
logicalHeight = maxHeight;
}
}
double? logicalContentHeight;
// Subtract padding and border width to get content width.
if (logicalHeight != null) {
logicalContentHeight = logicalHeight - renderStyle.border.vertical - renderStyle.padding.vertical;
// Logical height may be smaller than its border and padding width,
// in this case, content height will be negative which is illegal.
logicalContentHeight = math.max(0, logicalContentHeight);
}
_contentBoxLogicalHeight = logicalContentHeight;
}