Skip to Content
HTML and CSS Intermediate: Layouts That Don't Fall Apart on Phones
Intermediate
0 likes
Courses
HTML and CSS Intermediate: Layouts That Don't Fall Apart on Phones

Fix Overlap, Overflow and Z-Index Without Guessing

Diagnose horizontal scroll, stacking contexts and overflow, and fix them with a measured change. After this, you stop raising z-index until something sticks.

Course content

Sign in to save your progress.

Course Home

Skip ahead: If you already find overflow with DevTools, fix width/min-width instead of raising z-index first, and understand stacking contexts, skip to "Z-index is not a volume knob", then continue.

Horizontal scroll on a phone is almost never "the browser being weird". Something is wider than the viewport. Overlap is a stacking problem. Randomly setting z-index: 9999 treats the symptom and creates the next bug.

Find the wide element

/* temporary diagnostic */
* { outline: 1px solid rgba(3, 75, 255, 0.25); }

Or in DevTools: inspect, watch which box sticks out past the viewport. Common culprits:

  • Fixed widths wider than the screen (width: 1200px)
  • Negative margins that pull a child out
  • pre / long URLs without wrapping
  • An absolutely positioned badge with a large left offset
img, video, canvas, svg { max-width: 100%; height: auto; }
pre, code { overflow-x: auto; max-width: 100%; }
.page { overflow-x: clip; } /* last resort after fixing the cause */

Prefer fixing the offender. Clipping the page hides the bug until a different element overflows.

Overlap from position

.badge {
  position: absolute;
  top: -8px;
  right: -8px;
}

.card {
  position: relative; /* containing block for the badge */
}

position: absolute takes the element out of normal flow. Without a positioned ancestor, it anchors to the initial containing block and can cover unexpected content. Relative on the card is the usual fix for a badge.

Z-index is not a volume knob

z-index only works on positioned elements (and flex/grid children). It compares inside a stacking context. A child with z-index: 9999 cannot escape a parent that created a context with a lower stack level.

Things that create stacking contexts include: opacity less than 1, transform, filter, position with z-index other than auto, and more. If a modal sits under a header, check contexts before inventing larger numbers.

💡 Tip: In Chrome, the Layers panel and the 3D view help, but reading the positioned ancestors in Elements is usually enough.

Common mistakes

  • z-index: 99999 on everything that misbehaves. You lose control of the stack.
  • Ignoring overflow on a flex/grid child. Add min-width: 0 (or min-height: 0) so the item may shrink below its content size.
  • Hiding overflow to "fix" a sticky header covering content. Use scroll-padding-top instead.

Flex and grid overflow gotcha

A flex item’s default min-width is auto, which means “as wide as my content”. A long unbreakable string can force the item (and the page) wider than the viewport.

.main {
  flex: 1;
  min-width: 0; /* allow shrink */
}

The same idea applies to grid items. When a column overflows for “no reason”, check min-width before you invent another media query.

A calm z-index scale

:root {
  --z-header: 10;
  --z-dropdown: 20;
  --z-modal: 30;
}
.site-header { z-index: var(--z-header); }
.modal { z-index: var(--z-modal); }

Named layers beat random five-digit numbers. When two elements fight, you compare roles, not invent larger integers.

What happens if you skip this

Every new sticky widget raises z-index again. Eventually nothing can sit above the header, including the modal that takes payment.

Try it

Force a 1200px-wide child on a phone-sized viewport. Find it in DevTools. Fix the width. Then place a badge with relative/absolute correctly.

When you type another 9 on z-index, what problem are you refusing to name?

About

Diagnose horizontal scroll, stacking contexts and overflow, and fix them with a measured change. After this, you stop raising z-index until something sticks.

Duration
5 min
Last update
08/13/2026
Was this helpful?
​ 0 ​ 0

Comments (0)

Sign in to comment

No comments yet.