Categoría · Interactivo Nivel de Dificultad · Intermedio Publicado el · 15 de enero de 2024

Banner de Consentimiento de Cookies con Deslizamiento Inferior

Un elegante banner de consentimiento de cookies que se desliza desde abajo con transiciones suaves, divulgación progresiva y efectos de animación elegantes

#cookie-banner #gdpr #privacy #consent #responsive #modern #animated

Diseño Responsivo

Soporte para Modo Oscuro

No

líneas

1124

Compatibilidad del Navegador

No

Vista Previa en Vivo

Interactúa con el componente sin salir de la página.

400px

Banner de Consentimiento de Cookies con Deslizamiento Inferior

Un banner de consentimiento de cookies bellamente diseñado que se desliza desde la parte inferior con transiciones suaves y animaciones elegantes. Presenta divulgación progresiva, configuraciones personalizables y un diseño moderno que mejora la experiencia del usuario mientras garantiza el cumplimiento del RGPD.

Características

  • Animación de Deslizamiento Suave: Elegante transición de deslizamiento inferior con curvas de suavizado
  • Divulgación Progresiva: Secciones expandibles para información detallada de cookies
  • Transiciones Fluidas: Animaciones fluidas para todos los elementos interactivos
  • Tipografía Moderna: Fuentes limpias y legibles con jerarquía adecuada
  • Cumple RGPD: Gestión completa de consentimiento con controles granulares
  • Accesibilidad Primero: Navegación completa por teclado y soporte para lectores de pantalla
  • Diseño Responsivo: Se adapta hermosamente a todos los tamaños y orientaciones de pantalla
  • Estilo Personalizable: Fácil personalización de temas con variables CSS
  • Optimizado para Rendimiento: Implementación ligera y de carga rápida

Vista Previa

<!DOCTYPE html>
<html lang="es">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Banner de Cookies Deslizamiento Inferior</title>
    <style>
        :root {
            --color-primario: #4f46e5;
            --color-primario-hover: #4338ca;
            --color-secundario: #6b7280;
            --color-exito: #059669;
            --color-exito-hover: #047857;
            --color-peligro: #dc2626;
            --color-peligro-hover: #b91c1c;
            --fondo: #ffffff;
            --superficie: #f9fafb;
            --texto-primario: #111827;
            --texto-secundario: #6b7280;
            --texto-silenciado: #9ca3af;
            --color-borde: #e5e7eb;
            --sombra-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05);
            --sombra-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06);
            --sombra-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
            --radio-borde: 8px;
            --radio-borde-lg: 12px;
            --transicion: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
            --transicion-rapida: all 0.15s cubic-bezier(0.4, 0, 0.2, 1);
            --distancia-deslizamiento: 100%;
        }

        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }

        body {
            font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            min-height: 100vh;
            color: var(--texto-primario);
            line-height: 1.6;
            padding: 2rem;
            overflow-x: hidden;
        }

        .contenedor-demo {
            max-width: 1200px;
            margin: 0 auto;
            text-align: center;
            color: white;
        }

        .contenedor-demo h1 {
            font-size: 3rem;
            font-weight: 800;
            margin-bottom: 1rem;
            background: linear-gradient(135deg, #ffffff 0%, #f0f0f0 100%);
            -webkit-background-clip: text;
            -webkit-text-fill-color: transparent;
            background-clip: text;
        }

        .contenedor-demo p {
            font-size: 1.2rem;
            opacity: 0.9;
            margin-bottom: 2rem;
        }

        .btn-demo {
            padding: 1rem 2rem;
            border: none;
            border-radius: var(--radio-borde);
            background: rgba(255, 255, 255, 0.2);
            backdrop-filter: blur(10px);
            color: white;
            font-family: inherit;
            font-size: 1.1rem;
            font-weight: 600;
            cursor: pointer;
            transition: var(--transicion);
            border: 1px solid rgba(255, 255, 255, 0.3);
        }

        .btn-demo:hover {
            background: rgba(255, 255, 255, 0.3);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        /* Banner de Cookies Deslizamiento Inferior */
        .banner-cookies-deslizamiento-inferior {
            position: fixed;
            bottom: 0;
            left: 0;
            right: 0;
            background: var(--fondo);
            border-top: 1px solid var(--color-borde);
            box-shadow: 0 -4px 6px -1px rgba(0, 0, 0, 0.1), 0 -2px 4px -1px rgba(0, 0, 0, 0.06);
            transform: translateY(var(--distancia-deslizamiento));
            transition: transform 0.4s cubic-bezier(0.4, 0, 0.2, 1);
            z-index: 10000;
            backdrop-filter: blur(20px);
        }

        .banner-cookies-deslizamiento-inferior.mostrar {
            transform: translateY(0);
        }

        .contenido-banner {
            max-width: 1200px;
            margin: 0 auto;
            padding: 1.5rem;
        }

        .encabezado-banner {
            display: flex;
            align-items: flex-start;
            gap: 1rem;
            margin-bottom: 1rem;
        }

        .icono-banner {
            width: 48px;
            height: 48px;
            background: linear-gradient(135deg, var(--color-primario) 0%, var(--color-primario-hover) 100%);
            border-radius: 50%;
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 1.5rem;
            color: white;
            flex-shrink: 0;
            animation: pulso 2s infinite;
        }

        @keyframes pulso {
            0%, 100% {
                transform: scale(1);
                box-shadow: 0 0 0 0 rgba(79, 70, 229, 0.4);
            }
            50% {
                transform: scale(1.05);
                box-shadow: 0 0 0 10px rgba(79, 70, 229, 0);
            }
        }

        .texto-banner {
            flex: 1;
        }

        .titulo-banner {
            font-size: 1.25rem;
            font-weight: 700;
            color: var(--texto-primario);
            margin-bottom: 0.5rem;
        }

        .descripcion-banner {
            color: var(--texto-secundario);
            font-size: 0.95rem;
            line-height: 1.6;
        }

        .enlace-cookies {
            color: var(--color-primario);
            text-decoration: none;
            font-weight: 600;
            transition: var(--transicion-rapida);
            position: relative;
        }

        .enlace-cookies::after {
            content: '';
            position: absolute;
            bottom: -2px;
            left: 0;
            width: 0;
            height: 2px;
            background: var(--color-primario);
            transition: width 0.3s ease;
        }

        .enlace-cookies:hover {
            color: var(--color-primario-hover);
        }

        .enlace-cookies:hover::after {
            width: 100%;
        }

        .acciones-banner {
            display: flex;
            gap: 0.75rem;
            align-items: center;
            flex-wrap: wrap;
            margin-top: 1rem;
        }

        /* Botones de Deslizamiento */
        .btn-deslizamiento {
            padding: 0.75rem 1.5rem;
            border: none;
            border-radius: var(--radio-borde);
            font-family: inherit;
            font-size: 0.9rem;
            font-weight: 600;
            cursor: pointer;
            transition: var(--transicion);
            position: relative;
            overflow: hidden;
            text-transform: uppercase;
            letter-spacing: 0.5px;
            min-width: 120px;
        }

        .btn-deslizamiento::before {
            content: '';
            position: absolute;
            top: 0;
            left: -100%;
            width: 100%;
            height: 100%;
            background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.2), transparent);
            transition: left 0.5s ease;
        }

        .btn-deslizamiento:hover::before {
            left: 100%;
        }

        .btn-aceptar {
            background: var(--color-exito);
            color: white;
            box-shadow: var(--sombra-md);
        }

        .btn-aceptar:hover {
            background: var(--color-exito-hover);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        .btn-rechazar {
            background: var(--color-peligro);
            color: white;
            box-shadow: var(--sombra-md);
        }

        .btn-rechazar:hover {
            background: var(--color-peligro-hover);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        .btn-personalizar {
            background: var(--superficie);
            color: var(--texto-primario);
            border: 1px solid var(--color-borde);
            box-shadow: var(--sombra-sm);
        }

        .btn-personalizar:hover {
            background: var(--color-borde);
            transform: translateY(-2px);
            box-shadow: var(--sombra-md);
        }

        .btn-expandir {
            background: transparent;
            color: var(--color-primario);
            border: 1px solid var(--color-primario);
            padding: 0.5rem 1rem;
            font-size: 0.8rem;
        }

        .btn-expandir:hover {
            background: var(--color-primario);
            color: white;
        }

        /* Detalles Expandibles */
        .detalles-expandibles {
            max-height: 0;
            overflow: hidden;
            transition: max-height 0.4s cubic-bezier(0.4, 0, 0.2, 1), padding 0.4s ease;
            background: var(--superficie);
            border-radius: var(--radio-borde);
            margin-top: 1rem;
        }

        .detalles-expandibles.expandido {
            max-height: 400px;
            padding: 1.5rem;
            border: 1px solid var(--color-borde);
        }

        .cuadricula-detalles {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
            gap: 1.5rem;
        }

        .categoria-cookies {
            background: var(--fondo);
            padding: 1rem;
            border-radius: var(--radio-borde);
            border: 1px solid var(--color-borde);
            transition: var(--transicion-rapida);
        }

        .categoria-cookies:hover {
            box-shadow: var(--sombra-md);
            transform: translateY(-1px);
        }

        .encabezado-categoria {
            display: flex;
            justify-content: space-between;
            align-items: center;
            margin-bottom: 0.75rem;
        }

        .titulo-categoria {
            font-weight: 700;
            font-size: 1rem;
            color: var(--texto-primario);
        }

        .descripcion-categoria {
            font-size: 0.85rem;
            color: var(--texto-secundario);
            line-height: 1.5;
        }

        /* Interruptor de Deslizamiento */
        .interruptor-deslizamiento {
            position: relative;
            width: 48px;
            height: 24px;
            background: var(--color-borde);
            border-radius: 12px;
            cursor: pointer;
            transition: var(--transicion);
        }

        .interruptor-deslizamiento.activo {
            background: var(--color-exito);
        }

        .interruptor-deslizamiento::before {
            content: '';
            position: absolute;
            top: 2px;
            left: 2px;
            width: 20px;
            height: 20px;
            background: white;
            border-radius: 50%;
            transition: var(--transicion);
            box-shadow: var(--sombra-sm);
        }

        .interruptor-deslizamiento.activo::before {
            transform: translateX(24px);
        }

        .interruptor-deslizamiento:hover {
            transform: scale(1.05);
        }

        /* Indicador de Progreso */
        .indicador-progreso {
            position: absolute;
            bottom: 0;
            left: 0;
            height: 3px;
            background: var(--color-primario);
            width: 0;
            transition: width 0.3s ease;
        }

        .contenido-banner:hover .indicador-progreso {
            width: 100%;
        }

        /* Animación de Carga */
        .puntos-carga {
            display: inline-flex;
            gap: 4px;
        }

        .puntos-carga span {
            width: 6px;
            height: 6px;
            background: currentColor;
            border-radius: 50%;
            animation: carga 1.4s infinite ease-in-out;
        }

        .puntos-carga span:nth-child(1) { animation-delay: -0.32s; }
        .puntos-carga span:nth-child(2) { animation-delay: -0.16s; }

        @keyframes carga {
            0%, 80%, 100% {
                transform: scale(0.8);
                opacity: 0.5;
            }
            40% {
                transform: scale(1);
                opacity: 1;
            }
        }

        /* Animación de Éxito */
        .marca-exito {
            width: 20px;
            height: 20px;
            border-radius: 50%;
            display: inline-block;
            stroke-width: 2;
            stroke: currentColor;
            stroke-miterlimit: 10;
            box-shadow: inset 0px 0px 0px currentColor;
            animation: llenar 0.4s ease-in-out 0.4s forwards, escalar 0.3s ease-in-out 0.9s both;
        }

        .circulo-marca-exito {
            stroke-dasharray: 166;
            stroke-dashoffset: 166;
            stroke-width: 2;
            stroke-miterlimit: 10;
            stroke: currentColor;
            fill: none;
            animation: trazo 0.6s cubic-bezier(0.65, 0, 0.45, 1) forwards;
        }

        .check-marca-exito {
            transform-origin: 50% 50%;
            stroke-dasharray: 48;
            stroke-dashoffset: 48;
            animation: trazo 0.3s cubic-bezier(0.65, 0, 0.45, 1) 0.8s forwards;
        }

        @keyframes trazo {
            100% {
                stroke-dashoffset: 0;
            }
        }

        @keyframes escalar {
            0%, 100% {
                transform: none;
            }
            50% {
                transform: scale3d(1.1, 1.1, 1);
            }
        }

        @keyframes llenar {
            100% {
                box-shadow: inset 0px 0px 0px 30px currentColor;
            }
        }

        /* Diseño Responsivo */
        @media (max-width: 768px) {
            .encabezado-banner {
                flex-direction: column;
                text-align: center;
            }

            .acciones-banner {
                justify-content: center;
                flex-direction: column;
            }

            .btn-deslizamiento {
                width: 100%;
                min-width: auto;
            }

            .cuadricula-detalles {
                grid-template-columns: 1fr;
            }

            .contenido-banner {
                padding: 1rem;
            }
        }

        @media (max-width: 480px) {
            body {
                padding: 1rem;
            }

            .contenedor-demo h1 {
                font-size: 2rem;
            }

            .contenido-banner {
                padding: 0.75rem;
            }

            .titulo-banner {
                font-size: 1.1rem;
            }

            .descripcion-banner {
                font-size: 0.9rem;
            }
        }

        /* Variantes de Animación de Deslizamiento */
        .deslizar-izquierda {
            transform: translateX(-100%);
        }

        .deslizar-derecha {
            transform: translateX(100%);
        }

        .deslizar-desvanecer {
            transform: translateY(100%) scale(0.9);
            opacity: 0;
        }

        .deslizar-desvanecer.mostrar {
            transform: translateY(0) scale(1);
            opacity: 1;
        }

        /* Efecto de Rebote */
        .rebote-entrada {
            animation: reboteEntrada 0.6s cubic-bezier(0.68, -0.55, 0.265, 1.55);
        }

        @keyframes reboteEntrada {
            0% {
                transform: translateY(100%) scale(0.3);
                opacity: 0;
            }
            50% {
                transform: translateY(-10%) scale(1.05);
            }
            70% {
                transform: translateY(5%) scale(0.98);
            }
            100% {
                transform: translateY(0) scale(1);
                opacity: 1;
            }
        }
    </style>
</head>
<body>
    <div class="contenedor-demo">
        <h1>Diseño de Deslizamiento Suave</h1>
        <p>Experimenta la elegancia de las transiciones de deslizamiento suave con divulgación progresiva e interacciones modernas</p>
        <button class="btn-demo" onclick="mostrarBannerCookies()">Mostrar Banner de Cookies</button>
    </div>

    <!-- Banner de Cookies Deslizamiento Inferior -->
    <div id="bannerCookiesDeslizamientoInferior" class="banner-cookies-deslizamiento-inferior">
        <div class="indicador-progreso"></div>
        <div class="contenido-banner">
            <div class="encabezado-banner">
                <div class="icono-banner">🍪</div>
                <div class="texto-banner">
                    <div class="titulo-banner">Preferencias de Cookies</div>
                    <div class="descripcion-banner">
                        Utilizamos cookies para mejorar tu experiencia de navegación y proporcionar contenido personalizado. 
                        <a href="#" class="enlace-cookies">Política de Privacidad</a> | 
                        <a href="#" class="enlace-cookies">Política de Cookies</a>
                    </div>
                </div>
            </div>
            <div class="acciones-banner">
                <button class="btn-deslizamiento btn-aceptar" onclick="aceptarCookies()">Aceptar Todo</button>
                <button class="btn-deslizamiento btn-rechazar" onclick="rechazarCookies()">Rechazar</button>
                <button class="btn-deslizamiento btn-personalizar" onclick="abrirPersonalizacion()">Personalizar</button>
                <button class="btn-deslizamiento btn-expandir" onclick="alternarDetalles()">Saber Más</button>
            </div>
            
            <!-- Detalles Expandibles -->
            <div id="detallesExpandibles" class="detalles-expandibles">
                <div class="cuadricula-detalles">
                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies Esenciales</span>
                            <div class="interruptor-deslizamiento activo" data-categoria="esenciales"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies son necesarias para que el sitio web funcione y no se pueden desactivar. Generalmente solo se establecen en respuesta a acciones realizadas por ti.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies de Análisis</span>
                            <div class="interruptor-deslizamiento" data-categoria="analiticas"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies nos ayudan a entender cómo los visitantes interactúan con nuestro sitio web recopilando y reportando información de forma anónima.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies de Marketing</span>
                            <div class="interruptor-deslizamiento" data-categoria="marketing"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies se utilizan para entregar anuncios más relevantes para ti y tus intereses basados en tu comportamiento de navegación.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies Funcionales</span>
                            <div class="interruptor-deslizamiento" data-categoria="funcionales"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies habilitan funcionalidad mejorada y personalización, como recordar tus preferencias y configuraciones.
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <script>
        class BannerCookiesDeslizamientoInferior {
            constructor(opciones = {}) {
                this.opciones = {
                    mostrarAuto: true,
                    retrasoMostrar: 1500,
                    claveAlmacenamiento: 'consentimiento_cookies_deslizamiento_inferior',
                    diasExpiracion: 365,
                    habilitarAnimaciones: true,
                    direccionDeslizamiento: 'inferior',
                    tipoAnimacion: 'deslizar', // 'deslizar', 'desvanecer', 'rebote'
                    divulgacionProgresiva: true,
                    alAceptar: null,
                    alRechazar: null,
                    alPersonalizar: null,
                    ...opciones
                };

                this.banner = document.getElementById('bannerCookiesDeslizamientoInferior');
                this.detallesExpandibles = document.getElementById('detallesExpandibles');
                this.consentimiento = this.obtenerConsentimientoAlmacenado();
                this.esVisible = false;
                this.estaExpandido = false;

                this.inicializar();
            }

            inicializar() {
                if (this.opciones.mostrarAuto && !this.consentimiento) {
                    setTimeout(() => this.mostrar(), this.opciones.retrasoMostrar);
                }

                this.configurarEventListeners();
                this.cargarConfiguracion();
                this.configurarTipoAnimacion();
            }

            configurarEventListeners() {
                // Interruptores de alternancia
                document.querySelectorAll('.interruptor-deslizamiento').forEach(interruptor => {
                    interruptor.addEventListener('click', () => {
                        if (interruptor.dataset.categoria !== 'esenciales') {
                            interruptor.classList.toggle('activo');
                            this.animarInterruptor(interruptor);
                        }
                    });
                });

                // Navegación por teclado
                document.addEventListener('keydown', (e) => {
                    if (e.key === 'Escape' && this.estaExpandido) {
                        this.alternarDetalles();
                    }
                });

                // Efectos hover de botones
                document.querySelectorAll('.btn-deslizamiento').forEach(btn => {
                    btn.addEventListener('mouseenter', () => {
                        this.crearOnda(btn);
                    });
                });

                // Indicador de progreso al hacer hover
                this.banner.addEventListener('mouseenter', () => {
                    if (this.esVisible) {
                        this.mejorarIndicadorProgreso();
                    }
                });

                this.banner.addEventListener('mouseleave', () => {
                    if (this.esVisible) {
                        this.resetearIndicadorProgreso();
                    }
                });
            }

            configurarTipoAnimacion() {
                const clasesAnimacion = {
                    deslizar: '',
                    desvanecer: 'deslizar-desvanecer',
                    rebote: 'rebote-entrada'
                };

                const claseAnimacion = clasesAnimacion[this.opciones.tipoAnimacion];
                if (claseAnimacion) {
                    this.banner.classList.add(claseAnimacion);
                }
            }

            animarInterruptor(interruptor) {
                if (!this.opciones.habilitarAnimaciones) return;

                interruptor.style.transform = 'scale(0.9)';
                setTimeout(() => {
                    interruptor.style.transform = 'scale(1)';
                }, 150);

                // Agregar efecto de pulso
                interruptor.style.boxShadow = '0 0 0 8px rgba(5, 150, 105, 0.2)';
                setTimeout(() => {
                    interruptor.style.boxShadow = '';
                }, 300);
            }

            crearOnda(boton) {
                if (!this.opciones.habilitarAnimaciones) return;

                const onda = document.createElement('span');
                const rect = boton.getBoundingClientRect();
                const tamaño = Math.max(rect.width, rect.height);
                
                onda.style.width = onda.style.height = tamaño + 'px';
                onda.style.left = '50%';
                onda.style.top = '50%';
                onda.style.transform = 'translate(-50%, -50%) scale(0)';
                onda.style.position = 'absolute';
                onda.style.borderRadius = '50%';
                onda.style.background = 'rgba(255, 255, 255, 0.3)';
                onda.style.pointerEvents = 'none';
                onda.style.animation = 'onda 0.6s ease-out';
                
                boton.style.position = 'relative';
                boton.style.overflow = 'hidden';
                boton.appendChild(onda);
                
                setTimeout(() => {
                    onda.remove();
                }, 600);
            }

            mejorarIndicadorProgreso() {
                if (!this.opciones.habilitarAnimaciones) return;
                
                const indicador = this.banner.querySelector('.indicador-progreso');
                if (indicador) {
                    indicador.style.background = 'linear-gradient(90deg, var(--color-primario), var(--color-exito))';
                    indicador.style.height = '4px';
                }
            }

            resetearIndicadorProgreso() {
                if (!this.opciones.habilitarAnimaciones) return;
                
                const indicador = this.banner.querySelector('.indicador-progreso');
                if (indicador) {
                    indicador.style.background = 'var(--color-primario)';
                    indicador.style.height = '3px';
                }
            }

            mostrar() {
                this.banner.classList.add('mostrar');
                this.esVisible = true;
                
                if (this.opciones.habilitarAnimaciones) {
                    this.animarEntrada();
                }
            }

            ocultar() {
                this.banner.classList.remove('mostrar');
                this.esVisible = false;
                this.estaExpandido = false;
                this.detallesExpandibles.classList.remove('expandido');
            }

            animarEntrada() {
                const elementos = [
                    this.banner.querySelector('.icono-banner'),
                    this.banner.querySelector('.titulo-banner'),
                    this.banner.querySelector('.descripcion-banner'),
                    this.banner.querySelector('.acciones-banner')
                ];

                elementos.forEach((el, index) => {
                    if (el) {
                        el.style.opacity = '0';
                        el.style.transform = 'translateY(20px)';
                        
                        setTimeout(() => {
                            el.style.transition = 'all 0.6s cubic-bezier(0.4, 0, 0.2, 1)';
                            el.style.opacity = '1';
                            el.style.transform = 'translateY(0)';
                        }, index * 100);
                    }
                });
            }

            alternarDetalles() {
                this.estaExpandido = !this.estaExpandido;
                
                if (this.estaExpandido) {
                    this.detallesExpandibles.classList.add('expandido');
                    if (this.opciones.habilitarAnimaciones) {
                        this.animarExpansionDetalles();
                    }
                } else {
                    this.detallesExpandibles.classList.remove('expandido');
                }

                // Actualizar texto del botón
                const btnExpandir = this.banner.querySelector('.btn-expandir');
                if (btnExpandir) {
                    btnExpandir.textContent = this.estaExpandido ? 'Mostrar Menos' : 'Saber Más';
                }
            }

            animarExpansionDetalles() {
                const categorias = this.detallesExpandibles.querySelectorAll('.categoria-cookies');
                categorias.forEach((categoria, index) => {
                    categoria.style.opacity = '0';
                    categoria.style.transform = 'translateY(20px)';
                    
                    setTimeout(() => {
                        categoria.style.transition = 'all 0.4s cubic-bezier(0.4, 0, 0.2, 1)';
                        categoria.style.opacity = '1';
                        categoria.style.transform = 'translateY(0)';
                    }, index * 100);
                });
            }

            aceptar() {
                const consentimiento = {
                    esenciales: true,
                    analiticas: true,
                    marketing: true,
                    funcionales: true,
                    marcaTiempo: Date.now()
                };

                this.guardarConsentimiento(consentimiento);
                this.mostrarAnimacionExito();
                
                setTimeout(() => {
                    this.ocultar();
                }, 1500);

                if (this.opciones.alAceptar) {
                    this.opciones.alAceptar(consentimiento);
                }
            }

            rechazar() {
                const consentimiento = {
                    esenciales: true,
                    analiticas: false,
                    marketing: false,
                    funcionales: false,
                    marcaTiempo: Date.now()
                };

                this.guardarConsentimiento(consentimiento);
                this.ocultar();

                if (this.opciones.alRechazar) {
                    this.opciones.alRechazar(consentimiento);
                }
            }

            mostrarAnimacionExito() {
                if (!this.opciones.habilitarAnimaciones) return;

                const btnAceptar = this.banner.querySelector('.btn-aceptar');
                if (btnAceptar) {
                    btnAceptar.innerHTML = `
                        <svg class="marca-exito" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 52 52">
                            <circle class="circulo-marca-exito" cx="26" cy="26" r="25" fill="none"/>
                            <path class="check-marca-exito" fill="none" d="m14.1 27.2l7.1 7.2 16.7-16.8"/>
                        </svg>
                        Aceptado
                    `;
                    btnAceptar.style.background = 'var(--color-exito)';
                }
            }

            personalizar() {
                this.alternarDetalles();
                
                if (this.opciones.alPersonalizar) {
                    this.opciones.alPersonalizar();
                }
            }

            guardarPersonalizacion() {
                const interruptores = document.querySelectorAll('.interruptor-deslizamiento');
                const consentimiento = { marcaTiempo: Date.now() };

                interruptores.forEach(interruptor => {
                    const categoria = interruptor.dataset.categoria;
                    consentimiento[categoria] = interruptor.classList.contains('activo');
                });

                this.guardarConsentimiento(consentimiento);
                this.ocultar();

                if (this.opciones.alPersonalizar) {
                    this.opciones.alPersonalizar(consentimiento);
                }
            }

            cargarConfiguracion() {
                if (this.consentimiento) {
                    document.querySelectorAll('.interruptor-deslizamiento').forEach(interruptor => {
                        const categoria = interruptor.dataset.categoria;
                        if (this.consentimiento[categoria]) {
                            interruptor.classList.add('activo');
                        } else {
                            interruptor.classList.remove('activo');
                        }
                    });
                }
            }

            guardarConsentimiento(consentimiento) {
                const fechaExpiracion = new Date();
                fechaExpiracion.setDate(fechaExpiracion.getDate() + this.opciones.diasExpiracion);
                
                const datosConsentimiento = {
                    ...consentimiento,
                    expiracion: fechaExpiracion.getTime()
                };

                localStorage.setItem(this.opciones.claveAlmacenamiento, JSON.stringify(datosConsentimiento));
                this.consentimiento = consentimiento;
            }

            obtenerConsentimientoAlmacenado() {
                try {
                    const almacenado = localStorage.getItem(this.opciones.claveAlmacenamiento);
                    if (almacenado) {
                        const datos = JSON.parse(almacenado);
                        if (datos.expiracion && Date.now() < datos.expiracion) {
                            return datos;
                        } else {
                            localStorage.removeItem(this.opciones.claveAlmacenamiento);
                        }
                    }
                } catch (e) {
                    console.error('Error al leer el consentimiento de cookies:', e);
                }
                return null;
            }

            resetear() {
                localStorage.removeItem(this.opciones.claveAlmacenamiento);
                this.consentimiento = null;
                this.mostrar();
            }

            obtenerConsentimiento() {
                return this.consentimiento;
            }

            establecerDireccionDeslizamiento(direccion) {
                this.opciones.direccionDeslizamiento = direccion;
                this.configurarDireccionDeslizamiento();
            }

            configurarDireccionDeslizamiento() {
                const direcciones = {
                    inferior: 'translateY(100%)',
                    superior: 'translateY(-100%)',
                    izquierda: 'translateX(-100%)',
                    derecha: 'translateX(100%)'
                };

                const transformacion = direcciones[this.opciones.direccionDeslizamiento] || direcciones.inferior;
                document.documentElement.style.setProperty('--distancia-deslizamiento', transformacion);
            }

            establecerTipoAnimacion(tipo) {
                this.opciones.tipoAnimacion = tipo;
                this.configurarTipoAnimacion();
            }

            habilitarAnimaciones(habilitado) {
                this.opciones.habilitarAnimaciones = habilitado;
            }

            actualizarTema(tema) {
                const temas = {
                    claro: {
                        '--fondo': '#ffffff',
                        '--superficie': '#f9fafb',
                        '--texto-primario': '#111827',
                        '--texto-secundario': '#6b7280'
                    },
                    oscuro: {
                        '--fondo': '#1f2937',
                        '--superficie': '#374151',
                        '--texto-primario': '#f9fafb',
                        '--texto-secundario': '#d1d5db'
                    }
                };

                if (temas[tema]) {
                    Object.entries(temas[tema]).forEach(([propiedad, valor]) => {
                        document.documentElement.style.setProperty(propiedad, valor);
                    });
                }
            }
        }

        // Agregar animación de onda CSS
        const estilo = document.createElement('style');
        estilo.textContent = `
            @keyframes onda {
                to {
                    transform: translate(-50%, -50%) scale(2);
                    opacity: 0;
                }
            }
        `;
        document.head.appendChild(estilo);

        // Inicializar el banner
        const bannerCookies = new BannerCookiesDeslizamientoInferior({
            direccionDeslizamiento: 'inferior',
            tipoAnimacion: 'deslizar',
            habilitarAnimaciones: true,
            divulgacionProgresiva: true,
            alAceptar: (consentimiento) => {
                console.log('Cookies aceptadas:', consentimiento);
                // Inicializar scripts de análisis, marketing, etc.
            },
            alRechazar: (consentimiento) => {
                console.log('Cookies rechazadas:', consentimiento);
                // Cargar solo scripts esenciales
            },
            alPersonalizar: (consentimiento) => {
                console.log('Configuración personalizada guardada:', consentimiento);
                // Cargar scripts basados en las preferencias del usuario
            }
        });

        // Funciones globales para la demo
        function mostrarBannerCookies() {
            bannerCookies.resetear();
        }

        function aceptarCookies() {
            bannerCookies.aceptar();
        }

        function rechazarCookies() {
            bannerCookies.rechazar();
        }

        function abrirPersonalizacion() {
            bannerCookies.personalizar();
        }

        function alternarDetalles() {
            bannerCookies.alternarDetalles();
        }
    </script>
</body>
</html>

Uso

Implementación Básica

// Inicializar con configuración predeterminada
const bannerCookies = new BannerCookiesDeslizamientoInferior();

// Inicializar con opciones personalizadas
const bannerCookies = new BannerCookiesDeslizamientoInferior({
    mostrarAuto: true,
    retrasoMostrar: 2000,
    claveAlmacenamiento: 'mi_consentimiento_cookies',
    diasExpiracion: 180,
    habilitarAnimaciones: true,
    direccionDeslizamiento: 'inferior',
    tipoAnimacion: 'deslizar',
    divulgacionProgresiva: true,
    alAceptar: (consentimiento) => {
        console.log('Usuario aceptó cookies:', consentimiento);
        // Cargar scripts de análisis
        if (consentimiento.analiticas) {
            cargarGoogleAnalytics();
        }
        // Cargar scripts de marketing
        if (consentimiento.marketing) {
            cargarPixelsMarketing();
        }
    },
    alRechazar: (consentimiento) => {
        console.log('Usuario rechazó cookies:', consentimiento);
        // Cargar solo funcionalidad esencial
    },
    alPersonalizar: (consentimiento) => {
        console.log('Usuario guardó configuración personalizada:', consentimiento);
        // Cargar scripts basados en preferencias específicas
    }
});

Configuración Avanzada

// Estilo personalizado y comportamiento
const bannerAvanzado = new BannerCookiesDeslizamientoInferior({
    mostrarAuto: false, // Control manual
    retrasoMostrar: 0,
    claveAlmacenamiento: 'consentimiento_avanzado',
    diasExpiracion: 90,
    habilitarAnimaciones: true,
    direccionDeslizamiento: 'inferior',
    tipoAnimacion: 'rebote',
    divulgacionProgresiva: true,
    
    // Callbacks personalizados
    alAceptar: (consentimiento) => {
        // Configuración avanzada de análisis
        inicializarSeguimientoAvanzado(consentimiento);
    },
    
    alRechazar: (consentimiento) => {
        // Configuración mínima de seguimiento
        inicializarSoloEsencial();
    },
    
    alPersonalizar: (consentimiento) => {
        // Carga granular de scripts
        cargarScriptsBasadosEnConsentimiento(consentimiento);
    }
});

// Control de dirección
function cambiarDireccionDeslizamiento(direccion) {
    bannerAvanzado.establecerDireccionDeslizamiento(direccion);
}

// Control de animación
function cambiarTipoAnimacion(tipo) {
    bannerAvanzado.establecerTipoAnimacion(tipo);
}

// Alternar animaciones
function alternarAnimaciones(habilitado) {
    bannerAvanzado.habilitarAnimaciones(habilitado);
}

// Cambio de tema
function cambiarTema(tema) {
    bannerAvanzado.actualizarTema(tema);
}

// Control manual
function mostrarBannerConsentimiento() {
    bannerAvanzado.mostrar();
}

// Verificar estado actual de consentimiento
function verificarEstadoConsentimiento() {
    const consentimiento = bannerAvanzado.obtenerConsentimiento();
    if (consentimiento) {
        console.log('Consentimiento actual:', consentimiento);
    } else {
        console.log('Aún no se ha dado consentimiento');
    }
}

Métodos de la API

Métodos Principales

  • mostrar() - Mostrar el banner de cookies
  • ocultar() - Ocultar el banner de cookies
  • aceptar() - Aceptar todas las cookies y ocultar banner
  • rechazar() - Rechazar cookies opcionales y ocultar banner
  • resetear() - Limpiar consentimiento almacenado y mostrar banner nuevamente

Gestión de Configuración

  • alternarDetalles() - Alternar sección de detalles expandibles
  • personalizar() - Abrir interfaz de personalización
  • guardarPersonalizacion() - Guardar configuración actual
  • cargarConfiguracion() - Cargar y aplicar configuración almacenada

Gestión de Datos

  • obtenerConsentimiento() - Obtener objeto de consentimiento actual
  • guardarConsentimiento(consentimiento) - Guardar consentimiento en almacenamiento
  • obtenerConsentimientoAlmacenado() - Recuperar consentimiento del almacenamiento

Personalización

  • establecerDireccionDeslizamiento(direccion) - Cambiar dirección de deslizamiento (‘inferior’, ‘superior’, ‘izquierda’, ‘derecha’)
  • establecerTipoAnimacion(tipo) - Cambiar tipo de animación (‘deslizar’, ‘desvanecer’, ‘rebote’)
  • habilitarAnimaciones(habilitado) - Habilitar/deshabilitar animaciones
  • actualizarTema(tema) - Cambiar entre temas claro/oscuro
  • crearOnda(boton) - Crear efectos de onda en botones

Opciones de Personalización

Personalización Visual

  • Esquemas de Color: Modificar propiedades CSS personalizadas para diferentes temas de color
  • Velocidad de Animación: Ajustar duraciones de transición y tiempos de animación
  • Efectos de Deslizamiento: Personalizar direcciones de deslizamiento y tipos de animación
  • Tipografía: Cambiar familias, tamaños y pesos de fuente

Configuración Funcional

  • Visualización Automática: Controlar aparición automática del banner
  • Duración de Almacenamiento: Establecer período de expiración del consentimiento de cookies
  • Configuración de Retraso: Configurar timing de mostrar/ocultar
  • Funciones de Callback: Manejadores personalizados para acciones del usuario

Características de Accesibilidad

  • Navegación por Teclado: Soporte completo de teclado con indicadores de foco
  • Soporte para Lectores de Pantalla: Etiquetas y descripciones ARIA apropiadas
  • Alto Contraste: Visibilidad mejorada para accesibilidad
  • Divulgación Progresiva: Secciones expandibles para información detallada

Compatibilidad de Navegadores

  • Chrome 60+
  • Firefox 55+
  • Safari 12+
  • Edge 79+
  • Navegadores móviles (iOS Safari 12+, Chrome Mobile 60+)

Licencia

Licencia MIT - libre para usar en proyectos personales y comerciales.

HTML

1090

líneas

CSS

1

líneas

JavaScript

33

líneas


                <!DOCTYPE html>
<html lang="es">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Banner de Cookies Deslizamiento Inferior</title>
    <style>
        :root {
            --color-primario: #4f46e5;
            --color-primario-hover: #4338ca;
            --color-secundario: #6b7280;
            --color-exito: #059669;
            --color-exito-hover: #047857;
            --color-peligro: #dc2626;
            --color-peligro-hover: #b91c1c;
            --fondo: #ffffff;
            --superficie: #f9fafb;
            --texto-primario: #111827;
            --texto-secundario: #6b7280;
            --texto-silenciado: #9ca3af;
            --color-borde: #e5e7eb;
            --sombra-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05);
            --sombra-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06);
            --sombra-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
            --radio-borde: 8px;
            --radio-borde-lg: 12px;
            --transicion: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
            --transicion-rapida: all 0.15s cubic-bezier(0.4, 0, 0.2, 1);
            --distancia-deslizamiento: 100%;
        }

        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }

        body {
            font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            min-height: 100vh;
            color: var(--texto-primario);
            line-height: 1.6;
            padding: 2rem;
            overflow-x: hidden;
        }

        .contenedor-demo {
            max-width: 1200px;
            margin: 0 auto;
            text-align: center;
            color: white;
        }

        .contenedor-demo h1 {
            font-size: 3rem;
            font-weight: 800;
            margin-bottom: 1rem;
            background: linear-gradient(135deg, #ffffff 0%, #f0f0f0 100%);
            -webkit-background-clip: text;
            -webkit-text-fill-color: transparent;
            background-clip: text;
        }

        .contenedor-demo p {
            font-size: 1.2rem;
            opacity: 0.9;
            margin-bottom: 2rem;
        }

        .btn-demo {
            padding: 1rem 2rem;
            border: none;
            border-radius: var(--radio-borde);
            background: rgba(255, 255, 255, 0.2);
            backdrop-filter: blur(10px);
            color: white;
            font-family: inherit;
            font-size: 1.1rem;
            font-weight: 600;
            cursor: pointer;
            transition: var(--transicion);
            border: 1px solid rgba(255, 255, 255, 0.3);
        }

        .btn-demo:hover {
            background: rgba(255, 255, 255, 0.3);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        /* Banner de Cookies Deslizamiento Inferior */
        .banner-cookies-deslizamiento-inferior {
            position: fixed;
            bottom: 0;
            left: 0;
            right: 0;
            background: var(--fondo);
            border-top: 1px solid var(--color-borde);
            box-shadow: 0 -4px 6px -1px rgba(0, 0, 0, 0.1), 0 -2px 4px -1px rgba(0, 0, 0, 0.06);
            transform: translateY(var(--distancia-deslizamiento));
            transition: transform 0.4s cubic-bezier(0.4, 0, 0.2, 1);
            z-index: 10000;
            backdrop-filter: blur(20px);
        }

        .banner-cookies-deslizamiento-inferior.mostrar {
            transform: translateY(0);
        }

        .contenido-banner {
            max-width: 1200px;
            margin: 0 auto;
            padding: 1.5rem;
        }

        .encabezado-banner {
            display: flex;
            align-items: flex-start;
            gap: 1rem;
            margin-bottom: 1rem;
        }

        .icono-banner {
            width: 48px;
            height: 48px;
            background: linear-gradient(135deg, var(--color-primario) 0%, var(--color-primario-hover) 100%);
            border-radius: 50%;
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 1.5rem;
            color: white;
            flex-shrink: 0;
            animation: pulso 2s infinite;
        }

        @keyframes pulso {
            0%, 100% {
                transform: scale(1);
                box-shadow: 0 0 0 0 rgba(79, 70, 229, 0.4);
            }
            50% {
                transform: scale(1.05);
                box-shadow: 0 0 0 10px rgba(79, 70, 229, 0);
            }
        }

        .texto-banner {
            flex: 1;
        }

        .titulo-banner {
            font-size: 1.25rem;
            font-weight: 700;
            color: var(--texto-primario);
            margin-bottom: 0.5rem;
        }

        .descripcion-banner {
            color: var(--texto-secundario);
            font-size: 0.95rem;
            line-height: 1.6;
        }

        .enlace-cookies {
            color: var(--color-primario);
            text-decoration: none;
            font-weight: 600;
            transition: var(--transicion-rapida);
            position: relative;
        }

        .enlace-cookies::after {
            content: '';
            position: absolute;
            bottom: -2px;
            left: 0;
            width: 0;
            height: 2px;
            background: var(--color-primario);
            transition: width 0.3s ease;
        }

        .enlace-cookies:hover {
            color: var(--color-primario-hover);
        }

        .enlace-cookies:hover::after {
            width: 100%;
        }

        .acciones-banner {
            display: flex;
            gap: 0.75rem;
            align-items: center;
            flex-wrap: wrap;
            margin-top: 1rem;
        }

        /* Botones de Deslizamiento */
        .btn-deslizamiento {
            padding: 0.75rem 1.5rem;
            border: none;
            border-radius: var(--radio-borde);
            font-family: inherit;
            font-size: 0.9rem;
            font-weight: 600;
            cursor: pointer;
            transition: var(--transicion);
            position: relative;
            overflow: hidden;
            text-transform: uppercase;
            letter-spacing: 0.5px;
            min-width: 120px;
        }

        .btn-deslizamiento::before {
            content: '';
            position: absolute;
            top: 0;
            left: -100%;
            width: 100%;
            height: 100%;
            background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.2), transparent);
            transition: left 0.5s ease;
        }

        .btn-deslizamiento:hover::before {
            left: 100%;
        }

        .btn-aceptar {
            background: var(--color-exito);
            color: white;
            box-shadow: var(--sombra-md);
        }

        .btn-aceptar:hover {
            background: var(--color-exito-hover);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        .btn-rechazar {
            background: var(--color-peligro);
            color: white;
            box-shadow: var(--sombra-md);
        }

        .btn-rechazar:hover {
            background: var(--color-peligro-hover);
            transform: translateY(-2px);
            box-shadow: var(--sombra-lg);
        }

        .btn-personalizar {
            background: var(--superficie);
            color: var(--texto-primario);
            border: 1px solid var(--color-borde);
            box-shadow: var(--sombra-sm);
        }

        .btn-personalizar:hover {
            background: var(--color-borde);
            transform: translateY(-2px);
            box-shadow: var(--sombra-md);
        }

        .btn-expandir {
            background: transparent;
            color: var(--color-primario);
            border: 1px solid var(--color-primario);
            padding: 0.5rem 1rem;
            font-size: 0.8rem;
        }

        .btn-expandir:hover {
            background: var(--color-primario);
            color: white;
        }

        /* Detalles Expandibles */
        .detalles-expandibles {
            max-height: 0;
            overflow: hidden;
            transition: max-height 0.4s cubic-bezier(0.4, 0, 0.2, 1), padding 0.4s ease;
            background: var(--superficie);
            border-radius: var(--radio-borde);
            margin-top: 1rem;
        }

        .detalles-expandibles.expandido {
            max-height: 400px;
            padding: 1.5rem;
            border: 1px solid var(--color-borde);
        }

        .cuadricula-detalles {
            display: grid;
            grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
            gap: 1.5rem;
        }

        .categoria-cookies {
            background: var(--fondo);
            padding: 1rem;
            border-radius: var(--radio-borde);
            border: 1px solid var(--color-borde);
            transition: var(--transicion-rapida);
        }

        .categoria-cookies:hover {
            box-shadow: var(--sombra-md);
            transform: translateY(-1px);
        }

        .encabezado-categoria {
            display: flex;
            justify-content: space-between;
            align-items: center;
            margin-bottom: 0.75rem;
        }

        .titulo-categoria {
            font-weight: 700;
            font-size: 1rem;
            color: var(--texto-primario);
        }

        .descripcion-categoria {
            font-size: 0.85rem;
            color: var(--texto-secundario);
            line-height: 1.5;
        }

        /* Interruptor de Deslizamiento */
        .interruptor-deslizamiento {
            position: relative;
            width: 48px;
            height: 24px;
            background: var(--color-borde);
            border-radius: 12px;
            cursor: pointer;
            transition: var(--transicion);
        }

        .interruptor-deslizamiento.activo {
            background: var(--color-exito);
        }

        .interruptor-deslizamiento::before {
            content: '';
            position: absolute;
            top: 2px;
            left: 2px;
            width: 20px;
            height: 20px;
            background: white;
            border-radius: 50%;
            transition: var(--transicion);
            box-shadow: var(--sombra-sm);
        }

        .interruptor-deslizamiento.activo::before {
            transform: translateX(24px);
        }

        .interruptor-deslizamiento:hover {
            transform: scale(1.05);
        }

        /* Indicador de Progreso */
        .indicador-progreso {
            position: absolute;
            bottom: 0;
            left: 0;
            height: 3px;
            background: var(--color-primario);
            width: 0;
            transition: width 0.3s ease;
        }

        .contenido-banner:hover .indicador-progreso {
            width: 100%;
        }

        /* Animación de Carga */
        .puntos-carga {
            display: inline-flex;
            gap: 4px;
        }

        .puntos-carga span {
            width: 6px;
            height: 6px;
            background: currentColor;
            border-radius: 50%;
            animation: carga 1.4s infinite ease-in-out;
        }

        .puntos-carga span:nth-child(1) { animation-delay: -0.32s; }
        .puntos-carga span:nth-child(2) { animation-delay: -0.16s; }

        @keyframes carga {
            0%, 80%, 100% {
                transform: scale(0.8);
                opacity: 0.5;
            }
            40% {
                transform: scale(1);
                opacity: 1;
            }
        }

        /* Animación de Éxito */
        .marca-exito {
            width: 20px;
            height: 20px;
            border-radius: 50%;
            display: inline-block;
            stroke-width: 2;
            stroke: currentColor;
            stroke-miterlimit: 10;
            box-shadow: inset 0px 0px 0px currentColor;
            animation: llenar 0.4s ease-in-out 0.4s forwards, escalar 0.3s ease-in-out 0.9s both;
        }

        .circulo-marca-exito {
            stroke-dasharray: 166;
            stroke-dashoffset: 166;
            stroke-width: 2;
            stroke-miterlimit: 10;
            stroke: currentColor;
            fill: none;
            animation: trazo 0.6s cubic-bezier(0.65, 0, 0.45, 1) forwards;
        }

        .check-marca-exito {
            transform-origin: 50% 50%;
            stroke-dasharray: 48;
            stroke-dashoffset: 48;
            animation: trazo 0.3s cubic-bezier(0.65, 0, 0.45, 1) 0.8s forwards;
        }

        @keyframes trazo {
            100% {
                stroke-dashoffset: 0;
            }
        }

        @keyframes escalar {
            0%, 100% {
                transform: none;
            }
            50% {
                transform: scale3d(1.1, 1.1, 1);
            }
        }

        @keyframes llenar {
            100% {
                box-shadow: inset 0px 0px 0px 30px currentColor;
            }
        }

        /* Diseño Responsivo */
        @media (max-width: 768px) {
            .encabezado-banner {
                flex-direction: column;
                text-align: center;
            }

            .acciones-banner {
                justify-content: center;
                flex-direction: column;
            }

            .btn-deslizamiento {
                width: 100%;
                min-width: auto;
            }

            .cuadricula-detalles {
                grid-template-columns: 1fr;
            }

            .contenido-banner {
                padding: 1rem;
            }
        }

        @media (max-width: 480px) {
            body {
                padding: 1rem;
            }

            .contenedor-demo h1 {
                font-size: 2rem;
            }

            .contenido-banner {
                padding: 0.75rem;
            }

            .titulo-banner {
                font-size: 1.1rem;
            }

            .descripcion-banner {
                font-size: 0.9rem;
            }
        }

        /* Variantes de Animación de Deslizamiento */
        .deslizar-izquierda {
            transform: translateX(-100%);
        }

        .deslizar-derecha {
            transform: translateX(100%);
        }

        .deslizar-desvanecer {
            transform: translateY(100%) scale(0.9);
            opacity: 0;
        }

        .deslizar-desvanecer.mostrar {
            transform: translateY(0) scale(1);
            opacity: 1;
        }

        /* Efecto de Rebote */
        .rebote-entrada {
            animation: reboteEntrada 0.6s cubic-bezier(0.68, -0.55, 0.265, 1.55);
        }

        @keyframes reboteEntrada {
            0% {
                transform: translateY(100%) scale(0.3);
                opacity: 0;
            }
            50% {
                transform: translateY(-10%) scale(1.05);
            }
            70% {
                transform: translateY(5%) scale(0.98);
            }
            100% {
                transform: translateY(0) scale(1);
                opacity: 1;
            }
        }
    </style>
</head>
<body>
    <div class="contenedor-demo">
        <h1>Diseño de Deslizamiento Suave</h1>
        <p>Experimenta la elegancia de las transiciones de deslizamiento suave con divulgación progresiva e interacciones modernas</p>
        <button class="btn-demo" onclick="mostrarBannerCookies()">Mostrar Banner de Cookies</button>
    </div>

    <!-- Banner de Cookies Deslizamiento Inferior -->
    <div id="bannerCookiesDeslizamientoInferior" class="banner-cookies-deslizamiento-inferior">
        <div class="indicador-progreso"></div>
        <div class="contenido-banner">
            <div class="encabezado-banner">
                <div class="icono-banner">🍪</div>
                <div class="texto-banner">
                    <div class="titulo-banner">Preferencias de Cookies</div>
                    <div class="descripcion-banner">
                        Utilizamos cookies para mejorar tu experiencia de navegación y proporcionar contenido personalizado. 
                        <a href="#" class="enlace-cookies">Política de Privacidad</a> | 
                        <a href="#" class="enlace-cookies">Política de Cookies</a>
                    </div>
                </div>
            </div>
            <div class="acciones-banner">
                <button class="btn-deslizamiento btn-aceptar" onclick="aceptarCookies()">Aceptar Todo</button>
                <button class="btn-deslizamiento btn-rechazar" onclick="rechazarCookies()">Rechazar</button>
                <button class="btn-deslizamiento btn-personalizar" onclick="abrirPersonalizacion()">Personalizar</button>
                <button class="btn-deslizamiento btn-expandir" onclick="alternarDetalles()">Saber Más</button>
            </div>
            
            <!-- Detalles Expandibles -->
            <div id="detallesExpandibles" class="detalles-expandibles">
                <div class="cuadricula-detalles">
                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies Esenciales</span>
                            <div class="interruptor-deslizamiento activo" data-categoria="esenciales"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies son necesarias para que el sitio web funcione y no se pueden desactivar. Generalmente solo se establecen en respuesta a acciones realizadas por ti.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies de Análisis</span>
                            <div class="interruptor-deslizamiento" data-categoria="analiticas"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies nos ayudan a entender cómo los visitantes interactúan con nuestro sitio web recopilando y reportando información de forma anónima.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies de Marketing</span>
                            <div class="interruptor-deslizamiento" data-categoria="marketing"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies se utilizan para entregar anuncios más relevantes para ti y tus intereses basados en tu comportamiento de navegación.
                        </div>
                    </div>

                    <div class="categoria-cookies">
                        <div class="encabezado-categoria">
                            <span class="titulo-categoria">Cookies Funcionales</span>
                            <div class="interruptor-deslizamiento" data-categoria="funcionales"></div>
                        </div>
                        <div class="descripcion-categoria">
                            Estas cookies habilitan funcionalidad mejorada y personalización, como recordar tus preferencias y configuraciones.
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <script>
        class BannerCookiesDeslizamientoInferior {
            constructor(opciones = {}) {
                this.opciones = {
                    mostrarAuto: true,
                    retrasoMostrar: 1500,
                    claveAlmacenamiento: 'consentimiento_cookies_deslizamiento_inferior',
                    diasExpiracion: 365,
                    habilitarAnimaciones: true,
                    direccionDeslizamiento: 'inferior',
                    tipoAnimacion: 'deslizar', // 'deslizar', 'desvanecer', 'rebote'
                    divulgacionProgresiva: true,
                    alAceptar: null,
                    alRechazar: null,
                    alPersonalizar: null,
                    ...opciones
                };

                this.banner = document.getElementById('bannerCookiesDeslizamientoInferior');
                this.detallesExpandibles = document.getElementById('detallesExpandibles');
                this.consentimiento = this.obtenerConsentimientoAlmacenado();
                this.esVisible = false;
                this.estaExpandido = false;

                this.inicializar();
            }

            inicializar() {
                if (this.opciones.mostrarAuto && !this.consentimiento) {
                    setTimeout(() => this.mostrar(), this.opciones.retrasoMostrar);
                }

                this.configurarEventListeners();
                this.cargarConfiguracion();
                this.configurarTipoAnimacion();
            }

            configurarEventListeners() {
                // Interruptores de alternancia
                document.querySelectorAll('.interruptor-deslizamiento').forEach(interruptor => {
                    interruptor.addEventListener('click', () => {
                        if (interruptor.dataset.categoria !== 'esenciales') {
                            interruptor.classList.toggle('activo');
                            this.animarInterruptor(interruptor);
                        }
                    });
                });

                // Navegación por teclado
                document.addEventListener('keydown', (e) => {
                    if (e.key === 'Escape' && this.estaExpandido) {
                        this.alternarDetalles();
                    }
                });

                // Efectos hover de botones
                document.querySelectorAll('.btn-deslizamiento').forEach(btn => {
                    btn.addEventListener('mouseenter', () => {
                        this.crearOnda(btn);
                    });
                });

                // Indicador de progreso al hacer hover
                this.banner.addEventListener('mouseenter', () => {
                    if (this.esVisible) {
                        this.mejorarIndicadorProgreso();
                    }
                });

                this.banner.addEventListener('mouseleave', () => {
                    if (this.esVisible) {
                        this.resetearIndicadorProgreso();
                    }
                });
            }

            configurarTipoAnimacion() {
                const clasesAnimacion = {
                    deslizar: '',
                    desvanecer: 'deslizar-desvanecer',
                    rebote: 'rebote-entrada'
                };

                const claseAnimacion = clasesAnimacion[this.opciones.tipoAnimacion];
                if (claseAnimacion) {
                    this.banner.classList.add(claseAnimacion);
                }
            }

            animarInterruptor(interruptor) {
                if (!this.opciones.habilitarAnimaciones) return;

                interruptor.style.transform = 'scale(0.9)';
                setTimeout(() => {
                    interruptor.style.transform = 'scale(1)';
                }, 150);

                // Agregar efecto de pulso
                interruptor.style.boxShadow = '0 0 0 8px rgba(5, 150, 105, 0.2)';
                setTimeout(() => {
                    interruptor.style.boxShadow = '';
                }, 300);
            }

            crearOnda(boton) {
                if (!this.opciones.habilitarAnimaciones) return;

                const onda = document.createElement('span');
                const rect = boton.getBoundingClientRect();
                const tamaño = Math.max(rect.width, rect.height);
                
                onda.style.width = onda.style.height = tamaño + 'px';
                onda.style.left = '50%';
                onda.style.top = '50%';
                onda.style.transform = 'translate(-50%, -50%) scale(0)';
                onda.style.position = 'absolute';
                onda.style.borderRadius = '50%';
                onda.style.background = 'rgba(255, 255, 255, 0.3)';
                onda.style.pointerEvents = 'none';
                onda.style.animation = 'onda 0.6s ease-out';
                
                boton.style.position = 'relative';
                boton.style.overflow = 'hidden';
                boton.appendChild(onda);
                
                setTimeout(() => {
                    onda.remove();
                }, 600);
            }

            mejorarIndicadorProgreso() {
                if (!this.opciones.habilitarAnimaciones) return;
                
                const indicador = this.banner.querySelector('.indicador-progreso');
                if (indicador) {
                    indicador.style.background = 'linear-gradient(90deg, var(--color-primario), var(--color-exito))';
                    indicador.style.height = '4px';
                }
            }

            resetearIndicadorProgreso() {
                if (!this.opciones.habilitarAnimaciones) return;
                
                const indicador = this.banner.querySelector('.indicador-progreso');
                if (indicador) {
                    indicador.style.background = 'var(--color-primario)';
                    indicador.style.height = '3px';
                }
            }

            mostrar() {
                this.banner.classList.add('mostrar');
                this.esVisible = true;
                
                if (this.opciones.habilitarAnimaciones) {
                    this.animarEntrada();
                }
            }

            ocultar() {
                this.banner.classList.remove('mostrar');
                this.esVisible = false;
                this.estaExpandido = false;
                this.detallesExpandibles.classList.remove('expandido');
            }

            animarEntrada() {
                const elementos = [
                    this.banner.querySelector('.icono-banner'),
                    this.banner.querySelector('.titulo-banner'),
                    this.banner.querySelector('.descripcion-banner'),
                    this.banner.querySelector('.acciones-banner')
                ];

                elementos.forEach((el, index) => {
                    if (el) {
                        el.style.opacity = '0';
                        el.style.transform = 'translateY(20px)';
                        
                        setTimeout(() => {
                            el.style.transition = 'all 0.6s cubic-bezier(0.4, 0, 0.2, 1)';
                            el.style.opacity = '1';
                            el.style.transform = 'translateY(0)';
                        }, index * 100);
                    }
                });
            }

            alternarDetalles() {
                this.estaExpandido = !this.estaExpandido;
                
                if (this.estaExpandido) {
                    this.detallesExpandibles.classList.add('expandido');
                    if (this.opciones.habilitarAnimaciones) {
                        this.animarExpansionDetalles();
                    }
                } else {
                    this.detallesExpandibles.classList.remove('expandido');
                }

                // Actualizar texto del botón
                const btnExpandir = this.banner.querySelector('.btn-expandir');
                if (btnExpandir) {
                    btnExpandir.textContent = this.estaExpandido ? 'Mostrar Menos' : 'Saber Más';
                }
            }

            animarExpansionDetalles() {
                const categorias = this.detallesExpandibles.querySelectorAll('.categoria-cookies');
                categorias.forEach((categoria, index) => {
                    categoria.style.opacity = '0';
                    categoria.style.transform = 'translateY(20px)';
                    
                    setTimeout(() => {
                        categoria.style.transition = 'all 0.4s cubic-bezier(0.4, 0, 0.2, 1)';
                        categoria.style.opacity = '1';
                        categoria.style.transform = 'translateY(0)';
                    }, index * 100);
                });
            }

            aceptar() {
                const consentimiento = {
                    esenciales: true,
                    analiticas: true,
                    marketing: true,
                    funcionales: true,
                    marcaTiempo: Date.now()
                };

                this.guardarConsentimiento(consentimiento);
                this.mostrarAnimacionExito();
                
                setTimeout(() => {
                    this.ocultar();
                }, 1500);

                if (this.opciones.alAceptar) {
                    this.opciones.alAceptar(consentimiento);
                }
            }

            rechazar() {
                const consentimiento = {
                    esenciales: true,
                    analiticas: false,
                    marketing: false,
                    funcionales: false,
                    marcaTiempo: Date.now()
                };

                this.guardarConsentimiento(consentimiento);
                this.ocultar();

                if (this.opciones.alRechazar) {
                    this.opciones.alRechazar(consentimiento);
                }
            }

            mostrarAnimacionExito() {
                if (!this.opciones.habilitarAnimaciones) return;

                const btnAceptar = this.banner.querySelector('.btn-aceptar');
                if (btnAceptar) {
                    btnAceptar.innerHTML = `
                        <svg class="marca-exito" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 52 52">
                            <circle class="circulo-marca-exito" cx="26" cy="26" r="25" fill="none"/>
                            <path class="check-marca-exito" fill="none" d="m14.1 27.2l7.1 7.2 16.7-16.8"/>
                        </svg>
                        Aceptado
                    `;
                    btnAceptar.style.background = 'var(--color-exito)';
                }
            }

            personalizar() {
                this.alternarDetalles();
                
                if (this.opciones.alPersonalizar) {
                    this.opciones.alPersonalizar();
                }
            }

            guardarPersonalizacion() {
                const interruptores = document.querySelectorAll('.interruptor-deslizamiento');
                const consentimiento = { marcaTiempo: Date.now() };

                interruptores.forEach(interruptor => {
                    const categoria = interruptor.dataset.categoria;
                    consentimiento[categoria] = interruptor.classList.contains('activo');
                });

                this.guardarConsentimiento(consentimiento);
                this.ocultar();

                if (this.opciones.alPersonalizar) {
                    this.opciones.alPersonalizar(consentimiento);
                }
            }

            cargarConfiguracion() {
                if (this.consentimiento) {
                    document.querySelectorAll('.interruptor-deslizamiento').forEach(interruptor => {
                        const categoria = interruptor.dataset.categoria;
                        if (this.consentimiento[categoria]) {
                            interruptor.classList.add('activo');
                        } else {
                            interruptor.classList.remove('activo');
                        }
                    });
                }
            }

            guardarConsentimiento(consentimiento) {
                const fechaExpiracion = new Date();
                fechaExpiracion.setDate(fechaExpiracion.getDate() + this.opciones.diasExpiracion);
                
                const datosConsentimiento = {
                    ...consentimiento,
                    expiracion: fechaExpiracion.getTime()
                };

                localStorage.setItem(this.opciones.claveAlmacenamiento, JSON.stringify(datosConsentimiento));
                this.consentimiento = consentimiento;
            }

            obtenerConsentimientoAlmacenado() {
                try {
                    const almacenado = localStorage.getItem(this.opciones.claveAlmacenamiento);
                    if (almacenado) {
                        const datos = JSON.parse(almacenado);
                        if (datos.expiracion && Date.now() < datos.expiracion) {
                            return datos;
                        } else {
                            localStorage.removeItem(this.opciones.claveAlmacenamiento);
                        }
                    }
                } catch (e) {
                    console.error('Error al leer el consentimiento de cookies:', e);
                }
                return null;
            }

            resetear() {
                localStorage.removeItem(this.opciones.claveAlmacenamiento);
                this.consentimiento = null;
                this.mostrar();
            }

            obtenerConsentimiento() {
                return this.consentimiento;
            }

            establecerDireccionDeslizamiento(direccion) {
                this.opciones.direccionDeslizamiento = direccion;
                this.configurarDireccionDeslizamiento();
            }

            configurarDireccionDeslizamiento() {
                const direcciones = {
                    inferior: 'translateY(100%)',
                    superior: 'translateY(-100%)',
                    izquierda: 'translateX(-100%)',
                    derecha: 'translateX(100%)'
                };

                const transformacion = direcciones[this.opciones.direccionDeslizamiento] || direcciones.inferior;
                document.documentElement.style.setProperty('--distancia-deslizamiento', transformacion);
            }

            establecerTipoAnimacion(tipo) {
                this.opciones.tipoAnimacion = tipo;
                this.configurarTipoAnimacion();
            }

            habilitarAnimaciones(habilitado) {
                this.opciones.habilitarAnimaciones = habilitado;
            }

            actualizarTema(tema) {
                const temas = {
                    claro: {
                        '--fondo': '#ffffff',
                        '--superficie': '#f9fafb',
                        '--texto-primario': '#111827',
                        '--texto-secundario': '#6b7280'
                    },
                    oscuro: {
                        '--fondo': '#1f2937',
                        '--superficie': '#374151',
                        '--texto-primario': '#f9fafb',
                        '--texto-secundario': '#d1d5db'
                    }
                };

                if (temas[tema]) {
                    Object.entries(temas[tema]).forEach(([propiedad, valor]) => {
                        document.documentElement.style.setProperty(propiedad, valor);
                    });
                }
            }
        }

        // Agregar animación de onda CSS
        const estilo = document.createElement('style');
        estilo.textContent = `
            @keyframes onda {
                to {
                    transform: translate(-50%, -50%) scale(2);
                    opacity: 0;
                }
            }
        `;
        document.head.appendChild(estilo);

        // Inicializar el banner
        const bannerCookies = new BannerCookiesDeslizamientoInferior({
            direccionDeslizamiento: 'inferior',
            tipoAnimacion: 'deslizar',
            habilitarAnimaciones: true,
            divulgacionProgresiva: true,
            alAceptar: (consentimiento) => {
                console.log('Cookies aceptadas:', consentimiento);
                // Inicializar scripts de análisis, marketing, etc.
            },
            alRechazar: (consentimiento) => {
                console.log('Cookies rechazadas:', consentimiento);
                // Cargar solo scripts esenciales
            },
            alPersonalizar: (consentimiento) => {
                console.log('Configuración personalizada guardada:', consentimiento);
                // Cargar scripts basados en las preferencias del usuario
            }
        });

        // Funciones globales para la demo
        function mostrarBannerCookies() {
            bannerCookies.resetear();
        }

        function aceptarCookies() {
            bannerCookies.aceptar();
        }

        function rechazarCookies() {
            bannerCookies.rechazar();
        }

        function abrirPersonalizacion() {
            bannerCookies.personalizar();
        }

        function alternarDetalles() {
            bannerCookies.alternarDetalles();
        }
    </script>
</body>
</html>

              
1090líneas
37422caracteres
HTMLIdioma

Fragmentos de Código Relacionados

Explora packs de plantillas

¿Necesitas bloques más grandes? Descubre landings y colecciones de componentes.

Abrir la biblioteca de plantillas →