scroll-padding-left

Creates a scroll-only inset on the left side of a scroll container. Every element inside it comes to rest that far from the left edge when scrolled into view. Unlike real padding, the layout itself does not change at all.

Class List

Pattern: spl{value}{unit}

ClassCSSDescription
spl0scroll-padding-left: 0No scroll padding
spl8pxscroll-padding-left: 8px8px padding
spl16pxscroll-padding-left: 16px16px padding
spl2remscroll-padding-left: 2rem20px padding
spl4remscroll-padding-left: 4rem40px padding

Live Demo

This time the class goes on the container, not on the cards. Each button resets the container and scrolls the blue card into view aligned to the start. The larger the value, the more room is left on the left.

1
2
3
4
5
6
Target
8
9
10
11
12
13
14

One value on the container adjusts the resting position of every item, with no per-card classes. The container's real padding is untouched, so nothing is pushed around or clipped.

Class Details

spl0scroll-padding-left: 0

Resets the scroll padding to zero. Use it to cancel an inset that a shared component or ancestor class applied, for one specific scroll area.

<!-- Explicit default: snapped cards line up with the container edge -->
<div class="spl0 sstxm df oxa gap16px">
  <div class="ssas fs0 w28rem">Card 1</div>
  <div class="ssas fs0 w28rem">Card 2</div>
</div>

spl8pxscroll-padding-left: 8px

8px. The smallest inset that keeps borders and focus rings from being clipped. Suits dense horizontal rows such as filter chip bars.

<!-- Chip filter bar: a hair of inset so borders are never clipped -->
<div class="spl8px sstxm df oxa gap8px py8px">
  <button class="ssas fs0 py8px px16px br999px">All</button>
  <button class="ssas fs0 py8px px16px br999px">New</button>
</div>

spl16pxscroll-padding-left: 16px

16px. Gives a 16px carousel the same inset from one place on the container, instead of repeating a scroll-margin on every item.

<!-- Every card gets a 16px inset without repeating a class per card -->
<div class="spl16px sstxm df oxa gap16px">
  <article class="ssas fs0 w28rem">Card 1</article>
  <article class="ssas fs0 w28rem">Card 2</article>
  <article class="ssas fs0 w28rem">Card 3</article>
</div>

spl2remscroll-padding-left: 2rem

20px. In a section with 20px horizontal padding, this lines snapped cards up with the start of the section heading.

<!-- Align snapped cards with the section heading above the scroller -->
<section class="px2rem">
  <h2>Continue watching</h2>
  <div class="spl2rem sstxm df oxa gap16px">
    <article class="ssas fs0 w28rem">Item 1</article>
    <article class="ssas fs0 w28rem">Item 2</article>
  </div>
</section>

spl4remscroll-padding-left: 4rem

40px. When a 40px icon rail or fixed sidebar overlaps the scroll area, this pushes every snap position inward so nothing lands underneath it.

<!-- A 40px icon rail overlaps the scroller: inset every snap position -->
<div class="pr">
  <nav class="pa t0 l0 w4rem h100p bg18181B"></nav>
  <div class="spl4rem sstxm df oxa gap16px pl4rem">
    <article class="ssas fs0 w28rem">Card 1</article>
    <article class="ssas fs0 w28rem">Card 2</article>
  </div>
</div>

Usage Examples

<!-- Horizontal scroller behind a fixed sidebar -->
<aside class="pf t0 l0 w25rem h100vh bg18181B">Sidebar</aside>

<div class="spl4rem sstxm df oxa gap16px">
  <div class="ssas fs0 w28rem bg18181B p2rem br8px">Card 1</div>
  <div class="ssas fs0 w28rem bg18181B p2rem br8px">Card 2</div>
</div>

Practical example: horizontal media row in a streaming UI

One scroll-padding on the container replaces a scroll-margin class on every tile, and the same inset applies to keyboard focus moves and anchor jumps.

<!-- Media row in a streaming UI. One scroll-padding on the container
     replaces a scroll-margin class on every single tile, and the same
     inset applies to keyboard focus and to anchor jumps. -->
<section class="px2rem py2rem">
  <h2 class="fs2rem fw700 cFAFAFA mb16px">Trending now</h2>

  <div class="spl2rem spr2rem sstxm obxc swn df oxa gap12px">
    <a href="#t1" id="t1" class="ssas fs0 w28rem br8px oh bg18181B tdn">
      <img src="/poster-1.jpg" alt="" class="w100p h16rem ofc">
      <p class="p12px fs14px cFAFAFA">Title 1</p>
    </a>
    <a href="#t2" id="t2" class="ssas fs0 w28rem br8px oh bg18181B tdn">
      <img src="/poster-2.jpg" alt="" class="w100p h16rem ofc">
      <p class="p12px fs14px cFAFAFA">Title 2</p>
    </a>
  </div>
</section>

Pitfalls

It is not layout padding

scroll-padding is a virtual inset used only when computing where scrolling stops. To actually push the content in, add a normal padding class such as pl2rem as well.

It belongs on the container

Put it on the element that actually scrolls, the one carrying an overflow class such as oxa. On a child card it does nothing, and what you want there is scroll-margin-left.

Only consulted when something scrolls into view

It applies to anchor navigation, scrollIntoView, and scroll snapping. Manual scrolling is never constrained by it.