Domina los positions en CSS: static, relative, absolute, fixed y sticky
Antes de empezar
El position en CSS es una de las propiedades más importantes para controlar dónde aparecen los elementos en tu página. Te va a permitir crear headers fijos, elementos flotantes, overlays y mucho más.
En este ejemplo interactivo puedes ver todos los tipos de position en acción. ¡Haz scroll para ver cómo funciona el sticky!
Pulsa el botón que aparece debajo, RUN PROJECT
Los 5 tipos de position
1. position: static (el valor por defecto)
Es el comportamiento normal de todos los elementos HTML. No hace nada especial.
.box-static {
/* position: static; - No hace falta escribirlo, es por defecto */
background: #8ed1fc;
}
Características:
- Los elementos aparecen en el orden que están en el HTML
- No responde a
top,left,right,bottom - Sigue el flujo normal de la página
- No se puede superponer a otros elementos
Cuándo usarlo: Prácticamente siempre, es el comportamiento normal. Solo cambias el position cuando necesitas algo específico.
2. position: relative
El elemento se mueve desde su posición original, pero reserva su espacio.
.box-relative {
position: relative;
left: 30px; /* Se mueve 30px a la derecha */
top: 10px; /* Se mueve 10px hacia abajo */
background: #fd98a8;
}
Características:
- Mantiene su espacio en el flujo normal
- Puedes moverlo con
top,left,right,bottom - Punto de referencia para hijos con
position: absolute - No afecta a otros elementos
Cuándo usarlo:
- Para ajustes pequeños de posición
- Como contenedor para elementos absolute
- Para crear efectos de hover sutiles
/* Ejemplo: efecto hover sutil */
.card {
position: relative;
transition: top .2s linear;
}
.card:hover {
top: -2px; /* Se eleva ligeramente */
}
3. position: absolute
El elemento se sale completamente del flujo (no ocupa espacio) y se posiciona respecto a su contenedor posicionado más cercano.
.relative-container {
position: relative; /* Punto de referencia */
height: 180px;
}
.box-absolute {
position: absolute;
top: 20px; /* 20px desde arriba del contenedor */
right: 20px; /* 20px desde la derecha del contenedor */
background: #00edb1;
}
Características:
- No ocupa espacio en el flujo normal
- Se posiciona respecto al primer padre con position (que no sea static)
- Si no encuentra un padre posicionado, se posiciona respecto al viewport
- Puede superponerse a otros elementos
Cuándo usarlo:
- Tooltips y elementos emergentes
- Iconos sobre imágenes
- Overlays y modales
- Elementos decorativos
/* Ejemplo: tooltip */
.tooltip {
position: relative;
}
.tooltip-text {
position: absolute;
top: -30px;
left: 50%;
transform: translateX(-50%);
background: black;
color: white;
padding: 5px;
border-radius: 4px;
}
4. position: fixed
El elemento se fija respecto al viewport (la ventana del navegador) y siempre permanece visible.
.fixed-header {
position: fixed;
top: 0; /* Pegado arriba */
left: 0; /* Pegado a la izquierda */
width: 100%; /* Ancho completo */
background: #282828;
z-index: 999; /* Por encima de otros elementos */
}
.fixed-button {
position: fixed;
bottom: 15px; /* 15px desde abajo */
right: 15px; /* 15px desde la derecha */
background: #219ebc;
}
Características:
- Siempre visible, no se mueve con el scroll
- Se posiciona respecto al viewport, no a ningún contenedor
- No ocupa espacio en el flujo normal
- Perfecto para elementos que siempre deben estar accesibles
Cuándo usarlo:
- Headers y navbars fijos
- Botones flotantes (chat, “volver arriba”)
- Notificaciones persistentes
- Sidebars fijos
⚠️ Cuidado: Recuerda dejar espacio en el body para que el contenido no quede tapado por elementos fixed.
body {
padding-top: 60px; /* Altura del header fijo */
}
5. position: sticky
Es una mezcla entre relative y fixed. Se comporta como relative hasta que llega a cierta posición, entonces se “pega” como fixed.
.sticky-bar {
position: sticky;
top: 70px; /* Se pega cuando esté a 70px del top */
background: #dea325;
}
Características:
- Hybrid behavior: relative + fixed
- Solo se activa cuando el scroll llega al threshold definido
- Mantiene su espacio en el flujo (como relative)
- Se pega solo dentro de su contenedor padre
Cuándo usarlo:
- Menús que se fijan al hacer scroll
- Headers de tablas que permanecen visibles
- Sidebars que se fijan en cierto punto
- Call-to-actions que aparecen al scrollear
Ejemplo práctico:
/* Navbar que se fija después del hero */
.navbar {
position: sticky;
top: 0;
background: white;
box-shadow: 0 2px 4px rgba(0,0,0,0.1);
}
Conceptos importantes
Z-index: controlando las capas
Cuando tienes elementos superpuestos, z-index controla cuál aparece encima:
.modal-overlay {
position: fixed;
z-index: 9; /* Fondo del modal */
}
.modal-content {
position: fixed;
z-index: 99; /* Contenido por encima */
}
.tooltip {
position: absolute;
z-index: 999; /* Tooltips por encima de todo */
}
Reglas del z-index:
- Solo funciona en elementos posicionados (no static)
- Números más altos = más arriba
- Los hijos nunca pueden estar por encima de su padre
- Sin z-index, el último en el HTML queda encima
Contenedor de referencia
Para position: absolute, es crucial entender cuál es su punto de referencia:
/* ❌ Problemático: se posiciona respecto al viewport */
.card {
/* position: static por defecto */
}
.card-badge {
position: absolute;
top: 10px; /* ¡Se posiciona respecto a toda la página! */
right: 10px;
}
/* ✅ Correcto: contenedor de referencia */
.card {
position: relative; /* Ahora es el punto de referencia */
}
.card-badge {
position: absolute;
top: 10px; /* Respecto a .card */
right: 10px;
}
Casos de uso comunes
Header fijo con navegación
.header {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 60px;
background: white;
box-shadow: 0 2px 4px rgba(0,0,0,0.1);
z-index: 99;
}
body {
padding-top: 60px; /* Compensa la altura del header */
}
Modal centrado
.modal-overlay {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgba(0,0,0,0.5);
display: flex;
justify-content: center;
align-items: center;
z-index: 999;
}
.modal-content {
position: relative; /* Para el botón de cerrar */
background: white;
padding: 2rem;
border-radius: 8px;
max-width: 500px;
width: 90%;
}
.modal-close {
position: absolute;
top: 10px;
right: 10px;
}
Sidebar sticky
.sidebar {
position: sticky;
top: 80px; /* Debajo del header fijo */
height: calc(100vh - 80px);
overflow-y: auto;
}
Badge sobre imagen
.image-container {
position: relative;
display: inline-block;
}
.badge {
position: absolute;
top: -8px;
right: -8px;
background: red;
color: white;
border-radius: 50%;
width: 20px;
height: 20px;
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
}
Experimenta con el código
Pulsa el botón que aparece debajo, RUN PROJECT
Prueba estos experimentos:
- Cambia el
topdel sticky - ¿Qué pasa si ponestop: 0? - Modifica las coordenadas del absolute - Prueba con
bottomyleft - Juega con el z-index - ¿Puedes hacer que el botón fijo aparezca detrás?
- Agrega más elementos sticky - ¿Qué pasa si hay varios?
Errores comunes y cómo evitarlos
❌ Error 1: Absolute sin contenedor
/* Problemático */
.card-icon {
position: absolute;
top: 10px;
right: 10px;
/* Se posiciona respecto al viewport, no a la card */
}
/* Solución */
.card {
position: relative; /* Contenedor de referencia */
}
.card-icon {
position: absolute;
top: 10px;
right: 10px;
/* Ahora se posiciona respecto a .card */
}
❌ Error 2: Fixed sin compensar espacio
/* Problemático */
.header {
position: fixed;
top: 0;
height: 60px;
/* El contenido queda tapado por debajo */
}
/* Solución */
.header {
position: fixed;
top: 0;
height: 60px;
}
body {
padding-top: 60px; /* Compensa la altura del header */
}
❌ Error 3: Z-index en elementos static
/* No funciona */
.element {
/* position: static por defecto */
z-index: 999; /* ¡No hace nada! */
}
/* Funciona */
.element {
position: relative; /* O absolute, fixed, sticky */
z-index: 999;
}
Resumen rápido
| Position | Flujo | Referencia | Uso típico |
|---|---|---|---|
static | ✅ Normal | - | Comportamiento por defecto |
relative | ✅ Reserva espacio | Su posición original | Ajustes pequeños, contenedor para absolute |
absolute | ❌ Sale del flujo | Padre posicionado | Tooltips, overlays, elementos flotantes |
fixed | ❌ Sale del flujo | Viewport | Headers fijos, botones flotantes |
sticky | ✅ Híbrido | Contenedor padre | Menús que se fijan al scrollear |
Recuerda:
static= comportamiento normalrelative= pequeños ajustes + contenedor para absoluteabsolute= elementos flotantes respecto a su contenedorfixed= siempre visible respecto al viewportsticky= se fija al hacer scroll
¡Ahora ya puedes crear layouts más complejos y interfaces más dinámicas con total control sobre la posición de tus elementos!