CSS Position Property Explained
Understand CSS positioning — static, relative, absolute, fixed, and sticky. Learn when to use each type with visual examples and practical patterns.
CSS Position Property Explained
The position property controls how an element is placed in the document. It's one of the most misunderstood CSS properties — but once you get it, a lot of layouts suddenly make sense.
The Five Position Values
static (Default)
Every element is position: static by default. It flows normally in the document.
.element {
position: static; /* default — you never need to write this */
}
top, right, bottom, left, and z-index have no effect on static elements.
relative
The element stays in its normal position, but you can nudge it with top/right/bottom/left:
.element {
position: relative;
top: 10px; /* moves down 10px from where it would be */
left: 20px; /* moves right 20px from where it would be */
}
Key point: The element's original space in the layout is preserved. Other elements don't move.
Most common use: As a positioning context for absolute children.
absolute
The element is removed from the normal flow and positioned relative to its nearest positioned ancestor (any ancestor with position other than static):
.parent {
position: relative; /* creates positioning context */
}
.child {
position: absolute;
top: 0;
right: 0; /* child sits in parent's top-right corner */
}
If no positioned ancestor exists, it positions relative to the <body>.
Common uses:
- Badges/labels on cards
- Dropdown menus
- Tooltips
- Overlay elements
fixed
Like absolute, but positioned relative to the viewport. It stays in place when you scroll:
.navbar {
position: fixed;
top: 0;
left: 0;
right: 0;
z-index: 100;
}
Common uses:
- Fixed navigation bars
- Floating action buttons
- Cookie consent banners
- Chat widgets
sticky
A hybrid of relative and fixed. The element is relative until it reaches a scroll threshold, then becomes fixed:
.section-header {
position: sticky;
top: 0; /* sticks when scrolled to top of viewport */
}
Important: Sticky elements need a scrolling container and a threshold (top, bottom, etc.) to work.
Common uses:
- Table headers that stay visible while scrolling
- Section headers in long lists
- Sidebar that sticks on scroll
Positioning Context
Understanding positioning context is crucial:
absoluteelements look for the nearest ancestor withposition: relative,absolute,fixed, orsticky- If none is found, they use the document body
relativeon a parent creates a positioning context without moving the parent
/* Pattern: parent is relative, child is absolute */
.card {
position: relative;
}
.card .badge {
position: absolute;
top: -8px;
right: -8px;
}
z-index — Stacking Order
z-index only works on positioned elements (not static):
.dropdown {
position: absolute;
z-index: 10; /* above normal content */
}
.modal-overlay {
position: fixed;
z-index: 100; /* above dropdown */
}
.modal {
position: fixed;
z-index: 101; /* above overlay */
}
Stacking Context
A new stacking context is created by:
position: relative/absolute/fixedwithz-indexsetopacityless than 1transform,filter,perspective
Elements are stacked within their own context. A z-index: 9999 inside one context can't beat a z-index: 1 in a higher context.
Common Patterns
Centering with Absolute Position
.centered {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
This centers the element both horizontally and vertically within its positioned parent.
Full-Screen Overlay
.overlay {
position: fixed;
inset: 0; /* same as top: 0; right: 0; bottom: 0; left: 0 */
background: rgba(0, 0, 0, 0.5);
z-index: 50;
}
Badge on a Card
.card {
position: relative;
}
.badge {
position: absolute;
top: -6px;
right: -6px;
background: red;
color: white;
border-radius: 50%;
width: 20px;
height: 20px;
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
}
Sticky Table Header
table thead th {
position: sticky;
top: 0;
background: white;
z-index: 1;
}
Quick Reference
| Position | In Flow? | Positioned By | Scrolls With |
|---|---|---|---|
| static | Yes | N/A | Document |
| relative | Yes | Self | Document |
| absolute | No | Nearest positioned ancestor | Positioned ancestor |
| fixed | No | Viewport | Nothing (stays put) |
| sticky | Yes → No | Self + scroll threshold | Until threshold |
Key Takeaways
- Use
relativeon parents to create positioning context forabsolutechildren absoluteremoves from flow;relativekeeps in flowfixedstays visible during scroll — use for navbars and modalsstickyis the best of both worlds — use for table headers and section titlesz-indexonly works on positioned elements- Use
inset: 0as shorthand fortop: 0; right: 0; bottom: 0; left: 0
🚀 Practice What You Learned
Apply these concepts with hands-on coding challenges: