CSS scroll-margin-block-end Property

This property defines the margin at the end of the block axis for an element within a scroll container, affecting its snap position.

selector { scroll-margin-block-end: value; }
<length> Defines a fixed distance from the edge of the scroll snap area using standard units like px, rem, or em.

Code Examples

A basic scroll snap container where each section leaves a 50px gap at the bottom when snapped.

<style>
.container {
  width: 300px;
  height: 300px;
  overflow-y: scroll;
  scroll-snap-type: y mandatory;
  border: 2px solid #333333;
}
.section {
  height: 300px;
  scroll-snap-align: end;
  scroll-margin-block-end: 50px;
  background-color: #f0f0f0;
  border-bottom: 1px solid #cccccc;
}
</style>
<div class="container">
  <div class="section">Section 1</div>
  <div class="section">Section 2</div>
  <div class="section">Section 3</div>
</div>

An advanced example using JavaScript to dynamically set the scroll margin before programmatically scrolling an element into view.

<style>
.scroll-box {
  display: flex;
  flex-direction: column;
  height: 400px;
  overflow-y: auto;
  scroll-snap-type: y proximity;
  padding: 10px;
}
.item {
  min-height: 200px;
  margin-bottom: 20px;
  background: #0066cc;
  color: #ffffff;
  scroll-snap-align: end;
}
</style>
<div id="app-box" class="scroll-box">
  <div class="item" id="target-item">Item 1</div>
  <div class="item">Item 2</div>
  <div class="item">Item 3</div>
</div>
<button onclick="applyMargin()">Set Dynamic Margin</button>
<script>
function applyMargin() {
  const el = document.getElementById("target-item");
  el.style.scrollMarginBlockEnd = "100px";
  el.scrollIntoView({ behavior: "smooth", block: "end" });
}
</script>

Pro Tip

If you are using modern CSS layouts, stick to logical properties like this one instead of physical ones like scroll-margin-bottom. It makes your site much easier to translate into languages that read in different directions without having to rewrite your entire stylesheet.

Deep Dive

Think of this property as a buffer zone for your element. When a user scrolls and the element snaps into place, this value tells the browser to leave a specific amount of breathing room at the bottom (in standard layouts). Because it is a logical property, it follows the flow of your document. In a standard top-to-bottom layout, block-end refers to the bottom. If you change your writing mode to something vertical, the block-end will shift to the left or right. It does not change the physical layout of the page or the distance between elements; it only changes where the scroll container decides to stop when that element is the target.

Best Practices

Use this when you have sticky footers or bottom-aligned navigation bars that might overlap your content. By setting a scroll-margin-block-end, you ensure the content snaps to a position where it is fully visible and not tucked behind your UI elements. It is much cleaner than adding empty divs or invisible padding just to force a scroll gap.

Common Pitfalls

A common mistake is expecting this to push other elements away like a standard margin-bottom does. It won't. It only influences the scroll snap area. Also, remember that this property must be applied to the child element being scrolled into view, not the parent container. If your scroll-snap-type is not set on the parent, this property will appear to do nothing.

Accessibility

Ensure that the margin you set does not push the target element entirely out of the viewport on smaller screens. If the margin is too large, the user might land on a blank space instead of the content they intended to see.

Dev Data Table: scroll-margin-block-end property

default 0
animatable yes
inherited no
experimental no
year_intro 2018
year_standard 2021
js_syntax_1 element.style.scrollMarginBlockEnd = "20px";
js_syntax_2 element.style.setProperty("scroll-margin-block-end", "20px");
js_note When using JavaScript, ensure the property name is camelCased for the style object or use the kebab-case string within the setProperty method.
browsers { "Chrome": 69, "Edge": 79, "Firefox": 68, "Safari": 14.1, "Opera": 56, "Chrome Android": 69, "Safari on iOS": 14.5, "Samsung Internet": 10.1, "Opera Mobile": 48 }
results render here...