androidx.compose.ui.layout

Interfaces

ApproachIntrinsicMeasureScope

The receiver scope of a layout's intrinsic approach measurements lambdas.

Cmn
ApproachLayoutModifierNode

ApproachLayoutModifierNode is designed to support gradually approaching the destination layout calculated in the lookahead pass.

Cmn
ApproachMeasureScope

ApproachMeasureScope provides access to lookahead results to allow ApproachLayoutModifierNode to leverage lookahead results to define how measurements and placements approach their destination.

Cmn
BeyondBoundsLayout

Layout extra items in the specified direction.

Cmn
BeyondBoundsLayout.BeyondBoundsScope

The scope used in BeyondBoundsLayout.layout.

Cmn
BeyondBoundsLayoutProviderModifierNode

Provides a BeyondBoundsLayout through Modifier.Node APIs.

Cmn
ContentScale

Represents a rule to apply to scale a source rectangle to be inscribed into a destination

Cmn
GraphicLayerInfo

The info about the graphics layers used by tooling.

android
IntrinsicMeasurable

A part of the composition that can be measured.

Cmn
IntrinsicMeasureScope

The receiver scope of a layout's intrinsic measurements lambdas.

Cmn
LayoutCoordinates

A holder of the measured bounds for the Layout.

Cmn
LayoutIdParentData

Can be implemented by values used as parent data to make them usable as tags.

Cmn
LayoutInfo

The public information about the layouts used internally as nodes in the Compose UI hierarchy.

Cmn
LayoutModifier

A Modifier.Element that changes how its wrapped content is measured and laid out.

Cmn
LookaheadScope

LookaheadScope provides a receiver scope for all (direct and indirect) child layouts in LookaheadScope.

Cmn
Measurable

A part of the composition that can be measured.

Cmn
MeasurePolicy

Defines the measure and layout behavior of a Layout.

Cmn
MeasureResult

Interface holding the size and alignment lines of the measured layout, as well as the children positioning logic.

Cmn
MeasureScope

The receiver scope of a layout's measure lambda.

Cmn
Measured

A Measured corresponds to a layout that has been measured by its parent layout.

Cmn
MultiContentMeasurePolicy

Defines the measure and layout behavior of a Layout overload which accepts a list of multiple composable content lambdas.

Cmn
OnGloballyPositionedModifier

A modifier whose onGloballyPositioned is called with the final LayoutCoordinates of the Layout when the global position of the content may have changed.

Cmn
OnPlacedModifier

A modifier whose onPlaced is called after the parent LayoutModifier and parent layout has been placed and before child LayoutModifier is placed.

Cmn
OnRemeasuredModifier

A modifier whose onRemeasured is called when the layout content is remeasured.

Cmn
ParentDataModifier

A Modifier that provides data to the parent Layout.

Cmn
PinnableContainer

Represents a container which can be pinned when the content of this container is important.

Cmn
PinnableContainer.PinnedHandle

This is an object returned by pin which allows to release the pinning.

Cmn
RectRulers

A collection of Rulers used to define a Rectangle.

Cmn
Remeasurement

This object is associated with a layout node and allows to execute some extra measure/layout actions which are needed for some complex layouts.

Cmn
RemeasurementModifier

A Modifier.Element that provides a Remeasurement object associated with the layout node the modifier is applied to.

Cmn
RulerScope

A scope used in MeasureScope.layout for the rulers parameter to allow a layout to define Ruler values for children.

Cmn
SubcomposeLayoutState.PausedPrecomposition

A PausedPrecomposition is a subcomposition that can be composed incrementally as it supports being paused and resumed.

Cmn
SubcomposeLayoutState.PrecomposedSlotHandle

Instance of this interface is returned by precompose function.

Cmn
SubcomposeMeasureScope

The receiver scope of a SubcomposeLayout's measure lambda which adds ability to dynamically subcompose a content during the measuring on top of the features provided by MeasureScope.

Cmn
SubcomposeSlotReusePolicy

This policy allows SubcomposeLayout to retain some of slots which we were used but not used anymore instead of disposing them.

Cmn
WindowInsetsAnimation

Provides properties related to animating WindowInsetsRulers.

Cmn
WindowInsetsRulers

Contains rulers used for window insets.

Cmn

Classes

AlignmentLine

Defines an offset line that can be used by parent layouts to align and position their children.

Cmn
BeyondBoundsLayout.LayoutDirection

The direction (from the visible bounds) that a BeyondBoundsLayout is requesting more items to be laid.

Cmn
FixedScale

ContentScale implementation that always scales the dimension by the provided fixed floating point value

Cmn
HorizontalAlignmentLine

A horizontal AlignmentLine.

Cmn
HorizontalRuler

A horizontal Ruler.

Cmn
LayoutBoundsHolder

An object which holds on to a (potentially) mutating RelativeLayoutBounds of a specific node.

Cmn
ModifierInfo

Used by tooling to examine the modifiers on a LayoutInfo.

Cmn
Placeable

A Placeable corresponds to a child layout that can be positioned by its parent layout.

Cmn
Placeable.PlacementScope

Receiver scope that permits explicit placement of a Placeable.

Cmn
Ruler

A line that can be used to align layout children inside a Placeable.PlacementScope.

Cmn
ScaleFactor

Holds 2 dimensional scaling factors for horizontal and vertical axes

Cmn
SubcomposeLayoutState

State used by SubcomposeLayout.

Cmn
SubcomposeSlotReusePolicy.SlotIdsSet

Set containing slot ids currently available to reuse.

Cmn
VerticalAlignmentLine

A vertical AlignmentLine.

Cmn
VerticalRuler

A vertical Ruler.

Cmn

Objects

Annotations

Composables

Layout

Layout is the main core component for layout for "leaf" nodes.

Cmn
LookaheadScope

LookaheadScope creates a scope in which all layouts will first determine their destination layout through a lookahead pass, followed by an approach pass to run the measurement and placement approach defined in approachLayout or ApproachLayoutModifierNode, in order to gradually reach the destination.

Cmn
MultiMeasureLayout
Cmn
SubcomposeLayout

Analogue of Layout which allows to subcompose the actual content during the measuring stage for example to use the values calculated during the measurement as params for the composition of the children.

Cmn

Modifiers

approachLayout

Creates an approach layout intended to help gradually approach the destination layout calculated in the lookahead pass.

Cmn
layout

Creates a LayoutModifier that allows changing how the wrapped element is measured and laid out.

Cmn
layoutBounds

This will map the RelativeLayoutBounds of the modifier into the provided LayoutBoundsHolder.

Cmn
layoutId

Tag the element with layoutId to identify the element within its parent.

Cmn
onFirstVisible

Registers a callback to monitor when the node is first inside of the viewport of the window or not.

Cmn
onGloballyPositioned

Invoke onGloballyPositioned with the LayoutCoordinates of the element when the global position of the content may have changed.

Cmn
onLayoutRectChanged

Invokes callback with the position of this layout node relative to the coordinate system of the root of the composition, as well as in screen coordinates and window coordinates.

Cmn
onPlaced

Invoke onPlaced after the parent LayoutModifier and parent layout has been placed and before child LayoutModifier is placed.

Cmn
onSizeChanged

Invoked with the size of the modified Compose UI element when the element is first measured or when the size of the element changes.

Cmn
onVisibilityChanged

Registers a callback to monitor whether or not the node is inside of the viewport of the window or not.

Cmn

Top-level functions summary

RectRulers

Creates a RectRulers.

Cmn
inline ScaleFactor
ScaleFactor(scaleX: Float, scaleY: Float)

Constructs a ScaleFactor from the given x and y scale values

Cmn
SubcomposeSlotReusePolicy
SubcomposeSlotReusePolicy(maxSlotsToRetainForReuse: Int)

Creates SubcomposeSlotReusePolicy which retains the fixed amount of slots.

Cmn
ScaleFactor
lerp(start: ScaleFactor, stop: ScaleFactor, fraction: Float)

Linearly interpolate between two ScaleFactor parameters

Cmn
DelegatableNode
onVisibilityChangedNode(
    minDurationMs: @IntRange(from = 0) Long,
    minFractionVisible: @FloatRange(from = 0.0, to = 1.0) Float,
    viewportBounds: LayoutBoundsHolder?,
    callback: (Boolean) -> Unit
)

Creates a DelegatableNode for a modifier node, implementing the contract of onVisibilityChanged Modifier.

Cmn

Extension functions summary

Rect

Returns the bounding box of the child in the parent's content area, including any clipping done with respect to the parent.

Cmn
Rect

The boundaries of this layout inside the root composable.

Cmn
Rect

The boundaries of this layout relative to the window's origin.

Cmn
operator Size
Size.div(scaleFactor: ScaleFactor)

Division operator with Size

Cmn
LayoutCoordinates

Walks up the LayoutCoordinates hierarchy to find the LayoutCoordinates whose LayoutCoordinates.parentCoordinates is null and returns it.

Cmn
List<RectRulers>

Returns a List of RectRulers, one RectRulers for each display cutout.

Cmn
RectRulers

Merges multiple RectRulers into a single RectRulers, using the inner-most value.

Cmn
LayoutCoordinates

Obtains the LayoutCoordinates for the given LookaheadScope using a LayoutCoordinates within the LookaheadScope.

Cmn
RectRulers

Merges multiple RectRulers into a single RectRulers, using the outer-most value.

Cmn
Offset

Returns the position of the top-left in the parent's content area or (0, 0) for the root.

Cmn
Offset

The position of this layout inside the root composable.

Cmn
Offset

The position of this layout relative to the window.

Cmn
Offset

The position of this layout on the device's screen.

Cmn
DelegatableNode.RegistrationHandle
DelegatableNode.registerOnGlobalLayoutListener(
    throttleMillis: Long,
    debounceMillis: Long,
    callback: (RelativeLayoutBounds) -> Unit
)

Registers a callback to be executed with the position of this modifier node relative to the coordinate system of the root of the composition, as well as in screen coordinates and window coordinates, see RelativeLayoutBounds.

Cmn
DelegatableNode.RegistrationHandle
DelegatableNode.registerOnLayoutRectChanged(
    throttleMillis: Long,
    debounceMillis: Long,
    callback: (RelativeLayoutBounds) -> Unit
)

Registers a callback to be executed with the position of this modifier node relative to the coordinate system of the root of the composition, as well as in screen coordinates and window coordinates.

Cmn
inline ScaleFactor

If this ScaleFactor then this is returned, otherwise block is executed and its result is returned.

Cmn
operator Size
Size.times(scaleFactor: ScaleFactor)

Multiplication operator with Size.

Cmn
operator Size

Multiplication operator with Size with reverse parameter types to maintain commutative properties of multiplication

Cmn

Top-level properties summary

HorizontalAlignmentLine

AlignmentLine defined by the baseline of a first line of a androidx.compose.foundation.text.BasicText

Cmn
HorizontalAlignmentLine

AlignmentLine defined by the baseline of the last line of a androidx.compose.foundation.text.BasicText

Cmn
ProvidableCompositionLocal<PinnableContainer?>

Use this composition local to get the PinnableContainer handling the current subhierarchy.

Cmn
ProvidableModifierLocal<BeyondBoundsLayout?>

A modifier local that provides access to a BeyondBoundsLayout that a child can use to ask a parent to layout more items that are beyond its visible bounds.

Cmn

Extension properties summary

Boolean

false when this is ScaleFactor.Unspecified.

Cmn
Boolean

true when this is ScaleFactor.Unspecified.

Cmn
Any?

Retrieves the tag associated to a composable with the Modifier.layoutId modifier.

Cmn
View?

Return the owner as a View from the associated LayoutNode.

android

Top-level functions

RectRulers

fun RectRulers(): RectRulers

Creates a RectRulers.

ScaleFactor

inline fun ScaleFactor(scaleX: Float, scaleY: Float): ScaleFactor

Constructs a ScaleFactor from the given x and y scale values

SubcomposeSlotReusePolicy

fun SubcomposeSlotReusePolicy(maxSlotsToRetainForReuse: Int): SubcomposeSlotReusePolicy

Creates SubcomposeSlotReusePolicy which retains the fixed amount of slots.

Parameters
maxSlotsToRetainForReuse: Int

the SubcomposeLayout will retain up to this amount of slots.

lerp

fun lerp(start: ScaleFactor, stop: ScaleFactor, fraction: Float): ScaleFactor

Linearly interpolate between two ScaleFactor parameters

The fraction argument represents position on the timeline, with 0.0 meaning that the interpolation has not started, returning start (or something equivalent to start), 1.0 meaning that the interpolation has finished, returning stop (or something equivalent to stop), and values in between meaning that the interpolation is at the relevant point on the timeline between start and stop. The interpolation can be extrapolated beyond 0.0 and 1.0, so negative values and values greater than 1.0 are valid (and can easily be generated by curves).

Values for fraction are usually obtained from an Animation, such as an AnimationController.

onVisibilityChangedNode

fun onVisibilityChangedNode(
    minDurationMs: @IntRange(from = 0) Long = 0,
    minFractionVisible: @FloatRange(from = 0.0, to = 1.0) Float = 1.0f,
    viewportBounds: LayoutBoundsHolder? = null,
    callback: (Boolean) -> Unit
): DelegatableNode

Creates a DelegatableNode for a modifier node, implementing the contract of onVisibilityChanged Modifier. Such a node could be delegated to as part of a custom modifier node via androidx.compose.ui.node.DelegatingNode.delegate. In most of the cases users should just use onVisibilityChanged Modifier directly.

Note that if you need to update some of the params, it is recommended to androidx.compose.ui.node.DelegatingNode.undelegate the previous node, and delegate again to a new one with the correct values.

Registers a callback to monitor whether or not the node is inside of the viewport of the window or not. Example use cases for this include, auto-playing videos in a feed, logging how long an item was visible, and starting/stopping animations.

Parameters
minDurationMs: @IntRange(from = 0) Long = 0

the amount of time in milliseconds that this node should be considered visible before invoking the callback with (true). Depending on your use case, it might be useful to provide a non-zero number here if it is desirable to avoid triggering the callback on elements during really fast scrolls where they went from visible to invisible in a really short amount of time.

minFractionVisible: @FloatRange(from = 0.0, to = 1.0) Float = 1.0f

the fraction of the node which should be inside the viewport for the callback to get called with a value of true. A value of 1f means that the entire bounds of the rect need to be inside of the viewport, or that the rect fills 100% of the viewport. A value of 0f means that this will get triggered as soon as a non-zero amount of pixels are inside of the viewport.

viewportBounds: LayoutBoundsHolder? = null

a reference to the bounds to use as a "viewport" with which to calculate the amount of visibility this element has inside of that viewport. This is most commonly used to account for UI elements such as navigation bars which are drawn on top of the content that this modifier is applied to. It is required that this be passed in to a layoutBounds somewhere else in order for this parameter to get used properly. If null is provided, the window of the application will be used as the viewport.

callback: (Boolean) -> Unit

lambda that is invoked when the fraction of this node inside of the specified viewport crosses the minFractionVisible. The boolean argument passed into this lambda will be true in cases where the fraction visible is greater, and false when it is not.

Extension functions

LayoutCoordinates.boundsInParent

fun LayoutCoordinates.boundsInParent(): Rect

Returns the bounding box of the child in the parent's content area, including any clipping done with respect to the parent. For the root, the bounds is positioned at (0, 0) and sized to the size of the root.

LayoutCoordinates.boundsInRoot

fun LayoutCoordinates.boundsInRoot(): Rect

The boundaries of this layout inside the root composable.

LayoutCoordinates.boundsInWindow

fun LayoutCoordinates.boundsInWindow(clipBounds: Boolean = true): Rect

The boundaries of this layout relative to the window's origin.

Parameters
clipBounds: Boolean = true

Whether to clip the bounds of the layout to the window's boundaries. If true, any clipping that occurs between this layout and the window will affect the returned bounds, and can even result in an empty rectangle if clipped regions do not overlap. If false, the bounding box of this layout will be converted to window coordinates irrespective of any clipping applied. Defaults to true.

Returns
Rect

A Rect representing the bounding box of this LayoutCoordinates in the window's coordinate space. If the bounds are completely clipped, returns Rect.Zero.

Size.div

operator fun Size.div(scaleFactor: ScaleFactor): Size

Division operator with Size

Return a new Size with the width and height divided by ScaleFactor.scaleX and ScaleFactor.scaleY respectively

LayoutCoordinates.findRootCoordinates

fun LayoutCoordinates.findRootCoordinates(): LayoutCoordinates

Walks up the LayoutCoordinates hierarchy to find the LayoutCoordinates whose LayoutCoordinates.parentCoordinates is null and returns it. If LayoutCoordinates.isAttached, this will have the size of the androidx.compose.ui.platform.ComposeView.

Placeable.PlacementScope.getDisplayCutoutBounds

fun Placeable.PlacementScope.getDisplayCutoutBounds(): List<RectRulers>

Returns a List of RectRulers, one RectRulers for each display cutout. Each RectRulers provides values for the bounds of the display cutout. WindowInsetsRulers.DisplayCutout provides the safe inset values for content avoiding all display cutouts.

RectRulers.Companion.innermostOf

fun RectRulers.Companion.innermostOf(vararg rulers: RectRulers): RectRulers

Merges multiple RectRulers into a single RectRulers, using the inner-most value. That is, the RectRulers.left will be the greatest RectRulers.left, the RectRulers.top will be the greatest RectRulers.top, the RectRulers.right will be the least RectRulers.right, and the RectRulers.bottom will be the least of all rulers.

When rulers provide non-overlapping values, the result may have negative size. For example, if one RectRulers provides (10, 20, 30, 40) as their ruler values, and another provides (1, 1, 5, 5), the merged result will be (10, 20, 5, 5).

If one of the rulers does not provide a value, it will not be considered in the calculation.

LookaheadScope.lookaheadScopeCoordinates

fun LookaheadScope.lookaheadScopeCoordinates(
    sourceCoordinates: LayoutCoordinates
): LayoutCoordinates

Obtains the LayoutCoordinates for the given LookaheadScope using a LayoutCoordinates within the LookaheadScope.

Important: This must be an actual LayoutCoordinates instance from the PlacementScope or Modifier APIs. The Layout that associates with the coordinates needs to be within the subtree of the LookaheadScope. Using a custom LayoutCoordinates implementation will result in an IllegalArgumentException.

Parameters
sourceCoordinates: LayoutCoordinates

A LayoutCoordinates within the subtree of the given LookaheadScope.

RectRulers.Companion.outermostOf

fun RectRulers.Companion.outermostOf(vararg rulers: RectRulers): RectRulers

Merges multiple RectRulers into a single RectRulers, using the outer-most value. That is, the RectRulers.left will be the least RectRulers.left, the RectRulers.top will be the least RectRulers.top, the RectRulers.right will be the greatest RectRulers.right, and the RectRulers.bottom will be the greatest of all rulers.

If one of the rulers does not provide a value, it will not be considered in the calculation.

LayoutCoordinates.positionInParent

fun LayoutCoordinates.positionInParent(): Offset

Returns the position of the top-left in the parent's content area or (0, 0) for the root.

LayoutCoordinates.positionInRoot

fun LayoutCoordinates.positionInRoot(): Offset

The position of this layout inside the root composable.

LayoutCoordinates.positionInWindow

fun LayoutCoordinates.positionInWindow(): Offset

The position of this layout relative to the window.

LayoutCoordinates.positionOnScreen

fun LayoutCoordinates.positionOnScreen(): Offset

The position of this layout on the device's screen. Returns Offset.Unspecified if the conversion cannot be performed.

DelegatableNode.registerOnGlobalLayoutListener

fun DelegatableNode.registerOnGlobalLayoutListener(
    throttleMillis: Long,
    debounceMillis: Long,
    callback: (RelativeLayoutBounds) -> Unit
): DelegatableNode.RegistrationHandle

Registers a callback to be executed with the position of this modifier node relative to the coordinate system of the root of the composition, as well as in screen coordinates and window coordinates, see RelativeLayoutBounds.

It may also be used to calculate certain Layout relationships at the time of the callback execution, such as RelativeLayoutBounds.calculateOcclusions.

This will be called after layout pass. This API allows for throttling and debouncing parameters in order to moderate the frequency with which the callback gets invoked during high rates of change (e.g. scrolling).

Specifying throttleMillis will prevent callback from being executed more than once over that time period. Specifying debounceMillis will delay the execution of callback until that amount of time has elapsed without a new position.

Specifying 0 for both throttleMillis and debounceMillis will result in the callback being executed every time the position has changed. Specifying non-zero amounts for both will result in both conditions being met.

Parameters
throttleMillis: Long

The duration, in milliseconds, to prevent callback from being executed more than once over that time period.

debounceMillis: Long

The duration, in milliseconds, to delay the execution of callback until that amount of time has elapsed without a new position.

callback: (RelativeLayoutBounds) -> Unit

The callback to be executed, provides a new RelativeLayoutBounds instance associated to this DelegatableNode. Keep in mind this callback is executed on the main thread even when debounced.

Returns
DelegatableNode.RegistrationHandle

an object which should be used to unregister/dispose this callback, such as when a node is detached

DelegatableNode.registerOnLayoutRectChanged

fun DelegatableNode.registerOnLayoutRectChanged(
    throttleMillis: Long,
    debounceMillis: Long,
    callback: (RelativeLayoutBounds) -> Unit
): DelegatableNode.RegistrationHandle

Registers a callback to be executed with the position of this modifier node relative to the coordinate system of the root of the composition, as well as in screen coordinates and window coordinates. This will be called after layout pass. This API allows for throttling and debouncing parameters in order to moderate the frequency with which the callback gets invoked during high rates of change (e.g. scrolling).

Specifying throttleMillis will prevent callback from being executed more than once over that time period. Specifying debounceMillis will delay the execution of callback until that amount of time has elapsed without a new position.

Specifying 0 for both throttleMillis and debounceMillis will result in the callback being executed every time the position has changed. Specifying non-zero amounts for both will result in both conditions being met.

Parameters
throttleMillis: Long

The duration, in milliseconds, to prevent callback from being executed more than once over that time period.

debounceMillis: Long

The duration, in milliseconds, to delay the execution of callback until that amount of time has elapsed without a new position.

callback: (RelativeLayoutBounds) -> Unit

The callback to be executed.

Returns
DelegatableNode.RegistrationHandle

an object which should be used to unregister/dispose this callback

ScaleFactor.takeOrElse

inline fun ScaleFactor.takeOrElse(block: () -> ScaleFactor): ScaleFactor

If this ScaleFactor then this is returned, otherwise block is executed and its result is returned.

Size.times

operator fun Size.times(scaleFactor: ScaleFactor): Size

Multiplication operator with Size.

Return a new Size with the width and height multiplied by the ScaleFactor.scaleX and ScaleFactor.scaleY respectively

ScaleFactor.times

operator fun ScaleFactor.times(size: Size): Size

Multiplication operator with Size with reverse parameter types to maintain commutative properties of multiplication

Return a new Size with the width and height multiplied by the ScaleFactor.scaleX and ScaleFactor.scaleY respectively

Top-level properties

FirstBaseline

val FirstBaselineHorizontalAlignmentLine

AlignmentLine defined by the baseline of a first line of a androidx.compose.foundation.text.BasicText

LastBaseline

val LastBaselineHorizontalAlignmentLine

AlignmentLine defined by the baseline of the last line of a androidx.compose.foundation.text.BasicText

LocalPinnableContainer

val LocalPinnableContainerProvidableCompositionLocal<PinnableContainer?>

Use this composition local to get the PinnableContainer handling the current subhierarchy.

It will be not null, for example, when the current content is composed as an item of lazy list.

ModifierLocalBeyondBoundsLayout

val ModifierLocalBeyondBoundsLayoutProvidableModifierLocal<BeyondBoundsLayout?>

A modifier local that provides access to a BeyondBoundsLayout that a child can use to ask a parent to layout more items that are beyond its visible bounds.

Extension properties

ScaleFactor.isSpecified

val ScaleFactor.isSpecifiedBoolean

false when this is ScaleFactor.Unspecified.

ScaleFactor.isUnspecified

val ScaleFactor.isUnspecifiedBoolean

true when this is ScaleFactor.Unspecified.

Measurable.layoutId

val Measurable.layoutIdAny?

Retrieves the tag associated to a composable with the Modifier.layoutId modifier. For a parent data value to be returned by this property when not using the Modifier.layoutId modifier, the parent data value should implement the LayoutIdParentData interface.

Example usage:

import androidx.compose.foundation.layout.Box
import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.Layout
import androidx.compose.ui.layout.layout
import androidx.compose.ui.layout.layoutId
import androidx.compose.ui.unit.Constraints

Layout({
    // Here the Containers are only needed to apply the modifiers. You could use the
    // modifier on header and footer directly if they are composables accepting modifiers.
    Box(Modifier.layoutId("header")) { header() }
    Box(Modifier.layoutId("footer")) { footer() }
}) { measurables, constraints ->
    val placeables =
        measurables.map { measurable ->
            when (measurable.layoutId) {
                // You should use appropriate constraints. Here we measure fake constraints.
                "header" -> measurable.measure(Constraints.fixed(100, 100))
                "footer" -> measurable.measure(constraints)
                else -> error("Unexpected tag")
            }
        }
    // Size should be derived from children measured sizes on placeables,
    // but this is simplified for the purposes of the example.
    layout(100, 100) { placeables.forEach { it.placeRelative(0, 0) } }
}

LayoutInfo.view

val LayoutInfo.viewView?

Return the owner as a View from the associated LayoutNode.