Barra de navegación elegante y moderna con un tema oscuro, esquinas redondeadas y un indicador deslizante animado con CSS.
En este tutorial, construiremos una barra de navegación con un diseño oscuro y un indicador deslizante como fondo que resalta el elemento activo. Utilizaremos HTML, CSS y JavaScript para lograr una transición fluida y una interfaz atractiva.
Vamos a dividir la implementación en tres partes: estructura HTML, estilos CSS y funcionalidad con JavaScript.
El punto de partida es un elemento <nav>
que contiene una lista de enlaces y un <div>
que representará el indicador deslizante.
<nav> <div class="indicator" style="left: 0px; width: 85px;"></div> <ul> <li class="active"> <a href="#">Inicio</a> </li> <li> <a href="#">Productos</a> </li> <li> <a href="#">Sobre</a> </li> <li> <a href="#">Contactar</a> </li> </ul></nav>
El diseño se basa en un fondo oscuro con texto claro, esquinas redondeadas y una transición suave para el indicador.
body { background-color: #ffffff; margin: 0; min-height: 100vh; display: flex; justify-content: center; align-items: center;}
nav { position: relative; background-color: #2d2d2d; border: 1px solid #404040; border-radius: 12px; box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);}
ul { display: flex; list-style: none; padding: 0; margin: 0;}
li { position: relative;}
a { display: block; padding: 12px 24px; color: #e0e0e0; text-decoration: none; font-family: "Arial", "Helvetica", sans-serif; position: relative; transition: color 0.2s ease;}
a:hover { color: #ffffff;}
.indicator { position: absolute; top: 0; left: 0; height: 100%; background-color: #404040; border-radius: 8px; transition: left 0.3s ease, width 0.3s ease; z-index: 0;}
li.active a { color: #ffffff; position: relative; z-index: 1;}
La clave está en poner el .indicador
en posición absolute
, y añadir una transición left 0.3s ease, width 0.3s ease
.
Ahora agregamos la lógica para actualizar la posición y ancho del indicador al hacer clic en un elemento del menú.
const navItems = document.querySelectorAll("nav ul li a");const indicator = document.querySelector(".indicator");
function updateIndicator(element) { const li = element.parentElement; indicator.style.left = `${li.offsetLeft}px`; indicator.style.width = `${li.offsetWidth}px`;}
const initialActive = navItems[0];initialActive.parentElement.classList.add("active");updateIndicator(initialActive);
navItems.forEach((item) => { item.addEventListener("click", (e) => { e.preventDefault(); document .querySelector("nav ul li.active") ?.classList.remove("active"); item.parentElement.classList.add("active"); updateIndicator(item); });});
Veamos el ejemplo en acción:
<html lang="en">
<head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Navigation Bar</title> <style> body { background-color: #ffffff; margin: 0; min-height: 100vh; display: flex; justify-content: center; align-items: center; }
nav { position: relative; background-color: #2d2d2d; border: 1px solid #404040; border-radius: 12px; box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1); }
ul { display: flex; list-style: none; padding: 0; margin: 0; }
li { position: relative; }
a { display: block; padding: 12px 24px; color: #e0e0e0; text-decoration: none; font-family: "Arial", "Helvetica", sans-serif; position: relative; transition: color 0.2s ease; }
a:hover { color: #ffffff; }
.indicator { position: absolute; top: 0; left: 0; height: 100%; background-color: #404040; border-radius: 8px; transition: left 0.3s ease, width 0.3s ease; z-index: 0; }
li.active a { color: #ffffff; position: relative; z-index: 1; } </style></head>
<body> <nav> <div class="indicator" style="left: 0px; width: 85px;"></div> <ul> <li class="active"> <a href="#">Inicio</a> </li> <li> <a href="#">Productos</a> </li> <li> <a href="#">Sobre</a> </li> <li> <a href="#">Contactar</a> </li> </ul> </nav>
<script> const navItems = document.querySelectorAll("nav ul li a"); const indicator = document.querySelector(".indicator");
function updateIndicator(element) { const li = element.parentElement; indicator.style.left = `${li.offsetLeft}px`; indicator.style.width = `${li.offsetWidth}px`; }
// Set initial state const initialActive = navItems[0]; initialActive.parentElement.classList.add("active"); updateIndicator(initialActive);
// Event listeners navItems.forEach((item) => { item.addEventListener("click", (e) => { e.preventDefault(); document .querySelector("nav ul li.active") ?.classList.remove("active"); item.parentElement.classList.add("active"); updateIndicator(item); }); }); </script>
</body>
</html>
Con esta implementación, obtenemos una barra de navegación atractiva y fácil de usar. El indicador deslizante mejora la experiencia visual y aporta dinamismo a la interfaz. Puedes personalizar los colores y efectos para adaptarlos a tu proyecto.