::column
The ::column
CSS pseudo-element represents the individual columns generated when a container is set to display its content in multiple columns via CSS multi-column layout. The ::column
pseudo-element enables applying styles that do not affect the layout to these generated fragments.
Syntax
::column {
/* ... */
}
Description
When CSS multi-column layout is used to lay out a container's content in multiple columns (for example, using the column-count
property), ::column
pseudo-elements are generated to contain each individual column.
The ::column
pseudo-element only accepts scroll snap properties that apply to elements inside a scroll container, including scroll-margin
, scroll-snap-align
, and scroll-snap-stop
.
The ::column
pseudo-element can have a ::scroll-marker
pseudo-element. Other pseudo-elements like ::before
and ::after
are not generated on ::column
. Applying ::column::scroll-marker
creates a marker for every column of the orginating scroll container, with the ::scroll-marker
pseudo-elements inheriting from the ::column
pseudo-element's originating element rather than the ::column
itself.
This is useful for CSS carousels — ::column
can be used to generate ::scroll-marker
pseudo-elements for each column, and set them as snap targets using CSS scroll snap.
While the styling that can be applied to ::column
is very limited, it may be expanded in the future. Any properties and values supported in the future will be limited to ones that do not affect layout.
Examples
Scrolling column layout
This demo creates a responsive container that snaps each "page" of content into place. It uses the columns
property and the ::columns
pseudo-element to create content columns that span the full width of their parent scroll container, which can be scrolled horizontally. Each column contains one or more list items, which vary in number depending on the viewport width.
HTML
The HTML consists of an unordered list, with each list item containing some sample content:
<ul>
...
<li>
<h2>Item 1</h2>
</li>
...
</ul>
CSS
The list is given a fixed height
and a width
of 100vw
to make it span the full width of the viewport. An overflow-x
value of scroll
is then set so that the content will scroll horizontally, and CSS scroll snap is used to snap to each item or "page" — a scroll-snap-type
value of x mandatory
is used to make the list into a scroll snap container. Finally, a columns
value of 1
is set to force the list contents to display as a single column. A text-align
value of center
is also applied, to align the content with the center of the list.
ul {
width: 100vw;
height: 300px;
padding: 10px;
overflow-x: scroll;
scroll-snap-type: x mandatory;
columns: 1;
text-align: center;
}
The list items are then styled:
- A
display
value ofinline-block
is set to make the list items sit alongside one another and make the list scroll horizontally. - A fixed
width
andheight
has been set on them. - A
text-align
value ofleft
is set on them to override thetext-align: center
set on the parent container, so the item content will be left-aligned. - Every even-numbered list item is given a different background-color via
:nth-child()
, so that it is easier to see the scrolling effect.
li {
list-style-type: none;
display: inline-block;
height: 100%;
width: 200px;
text-align: left;
background-color: #eee;
outline: 1px solid #ddd;
padding: 0 20px;
margin: 0 10px;
}
li:nth-child(even) {
background-color: cyan;
}
The scroll-snap-align
property is set on the ::column
pseudo-elements — which represent the content columns generated by the columns
property — so that when scrolled, a column is snapped to be centered within the scroll container.
ul::column {
scroll-snap-align: center;
}
Result
Column-based carousel with scroll markers
Expanding on the previous example, we will create scroll markers to enable direct navigation to different columns by applying a scroll-marker-group
to the container and a ::scroll-marker
to each ::column
pseudo-element. The HTML remains unchanged.
CSS
We create a scroll marker group with the scroll-marker-group
property, placing the group after all the content:
ul {
scroll-marker-group: after;
}
We then apply styles to the ::scroll-marker-group
pseudo-element to lay out the scroll markers in the center of the row with a 0.4em
gap between each one:
::scroll-marker-group {
display: flex;
gap: 0.4em;
place-content: center;
}
Finally, we use the ::scroll-marker
pseudo-element to create a round, transparent marker for each list item with a black border, then style the marker of the currently-scrolled element differently from the others, targeting the marker with the :target-current
pseudo-class:
ul::column::scroll-marker {
content: "";
width: 16px;
height: 16px;
background-color: transparent;
border: 2px solid black;
border-radius: 10px;
}
ul::column::scroll-marker:target-current {
background-color: black;
}
Result
Try pressing the scroll markers to jump straight to each page. Note how the current marker is highlighted so you can see where you are in the pagination. Also try tabbing to the scroll marker group, then use the cursor keys to cycle through each page.
See Creating CSS carousels for more carousel examples.
Specifications
Specification |
---|
CSS Multi-column Layout Module Level 2 # column-pseudo |
Browser compatibility
See also
columns
::scroll-marker
::scroll-marker-group
:target-current
- Creating CSS carousels
- CSS multi-column layout module
- CSS overflow module
- CSS Carousel Gallery via chrome.dev (2025)