CSS Houdini's Layout API explained
Adrian Bece
Posted on July 20, 2020
This post has been originally published on Smashing Magazine and I decided to split it into parts to make it more digestible. I'll be converting the post into markdown and publish a part of it on DEV every week. If you want to read it right away in its entirety, feel free to read it on Smashing Magazine until all parts are available on DEV. Thank you.
Layout API
The Layout API allows developers to extend the browser’s layout rendering process by defining new layout
modes that can be used in display
CSS property. Layout API introduces new concepts, is very complex and
offers a lot of options for developing custom layout algorithms.
Similarly to other Worklets, the layout Worklet needs to be registered and defined first.
registerLayout('exampleLayout', class {
static get inputProperties() { return ['--exampleVariable']; }
static get childrenInputProperties() { return ['--exampleChildVariable']; }
static get layoutOptions() {
return {
childDisplay: 'normal',
sizing: 'block-like'
};
}
intrinsicSizes(children, edges, styleMap) {
/* ... */
}
layout(children, edges, constraints, styleMap, breakToken) {
/* ... */
}
});
Worklet register contains the following methods:
-
inputProperties
: An array of CSS custom properties that the Worklet will keep track of that belongs to a Parent Layout element, i.e. the element that calls this layout. This array represents dependencies of a Layout Worklet. -
childrenInputProperties
: An array of CSS custom properties that the Worklet will keep track of that belong to child elements of a Parent Layout element, i.e. the children of the elements that set this layout. -
layoutOptions
: defines the following layout properties:-
childDisplay
: can have a pre-defined value ofblock
ornormal
. Determines if the boxes will be displayed as blocks or inline. -
sizing
: can have a pre-defined value ofblock-like
ormanual
. It tells the browser to either pre-calculate the size or not to pre-calculate (unless a size is explicitly set), respectively.
-
-
intrinsicSizes
: defines how a box or its content fits into a layout context.-
children
: child elements of a Parent Layout element, i.e. the children of the element that call this layout. -
edges
: Layout Edges of a box -
styleMap
: typed OM styles of a box
-
-
layout
: the main function that performs a layout.-
children
: child elements of a Parent Layout element, i.e. the children of the element that call this layout. -
edges
: Layout Edges of a box -
constraints
: constraints of a Parent Layout -
styleMap
: typed OM styles of a box -
breakToken
: break token used to resume a layout in case of pagination or printing.
-
Like in the case of a Paint API, the browser rendering engine determines when the paint Worklet is being called. It only needs to be added to an HTML or main JavaScript file.
CSS.layoutWorklet.addModule('path/to/worklet/file.js');
And, finally, it needs to be referenced in a CSS file
.exampleElement {
display: layout(exampleLayout);
}
How Layout API Performs Layout
In the previous example, exampleLayout
has been defined using the Layout API.
.exampleElement {
display: layout(exampleLayout);
}
This element is called a Parent Layout that is enclosed with Layout Edges which
consists of paddings, borders and scroll bars. Parent Layout consists of child elements which are called
Current Layouts. Current Layouts are the actual target elements whose layout can be customized
using the Layout API. For example, when using display: flex;
on an element, its children are being
repositioned to form the flex layout. This is similar to what is being done with the Layout API.
Each Current Layout consists of Child Layout which is a layout algorithm for the
LayoutChild (element, ::before
and ::after
pseudo-elements) and
LayoutChild is a CSS generated box that only contains style data (no layout data). LayoutChild
elements are automatically created by browser rendering engine on style step. Layout Child can generate a
Fragment which actually performs layout render actions.
Example
Similarly to the Paint API example, this example is importing a masonry layout Worklet directly from Google Chrome Labs repository, but in this example, it’s used with image content instead of text. Complete source code is available on the example repository.
Feature Detection
if (CSS.layoutWorklet) {
/* ... */
}
W3C Specification Status
- First Public Working Draft: ready for community review, prone to specification change
Browser Support
Google Chrome | Microsoft Edge | Opera Browser | Firefox | Safari |
---|---|---|---|---|
Partial support (*) | Partial support (*) | Partial support (*) | Not supported | Not supported |
* supported with “Experimental Web Platform features” flag enabled.
Data source: Is Houdini Ready Yet?
These articles are fueled by coffee. So if you enjoy my work and found it useful, consider buying me a coffee! I would really appreciate it.
Thank you for taking the time to read this post. Keep an eye out for the next part in the series. If you've found this useful, please give it a ❤️ or 🦄, share and comment.
Posted on July 20, 2020
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.
Related
October 17, 2023