mejoras de estructura

This commit is contained in:
2026-09-14 17:08:10 -03:00
parent 62467348f4
commit 7c13f697db
21 changed files with 1650 additions and 1591 deletions
+15 -9
View File
@@ -1,14 +1,20 @@
# AGENTS.md para Web A&R 2026 # AGENTS.md para Web A&R 2026
## Estructura del sitio web ## Estructura y Archivos Clave
Sitio corporativo simple para agencia de marketing digital: - **Páginas principales**: index.html, nosotros.html, servicios.html, planes.html
- Archivos HTML principales: index.html, nosotros.html, servicios.html, planes.html - **Componentes reutilizables** en `partials/` (menu.html, footer.html)
- Componentes reutilizables en `include/` (header.html, footer.html) - **Assets vacíos**: assets/, styles/ (diseño pendiente)
- assets/ y styles/ directorios vacíos - diseño pendiente - **Scripts JavaScript**: scripts/loader.js, scripts/main.js
## Convenciones ## Convenciones Específicas del Repo
- Nombre de la empresa: Amor&Roma (incluye símbolo "&" - no acento) - **Nombre correcto**: Amor&Roma (símbolo "&", NO acento ni tilde)
- Estética boutique como enfoque de diseño - **Estructura**: HTML/CSS vanilla, sin frameworks detectados
- Desarrollado con HTML/CSS vanilla (sin frameworks detectados en el código actual) - **Componentes reutilizables**: Los partials se incluyen en páginas principales (ej: include header html)
- **Nomenclatura de archivos**: Minúsculas con nombres descriptivos
## Convenciones Técnicas
- Usar doble comillas (") para rutas que contienen "&&" de caracteres especiales
- Directorios `partials/` y `scripts/` se reflejan en la estructura como subdirectorios no raíces
+15
View File
@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Creator: CorelDRAW -->
<svg xmlns="http://www.w3.org/2000/svg" xml:space="preserve" width="24px" height="23px" version="1.1" shape-rendering="geometricPrecision" text-rendering="geometricPrecision" image-rendering="optimizeQuality" fill-rule="evenodd" clip-rule="evenodd"
viewBox="0 0 19.25 18.03"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:xodm="http://www.corel.com/coreldraw/odm/2003">
<g id="Capa_x0020_1">
<metadata id="CorelCorpID_0Corel-Layer"/>
<g id="_2093823756928">
<path fill="#221728" d="M7.84 0.1c-4.73,0.69 -8.82,5.04 -7.63,10.74 1.35,6.49 9.06,9.42 14.33,5.28 1.22,-0.97 1.65,-2.03 -0.69,-2.08 -6.25,-0.13 -8.69,-8.49 -3.17,-11.93 0.49,-0.31 1.13,-0.49 0.93,-1.27 -0.27,-1.01 -2.69,-0.9 -3.77,-0.74z"/>
<path fill="#221728" fill-opacity="0.501961" d="M15.94 10.42c0.28,-0.75 0.32,-1.79 0.77,-2.16 0.53,-0.43 2.54,-0.37 2.54,-1.18 0,-0.81 -2.01,-0.75 -2.54,-1.18 -0.42,-0.34 -0.48,-1.25 -0.71,-1.98 -0.4,-1.3 -0.97,-0.66 -1.24,0.33 -0.07,0.26 -0.35,1.32 -0.46,1.49 -0.46,0.73 -2.68,0.35 -2.68,1.34 0,0.95 2.12,0.66 2.63,1.26 0.44,0.53 0.36,1.48 0.63,2.06 0.26,0.59 0.79,0.76 1.06,0.02z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.3 KiB

+15
View File
@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Creator: CorelDRAW -->
<svg xmlns="http://www.w3.org/2000/svg" xml:space="preserve" width="24px" height="24px" version="1.1" shape-rendering="geometricPrecision" text-rendering="geometricPrecision" image-rendering="optimizeQuality" fill-rule="evenodd" clip-rule="evenodd"
viewBox="0 0 27.53 27.44"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:xodm="http://www.corel.com/coreldraw/odm/2003">
<g id="Capa_x0020_1">
<metadata id="CorelCorpID_0Corel-Layer"/>
<g id="_2056493314832">
<path fill="#EAF0EE" d="M7.69 14.34c0.25,3.13 3.12,5.73 6.6,5.46 3.21,-0.25 5.83,-3.1 5.51,-6.68 -0.7,-7.79 -12.79,-7 -12.11,1.22z"/>
<path fill="#EAF0EE" fill-opacity="0.501961" d="M27.26 14.34c1.6,-2.21 -4.39,-2.18 -4.95,-1.26 -1.49,2.44 4.33,2.12 4.95,1.26zm-13.92 -14.23c-1.02,0.38 -0.71,1.88 -0.72,3.12 -0.01,1.12 0.11,2.64 1.57,2.03 0.96,-0.4 0.67,-1.99 0.68,-3.1 0.01,-1.1 -0.12,-2.58 -1.53,-2.05zm9.58 23.61c0.58,-0.13 0.9,-0.61 0.81,-1.3 -0.09,-0.67 -1.66,-1.89 -2.08,-2.35 -0.39,-0.42 -0.63,-0.93 -1.53,-0.71 -0.59,0.15 -0.86,0.73 -0.74,1.37 0.07,0.38 1.75,1.94 2.07,2.29 0.32,0.34 0.68,0.86 1.47,0.7zm-18.39 -19.95c-1.89,0.65 -0.09,2.26 0.32,2.67 0.47,0.47 1.53,2.05 2.69,1.6 0.42,-0.17 0.76,-0.71 0.57,-1.37 -0.13,-0.41 -1.64,-1.74 -2.13,-2.27 -0.36,-0.39 -0.67,-0.9 -1.45,-0.63zm17.72 0.03c-0.58,0.27 -1.83,1.65 -2.34,2.15 -1.19,1.18 -0.27,2.59 1.03,2.1 0.36,-0.14 1.86,-1.83 2.25,-2.18 1.35,-1.21 0.07,-2.52 -0.94,-2.07zm-14.2 17.26c0.57,-1.05 -0.7,-2.55 -1.99,-1.27 -0.36,0.37 -2.03,1.98 -2.17,2.26 -0.61,1.21 0.8,2.43 1.95,1.17 0.24,-0.26 2.18,-2.11 2.21,-2.16zm6.7 5.76c0.19,-0.35 0.18,-3.07 0.11,-3.64 -0.15,-1.27 -2.96,-2.69 -2.23,3.18 0.16,1.29 1.6,1.39 2.12,0.46zm-9.55 -12.48c1.59,-2.21 -4.4,-2.18 -4.96,-1.26 -1.49,2.44 4.33,2.12 4.96,1.26z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

+68
View File
@@ -0,0 +1,68 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Blog - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
<link rel="stylesheet" href="style/blog.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<!-- Sección 1: Encabezado del blog -->
<section id="blog-section-1">
<h2>Blog</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 2: Filtros dinámicos -->
<section id="blog-section-2">
<div class="blog-filters">
<label for="filter-category">Categoría:</label>
<select id="filter-category">
<option value="">Todas</option>
<!-- Las opciones se cargarán dinámicamente -->
</select>
<label for="filter-date-from">Desde:</label>
<input type="date" id="filter-date-from">
<label for="filter-date-to">Hasta:</label>
<input type="date" id="filter-date-to">
<button type="button" id="btn-apply-filters">Aplicar filtros</button>
<button type="button" id="btn-clear-filters">Limpiar</button>
</div>
</section>
<!-- Sección 3: Listado de artículos -->
<section id="blog-section-3">
<div class="blog-list" id="blog-list">
<!-- Los artículos se inyectarán aquí desde PHP/DB -->
<p>Cargando artículos...</p>
</div>
</section>
<!-- Sección 4: Paginación -->
<section id="blog-section-4">
<nav class="blog-pagination" id="blog-pagination" aria-label="Paginación del blog">
<!-- Controles de paginación -->
</nav>
</section>
<!-- Sección 5: CTA / Suscripción -->
<section id="blog-section-5">
<h2>Suscríbete</h2>
<p>Contenido pendiente de definir.</p>
</section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
+70
View File
@@ -0,0 +1,70 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Contacto - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<!-- Sección 1: Encabezado -->
<section id="contacto-section-1">
<h2>Contacto</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 2: Formulario de contacto -->
<section id="contacto-section-2">
<h3>Escríbenos</h3>
<form class="contact-form" id="contact-form" novalidate>
<label for="contact-name">Nombre</label>
<input type="text" id="contact-name" name="name" required>
<label for="contact-email">Email</label>
<input type="email" id="contact-email" name="email" required>
<label for="contact-phone">Teléfono (opcional)</label>
<input type="tel" id="contact-phone" name="phone">
<label for="contact-subject">Asunto</label>
<input type="text" id="contact-subject" name="subject" required>
<label for="contact-message">Mensaje</label>
<textarea id="contact-message" name="message" rows="5" required></textarea>
<button type="submit">Enviar mensaje</button>
</form>
</section>
<!-- Sección 3: Redes sociales -->
<section id="contacto-section-3">
<h3>Síguenos</h3>
<ul class="contact-social">
<li><a href="#" target="_blank" rel="noopener">[Red 1]</a></li>
<li><a href="#" target="_blank" rel="noopener">[Red 2]</a></li>
<li><a href="#" target="_blank" rel="noopener">[Red 3]</a></li>
</ul>
</section>
<!-- Sección 4: WhatsApp directo -->
<section id="contacto-section-4">
<h3>¿Prefieres WhatsApp?</h3>
<a class="whatsapp-link"
href="https://wa.me/[NUMERO]?text=[MENSAJE_PREDEFINIDO]"
target="_blank"
rel="noopener">
Escríbenos por WhatsApp
</a>
</section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
+38
View File
@@ -0,0 +1,38 @@
<footer class="site-footer">
<div class="footer-content">
<div class="footer-col" id="footer-brand">
<!-- Marca / logo -->
<span>[Logo]</span>
<p>[Descripción breve]</p>
</div>
<div class="footer-col" id="footer-links">
<h4>Enlaces</h4>
<ul>
<li><a href="inicio.html">Inicio</a></li>
<li><a href="servicios.html">Servicios</a></li>
<li><a href="planes.html">Planes</a></li>
<li><a href="portfolio.html">Portfolio</a></li>
<li><a href="nosotros.html">Nosotros</a></li>
<li><a href="blog.html">Blog</a></li>
<li><a href="contacto.html">Contacto</a></li>
</ul>
</div>
<div class="footer-col" id="footer-contact">
<h4>Contacto</h4>
<p>[Teléfono]</p>
<p>[Email]</p>
<p>[Dirección]</p>
</div>
<div class="footer-col" id="footer-social">
<h4>Redes</h4>
<ul>
<li><a href="#" target="_blank" rel="noopener">[Red 1]</a></li>
<li><a href="#" target="_blank" rel="noopener">[Red 2]</a></li>
<li><a href="#" target="_blank" rel="noopener">[Red 3]</a></li>
</ul>
</div>
</div>
<div class="footer-bottom">
<p>&copy; <span id="current-year"></span> [Nombre de la agencia]. Todos los derechos reservados.</p>
</div>
</footer>
+76
View File
@@ -0,0 +1,76 @@
<header class="site-header">
<nav class="main-nav">
<a href="inicio.html" class="logo">
<img src="assets/logos/logo_ciruela.png" alt="Logo" class="logo-light">
<img src="assets/logos/logo_frio.png" alt="Logo" class="logo-dark">
</a>
<div class="nav-actions">
<button class="theme-toggle" aria-label="Cambiar tema">
<img src="assets/iconos/moon.svg" alt="Modo oscuro" class="theme-icon icon-moon">
<img src="assets/iconos/sun.svg" alt="Modo claro" class="theme-icon icon-sun">
</button>
<button class="menu-toggle" aria-label="Abrir menú" aria-expanded="false">
Menú
</button>
</div>
</nav>
</header>
<!-- Overlay para cerrar el menú -->
<div class="menu-overlay" id="menu-overlay"></div>
<!-- Menú fullscreen -->
<div class="fullscreen-menu" id="fullscreen-menu">
<button class="menu-close" aria-label="Cerrar menú">✕</button>
<div class="menu-content">
<!-- Columna 1: Navegación de inicio -->
<div class="menu-column">
<h3>Inicio</h3>
<ul>
<li><a href="inicio.html#section-1">Sección 1</a></li>
<li><a href="inicio.html#section-2">Sección 2</a></li>
<li><a href="inicio.html#section-3">Sección 3</a></li>
<li><a href="inicio.html#section-4">Sección 4</a></li>
<li><a href="inicio.html#section-5">Sección 5</a></li>
<li><a href="inicio.html#section-6">Sección 6</a></li>
<li><a href="inicio.html#section-7">Sección 7</a></li>
</ul>
</div>
<!-- Columna 2: Sitemap y políticas -->
<div class="menu-column">
<h3>Navegación</h3>
<ul>
<li><a href="inicio.html">Inicio</a></li>
<li><a href="servicios.html">Servicios</a></li>
<li><a href="planes.html">Planes</a></li>
<li><a href="portfolio.html">Portfolio</a></li>
<li><a href="nosotros.html">Nosotros</a></li>
<li><a href="blog.html">Blog</a></li>
<li><a href="contacto.html">Contacto</a></li>
</ul>
</div>
<!-- Columna 3: Contacto y botones -->
<div class="menu-column">
<h3>Contacto</h3>
<div class="menu-contact-info">
<p>📧 info@agencia.com</p>
<p>📞 +34 123 456 789</p>
<div class="menu-social">
<a href="https://instagram.com" target="_blank" rel="noopener">Instagram</a>
<a href="https://facebook.com" target="_blank" rel="noopener">Facebook</a>
<a href="https://linkedin.com" target="_blank" rel="noopener">LinkedIn</a>
</div>
</div>
<div class="menu-buttons">
<a href="contacto.html" class="btn-menu btn-menu-primary">Hablemos</a>
<a href="trabaja.html" class="btn-menu btn-menu-secondary">Trabaja con nosotros</a>
</div>
</div>
</div>
</div>
-562
View File
@@ -1,562 +0,0 @@
<!DOCTYPE html>
<html lang="es">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Amor & Roma — Estudio Creativo</title>
<link rel="stylesheet" href="styles/main.css">
<link rel="preload" href="partials/menu.html" as="fetch" crossorigin>
<link rel="preload" href="partials/footer.html" as="fetch" crossorigin>
</head>
<body>
<!-- ===== CANVAS PARA EFECTO DE HUMO ===== -->
<canvas id="fluidCanvas"></canvas>
<!-- ===== OVERLAY ===== -->
<div class="overlay" id="overlay" onclick="toggleMenu()"></div>
<!-- ===== MENU BOTTOM SHEET ===== -->
<div id="menu-placeholder"></div>
<!-- ===== HEADER ===== -->
<header>
<div class="logo">
<a href="#inicio">
<img src="./assets/logos/logo_frio.png" alt="Amor & Roma" class="logo-img">
</a>
</div>
<button class="menu-btn" onclick="toggleMenu()" aria-label="Abrir menú">
<span class="bars"><span></span><span></span><span></span></span>
<span class="menu-label">Menú</span>
</button>
</header>
<!-- ===== HERO ===== -->
<section class="hero" id="inicio">
<div class="hero-content">
<div class="eyebrow">Estudio Creativo · Agencia Boutique</div>
<h1>Marcas con <span class="grad-word">esencia,</span><br>construidas con <span class="grad-word">estrategia.</span></h1>
<p>Branding, diseño web y marketing digital para negocios que quieren crecer sin perder lo que los hace únicos.</p>
<div class="hero-actions">
<a href="#servicios" class="btn btn-solid">Ver servicios</a>
<a href="#contacto" class="btn btn-outline">Contactanos</a>
</div>
</div>
<div class="scroll-hint"><div class="line"></div>Scroll</div>
</section>
<!-- ===== SERVICIOS ===== -->
<section class="servicios" id="servicios">
<div class="eyebrow">Lo que hacemos</div>
<h2>Servicios pensados para marcas con <span class="grad-word">esencia.</span></h2>
<p class="lede">Cuatro disciplinas que trabajan juntas, no por separado — cada proyecto se arma con la combinación justa para tu marca.</p>
<div class="tabs">
<button class="tab active" onclick="showTab(0,this)"><span class="num">01</span>Branding</button>
<button class="tab" onclick="showTab(1,this)"><span class="num">02</span>Diseño Web</button>
<button class="tab" onclick="showTab(2,this)"><span class="num">03</span>Marketing Digital</button>
<button class="tab" onclick="showTab(3,this)"><span class="num">04</span>IA & Automatización</button>
</div>
<div class="panel active" data-panel="0">
<div class="panel-copy">
<h3>Identidad con <em>alma,</em><br>no solo con estilo.</h3>
<p>Construimos el sistema visual y verbal que sostiene tu marca: desde el naming y el logo hasta el tono de voz con el que hablás en cada canal.</p>
<a href="#contacto" class="btn btn-outline">Quiero mi identidad de marca →</a>
</div>
<div class="panel-list">
<div class="item"><span class="icon-min">✦</span> Naming y concepto de marca</div>
<div class="item"><span class="icon-min">✦</span> Diseño de logo e isotipo</div>
<div class="item"><span class="icon-min">✦</span> Paleta, tipografía y manual de marca</div>
<div class="item"><span class="icon-min">✦</span> Tono de voz y guía de comunicación</div>
</div>
</div>
<div class="panel" data-panel="1">
<div class="panel-copy">
<h3>Sitios que <em>convierten,</em><br>no solo que se ven bien.</h3>
<p>Diseño y desarrollo de sitios web a medida — rápidos, responsivos y pensados para que quien llega, actúe.</p>
<a href="#contacto" class="btn btn-outline">Quiero mi sitio web →</a>
</div>
<div class="panel-list">
<div class="item"><span class="icon-min">✦</span> Landing pages y sitios institucionales</div>
<div class="item"><span class="icon-min">✦</span> UX/UI a medida</div>
<div class="item"><span class="icon-min">✦</span> Optimización SEO técnica</div>
<div class="item"><span class="icon-min">✦</span> E-commerce y tiendas online</div>
</div>
</div>
<div class="panel" data-panel="2">
<div class="panel-copy">
<h3>Presencia <em>constante,</em><br>estrategia real.</h3>
<p>Gestión de redes, contenido y pauta — con reportes claros para que sepas siempre qué está funcionando y por qué.</p>
<a href="#contacto" class="btn btn-outline">Quiero mi estrategia digital →</a>
</div>
<div class="panel-list">
<div class="item"><span class="icon-min">✦</span> Community management</div>
<div class="item"><span class="icon-min">✦</span> Publicidad en Meta e Instagram Ads</div>
<div class="item"><span class="icon-min">✦</span> Estrategia de contenido y calendario</div>
<div class="item"><span class="icon-min">✦</span> Reportes mensuales de performance</div>
</div>
</div>
<div class="panel" data-panel="3">
<div class="panel-copy">
<h3>Tecnología al servicio<br>de <em>tu tiempo.</em></h3>
<p>Automatizamos lo repetitivo para que tu equipo se enfoque en lo estratégico — sin perder el trato cercano con tus clientes.</p>
<a href="#contacto" class="btn btn-outline">Quiero automatizar procesos →</a>
</div>
<div class="panel-list">
<div class="item"><span class="icon-min">✦</span> Chatbots y respuestas automáticas</div>
<div class="item"><span class="icon-min">✦</span> Automatización de leads y seguimiento</div>
<div class="item"><span class="icon-min">✦</span> Integraciones con CRM y WhatsApp</div>
<div class="item"><span class="icon-min">✦</span> Consultoría en IA aplicada a tu negocio</div>
</div>
</div>
</section>
<!-- ===== PLANES ===== -->
<section class="planes" id="planes">
<div class="eyebrow">Inversión</div>
<h2>Un plan para cada <span class="grad-word">etapa</span> de tu marca.</h2>
<p class="lede">Cuatro niveles pensados para acompañar tu crecimiento — desde presencia digital consistente hasta gestión integral de marca.</p>
<div class="plans-grid">
<div class="plan-card">
<div class="plan-name">Esencial</div>
<div class="plan-stars">★</div>
<div class="plan-obj">Establecer una presencia digital profesional y consistente.</div>
<ul class="plan-feats">
<li>2 redes sociales</li>
<li>8 publicaciones + 8 historias / mes</li>
<li>1 diseño de marca (logo)</li>
<li>Reunión mensual de estrategia</li>
<li>Reporte mensual de métricas</li>
</ul>
<a href="#contacto" class="plan-cta">+Info</a>
</div>
<div class="plan-card">
<div class="plan-name">Impulso</div>
<div class="plan-stars">★★</div>
<div class="plan-obj">Aumentar visibilidad, interacción y generación de leads calificados.</div>
<ul class="plan-feats">
<li>2 redes · 12 publicaciones + 4 reels</li>
<li>Logo + paleta de colores</li>
<li>1 campaña Meta Ads + retargeting</li>
<li>Automatización de respuestas frecuentes</li>
<li>Gestión de Meta Business Suite</li>
</ul>
<a href="#contacto" class="plan-cta">+Info</a>
</div>
<div class="plan-card reco">
<div class="badge">Más Popular</div>
<div class="plan-name">Premium</div>
<div class="plan-stars">★★★</div>
<div class="plan-obj">Consolidar y expandir la empresa comercialmente.</div>
<ul class="plan-feats">
<li>3 redes · 16 publicaciones + 8 reels</li>
<li>Sesión de fotos/video quincenal</li>
<li>2 campañas Meta Ads + Google Ads</li>
<li>Respuestas con IA 24/7</li>
<li>Reporte semanal + reunión mensual</li>
<li>Soporte prioritario</li>
</ul>
<a href="#contacto" class="plan-cta">+Info</a>
</div>
<div class="plan-card">
<div class="plan-name">Elite</div>
<div class="plan-stars">★★★★</div>
<div class="plan-obj">Máximo posicionamiento y gestión integral de marca.</div>
<ul class="plan-feats">
<li>4 redes · 20 publicaciones + 16 reels</li>
<li>Dirección creativa integral de marca</li>
<li>3 campañas + TikTok Ads + Google Ads</li>
<li>Estrategia 360° con planificación mensual</li>
<li>Gestión de reputación online</li>
</ul>
<a href="#contacto" class="plan-cta">+Info</a>
</div>
</div>
<a href="#cotizador" class="btn btn-outline plan-main-cta">Consulta tu plan ideal</a>
</section>
<!-- ===== POTENCIADORES DE NEGOCIO ===== -->
<section class="servicios-carta" id="servicios-carta">
<div class="eyebrow">Potenciadores de negocio</div>
<h2>Para complementar cualquier <span class="grad-word">plan,</span><br>o contratar de forma <span class="grad-word">independiente.</span></h2>
<p class="lede">Elegí los servicios que necesitás, sin compromiso mensual. Todo lo que tu marca necesita, a tu ritmo.</p>
<div class="acc" id="acc">
<div class="acc-item open">
<div class="acc-head" onclick="toggleAcc(this)">
<div class="acc-head-left"><span class="acc-num">01</span><span class="acc-name">Diseño Web & Desarrollo</span></div>
<div class="acc-toggle">+</div>
</div>
<div class="acc-body">
<div class="acc-body-inner">
<div class="service-row"><b>Landing Page Profesional</b>Diseño de una sección, UI/UX + SEO básico <span class="price">Desde $350.000</span></div>
<div class="service-row"><b>Sitio Institucional (hasta 7 secciones)</b>Inicio, Servicios, Nosotros, Blog, Contacto <span class="price">Desde $600.000</span></div>
<div class="service-row"><b>E-commerce</b>Tienda online autoadministrable con pasarela de pago <span class="price">Desde $900.000</span></div>
<div class="service-row"><b>Mantenimiento Web</b>Backups, seguridad y soporte técnico <span class="price">Desde $50.000/mes</span></div>
</div>
</div>
</div>
<div class="acc-item">
<div class="acc-head" onclick="toggleAcc(this)">
<div class="acc-head-left"><span class="acc-num">02</span><span class="acc-name">Branding e Identidad Visual</span></div>
<div class="acc-toggle">+</div>
</div>
<div class="acc-body">
<div class="acc-body-inner">
<div class="service-row"><b>Diseño de Logotipo</b>3 propuestas + revisiones <span class="price">Desde $180.000</span></div>
<div class="service-row"><b>Manual de Marca Completo</b>Logo, paleta, tipografías, tono de voz <span class="price">Desde $300.000</span></div>
<div class="service-row"><b>Rediseño de Identidad Visual</b>Actualización de marca existente <span class="price">A cotizar</span></div>
</div>
</div>
</div>
<div class="acc-item">
<div class="acc-head" onclick="toggleAcc(this)">
<div class="acc-head-left"><span class="acc-num">03</span><span class="acc-name">Publicidad Digital Avanzada</span></div>
<div class="acc-toggle">+</div>
</div>
<div class="acc-body">
<div class="acc-body-inner">
<div class="service-row"><b>Campaña Google Ads</b>Búsqueda y display <span class="price">Desde $150.000/mes</span></div>
<div class="service-row"><b>Campaña TikTok Ads</b>Alcance a audiencias jóvenes <span class="price">Desde $120.000/mes</span></div>
<div class="service-row"><b>Auditoría de Campañas</b>Análisis y oportunidades de mejora <span class="price">Desde $90.000</span></div>
</div>
</div>
</div>
<div class="acc-item">
<div class="acc-head" onclick="toggleAcc(this)">
<div class="acc-head-left"><span class="acc-num">04</span><span class="acc-name">Diseño Digital & Gráfico</span></div>
<div class="acc-toggle">+</div>
</div>
<div class="acc-body">
<div class="acc-body-inner">
<div class="service-row"><b>Infografías</b>Comunicación visual de datos y procesos <span class="price">Desde $80.000/u</span></div>
<div class="service-row"><b>Plantillas para Redes</b>Set editable de 5 piezas <span class="price">Desde $100.000</span></div>
<div class="service-row"><b>Material Impreso</b>Flyers, folletos, tarjetas <span class="price">A cotizar</span></div>
</div>
</div>
</div>
<div class="acc-item">
<div class="acc-head" onclick="toggleAcc(this)">
<div class="acc-head-left"><span class="acc-num">05</span><span class="acc-name">Producción Audiovisual</span></div>
<div class="acc-toggle">+</div>
</div>
<div class="acc-body">
<div class="acc-body-inner">
<div class="service-row"><b>Sesión Fotográfica</b>Producto, instalaciones o equipo <span class="price">A cotizar</span></div>
<div class="service-row"><b>Reel / Video Corto</b>Hasta 30 segundos, con edición <span class="price">Desde $120.000</span></div>
<div class="service-row"><b>Pack de 3 Reels</b>Contenido consistente de alto impacto <span class="price">Desde $300.000</span></div>
</div>
</div>
</div>
</div>
</section>
<!-- ===== PROCESO ===== -->
<section class="proceso" id="proceso">
<div class="eyebrow">Cómo trabajamos</div>
<h2>Tu proyecto, paso a paso, y sin <span class="grad-word">sorpresas.</span></h2>
<p class="lede">Un proceso claro y colaborativo — sabés exactamente qué pasa en cada etapa, sin plantillas genéricas.</p>
<div class="arcade-grid">
<div class="column">
<div class="arch"><span class="num">01</span></div>
<div class="cat">Contacto</div>
<div class="step-title">Reunión de brief</div>
<div class="step-desc">Nos contás tu marca y objetivos.</div>
</div>
<div class="column">
<div class="arch"><span class="num">02</span></div>
<div class="cat">Propuesta</div>
<div class="step-title">Plan de trabajo</div>
<div class="step-desc">Entregables, inversión y tiempos.</div>
</div>
<div class="column">
<div class="arch"><span class="num">03</span></div>
<div class="cat">Diseño</div>
<div class="step-title">Dirección de arte</div>
<div class="step-desc">Concepto visual a tu aprobación.</div>
</div>
<div class="column">
<div class="arch"><span class="num">04</span></div>
<div class="cat">Producción</div>
<div class="step-title">Desarrollo</div>
<div class="step-desc">Construimos con seguimiento.</div>
</div>
<div class="column">
<div class="arch"><span class="num">05</span></div>
<div class="cat">Revisión</div>
<div class="step-title">Ajustes finales</div>
<div class="step-desc">Tu feedback moldea el resultado.</div>
</div>
<div class="column">
<div class="arch final"><svg viewBox="0 0 24 24" stroke="currentColor" fill="none" stroke-width="2.4"><path d="M5 12l5 5L19 7"/></svg></div>
<div class="cat">Lanzamiento</div>
<div class="step-title">Entrega</div>
<div class="step-desc">Accesos y capacitación completa.</div>
</div>
</div>
</section>
<!-- ===== CIFRAS ===== -->
<section class="cifras" id="cifras">
<div class="eyebrow">Inversión & tiempos</div>
<h2>Transparencia antes de la <span class="grad-word">primera reunión.</span></h2>
<p class="lede">Los números, dichos de entrada — no como parte de una negociación, sino como punto de partida.</p>
<div class="cifras-grid">
<div class="cifra-card">
<div class="cifra-icon"></div>
<div class="cifra-label">Inversión</div>
<div class="cifra-value">Desde $250.000/mes</div>
<div class="cifra-desc">Planes desde <b>$250.000</b> (Esencial) hasta <b>$1.000.000</b> (Elite). El armado inicial —branding, sitio web— se presupuesta por proyecto.</div>
</div>
<div class="cifra-card">
<div class="cifra-icon"></div>
<div class="cifra-label">Tiempos</div>
<div class="cifra-value">15–30 días</div>
<div class="cifra-desc">Presencia digital lista en <b>15-30 días</b>. Resultados de posicionamiento sostenido en <b>3-6 meses</b>. Sin promesas de magia inmediata.</div>
</div>
<div class="cifra-card">
<div class="cifra-icon"></div>
<div class="cifra-label">Contrato</div>
<div class="cifra-value">3 meses · luego mensual</div>
<div class="cifra-desc">Compromiso mínimo de <b>3 meses</b> para que la estrategia tome forma, luego renovación mensual. Cancelación <b>con 30 días de aviso</b>.</div>
</div>
</div>
</section>
<!-- ===== COTIZADOR ===== -->
<section class="cotizador" id="cotizador">
<div class="eyebrow">Cotizador</div>
<h2>¿Cuál es tu <span class="grad-word">plan ideal</span><span class="signopreg">?</span></h2>
<p class="lede">3 preguntas rápidas y te decimos qué plan se ajusta mejor a tu marca.</p>
<div class="card">
<div class="progress">
<div class="seg"><i id="p1"></i></div>
<div class="seg"><i id="p2"></i></div>
<div class="seg"><i id="p3"></i></div>
</div>
<div class="step active" data-step="0">
<div class="q-num">Pregunta 01</div>
<div class="q-title">¿Cómo describirías el momento de tu negocio?</div>
<div class="options" data-q="0">
<div class="opt" data-val="1"><div class="opt-title">Recién empezando</div><div class="opt-sub">Necesito presencia digital desde cero</div></div>
<div class="opt" data-val="2"><div class="opt-title">En crecimiento</div><div class="opt-sub">Ya tengo redes, quiero más alcance</div></div>
<div class="opt" data-val="3"><div class="opt-title">Establecido</div><div class="opt-sub">Busco consolidar y vender más</div></div>
<div class="opt" data-val="4"><div class="opt-title">Consolidado</div><div class="opt-sub">Quiero gestión integral de marca</div></div>
</div>
<div class="nav-row"><span></span><button class="btn btn-cotizador" onclick="next()" disabled id="next0">Siguiente →</button></div>
</div>
<div class="step" data-step="1">
<div class="q-num">Pregunta 02</div>
<div class="q-title">¿Qué es lo que más necesitás hoy?</div>
<div class="options" data-q="1">
<div class="opt" data-val="1"><div class="opt-title">Presencia en redes</div><div class="opt-sub">Contenido consistente y profesional</div></div>
<div class="opt" data-val="2"><div class="opt-title">Más leads y ventas</div><div class="opt-sub">Publicidad digital que convierta</div></div>
<div class="opt" data-val="3"><div class="opt-title">Producción de contenido</div><div class="opt-sub">Fotos, video y piezas de calidad</div></div>
<div class="opt" data-val="4"><div class="opt-title">Todo integrado</div><div class="opt-sub">Estrategia 360° gestionada por otros</div></div>
</div>
<div class="nav-row"><button class="btn btn-cotizador-back" onclick="prev()">← Atrás</button><button class="btn btn-cotizador" onclick="next()" disabled id="next1">Siguiente →</button></div>
</div>
<div class="step" data-step="2">
<div class="q-num">Pregunta 03</div>
<div class="q-title">¿Cuál es tu presupuesto mensual aproximado?</div>
<div class="options" data-q="2">
<div class="opt" data-val="1"><div class="opt-title">Hasta $300.000</div><div class="opt-sub">ARS / mes</div></div>
<div class="opt" data-val="2"><div class="opt-title">$300.000 – $450.000</div><div class="opt-sub">ARS / mes</div></div>
<div class="opt" data-val="3"><div class="opt-title">$450.000 – $700.000</div><div class="opt-sub">ARS / mes</div></div>
<div class="opt" data-val="4"><div class="opt-title">Más de $700.000</div><div class="opt-sub">ARS / mes</div></div>
</div>
<div class="nav-row"><button class="btn btn-cotizador-back" onclick="prev()">← Atrás</button><button class="btn btn-cotizador" onclick="showResult()" disabled id="next2">Ver resultado →</button></div>
</div>
<div class="result" id="result">
<div class="result-badge">Tu plan recomendado</div>
<div class="result-plan" id="rp-name">—</div>
<div class="result-price" id="rp-price">—</div>
<p class="result-desc" id="rp-desc">—</p>
<div class="result-actions">
<a class="btn btn-solid" href="#contacto">Quiero este plan</a>
<button class="btn btn-cotizador-restart" onclick="restart()">Volver a empezar</button>
</div>
</div>
</div>
</section>
<!-- ===== NOSOTROS ===== -->
<section class="quienes" id="nosotros">
<div class="eyebrow">Nosotros</div>
<h2>Mentes creativas, con <span class="grad-word">mucha energía.</span></h2>
<p class="lede"> Combinamos el arte del Marketing con la Ciencia de los datos.</p>
<div class="team-grid team-grid-simple">
<div class="team-card-simple">
<div class="team-name">Patricia Pugliese</div>
<div class="team-role">Estrategia & Creatividad</div>
<div class="team-detail">Investigación, branding, identidad visual y todo lo que da forma a una marca con personalidad.</div>
</div>
<div class="team-card-simple">
<div class="team-name">Francisco Anfuso</div>
<div class="team-role">Desarrollo & Tecnología</div>
<div class="team-detail">Diseño web, desarrollo, automatizaciones y soluciones técnicas que funcionan sin complicaciones.</div>
</div>
</div>
<div class="team-footer">
<p class="team-footer-text">Como todo equipo en crecimiento, sumamos colaboradores según el proyecto — diseñadores, redactores y especialistas que se suman cuando hace falta.</p>
</div>
</section>
<!-- ===== FAQ ===== -->
<section class="faq" id="faq">
<div class="eyebrow">Preguntas Frecuentes</div>
<h2>Todo lo que necesitás saber <span class="grad-word">antes de empezar.</span></h2>
<p class="lede">Respondemos las dudas más comunes para que llegues con confianza al primer encuentro.</p>
<div class="faq-grid">
<div class="faq-item open">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Cómo funciona el proceso de trabajo?</em></span>
<span class="faq-toggle">−</span>
</div>
<div class="faq-body"><p>Empezamos con una llamada de descubrimiento para conocer tu negocio, objetivos y desafíos. Luego armamos una propuesta a medida, la ejecutamos con entregas parciales y ajustamos hasta que estés 100% conforme. Todo con comunicación clara y tiempos acordados.</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Qué incluye exactamente cada plan?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>Cada plan tiene un desglose detallado en la sección de Planes. Pero en resumen: incluyen gestión de redes, diseño de marca, publicidad digital, automatizaciones y reportes. Si necesitás algo específico que no esté listado, lo sumamos a medida.</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Puedo contratar servicios sueltos sin un plan mensual?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>¡Sí! En la sección "Servicios a la carta" tenés disponibles branding, diseño web, campañas puntuales y producción de contenido. Podés contratarlos de forma independiente, sin compromiso mensual.</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Qué resultados puedo esperar?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>Depende del punto de partida, pero nuestros clientes suelen ver aumento en alcance, engagement y generación de leads en los primeros 3 meses. Compartimos reportes mensuales para que siempre sepas cómo evoluciona tu marca.</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Trabajan con negocios de cualquier rubro?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>Trabajamos con marcas de moda, gastronomía, tecnología, salud, educación y más. Lo importante es que tengas claros tus valores y quieras construir una marca con identidad propia — el rubro es secundario.</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Cómo facturan? ¿Hay algún costo de inicio?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>Facturamos con factura electrónica tipo C o E. No hay costo de inicio: los planes se abonan mes a mes, con un 50% de anticipo en proyectos puntuales (como diseño web o branding completo).</p></div>
</div>
<div class="faq-item">
<div class="faq-head" onclick="toggleFaq(this)">
<span class="faq-q"> <em>¿Puedo cambiar de plan o cancelar cuando quiera?</em></span>
<span class="faq-toggle">+</span>
</div>
<div class="faq-body"><p>Por supuesto. Podés subir o bajar de plan con 15 días de aviso. Si querés cancelar, también con 15 días de anticipación. Sin letra chica ni permanencias forzadas.</p></div>
</div>
</div>
</section>
<!-- ===== CONTACTO ===== -->
<section class="contacto" id="contacto">
<div class="eyebrow">Contacto</div>
<h2>¿Empezamos a <span class="grad-word">construir</span> tu marca?</h2>
<p class="lede">Completá el formulario o escribinos directo — te respondemos en menos de 24 horas.</p>
<div class="contact-grid">
<div class="contact-form-wrap">
<form class="contact-form" id="contactForm" onsubmit="return handleSubmit(event)">
<div class="form-row">
<div class="form-group">
<label for="nombre">Nombre completo <span class="req">*</span></label>
<input type="text" id="nombre" name="nombre" required placeholder="Tu nombre">
</div>
<div class="form-group">
<label for="email">Email <span class="req">*</span></label>
<input type="email" id="email" name="email" required placeholder="tu@email.com">
</div>
</div>
<div class="form-row">
<div class="form-group">
<label for="empresa">Empresa / Emprendimiento</label>
<input type="text" id="empresa" name="empresa" placeholder="Nombre de tu marca">
</div>
<div class="form-group">
<label for="telefono">Teléfono</label>
<input type="tel" id="telefono" name="telefono" placeholder="+54 9 388 000-0000">
</div>
</div>
<div class="form-group full">
<label for="servicio">¿Qué servicio te interesa? <span class="req">*</span></label>
<div class="filter-tags" id="servicioFilter">
<button type="button" class="filter-tag active" data-value="todos" onclick="selectFilter(event)">Todos</button>
<button type="button" class="filter-tag" data-value="branding" onclick="selectFilter(event)">Branding</button>
<button type="button" class="filter-tag" data-value="web" onclick="selectFilter(event)">Diseño Web</button>
<button type="button" class="filter-tag" data-value="marketing" onclick="selectFilter(event)">Marketing Digital</button>
<button type="button" class="filter-tag" data-value="ia" onclick="selectFilter(event)">IA & Automatización</button>
<button type="button" class="filter-tag" data-value="otro" onclick="selectFilter(event)">Otro</button>
</div>
<input type="hidden" id="servicioSeleccionado" name="servicio" value="todos">
<input type="text" id="servicioOtro" name="servicio_otro" placeholder="Especificá cuál..." style="display:none; margin-top:10px; width:100%;">
</div>
<div class="form-group full">
<label for="mensaje">¿Qué necesitás? <span class="req">*</span></label>
<textarea id="mensaje" name="mensaje" required placeholder="Contanos sobre tu proyecto, tus objetivos y lo que estás buscando..." rows="5"></textarea>
</div>
<div class="form-row">
<div class="form-group" style="flex:1;">
<label class="checkbox-label">
<input type="checkbox" required>
<span>Acepto la <a href="#" style="color:var(--bordo);">política de privacidad</a></span>
</label>
</div>
<button type="submit" class="btn btn-solid" style="padding:14px 44px;">Enviar mensaje</button>
</div>
</form>
</div>
<div class="contact-direct">
<div class="contact-card">
<div class="contact-icon">📧</div>
<div class="contact-info">
<div class="contact-label">Email</div>
<a href="mailto:contacto@amoryroma.com.ar">contacto@amoryroma.com.ar</a>
</div>
</div>
<div class="contact-card">
<div class="contact-icon">💬</div>
<div class="contact-info">
<div class="contact-label">WhatsApp</div>
<a href="https://wa.me/5493886118304" target="_blank">+54 9 388 611-8304</a>
</div>
</div>
<div class="contact-card">
<div class="contact-icon">📱</div>
<div class="contact-info">
<div class="contact-label">Redes</div>
<div class="contact-socials">
<a href="https://www.instagram.com/amoryroma.creativo/" target="_blank">Instagram</a>
<a href="https://www.linkedin.com/in/patricia-pugliese/" target="_blank">LinkedIn</a>
<a href="https://web.facebook.com/amoryroma.creativo" target="_blank">Facebook</a>
</div>
</div>
</div>
<div class="contact-card">
<div class="contact-icon">📍</div>
<div class="contact-info">
<div class="contact-label">Argentina</div>
<span style="font-size:13px; color:var(--dusty);">Trabajamos remoto worldwide</span>
</div>
</div>
</div>
</div>
</section>
<!-- ===== FOOTER ===== -->
<div id="footer-placeholder"></div>
<!-- ===== SCRIPTS ===== -->
<script src="scripts/main.js"></script>
<script src="fluid.js"></script>
<script src="scripts/loader.js" defer></script>
</body>
</html>
+62
View File
@@ -0,0 +1,62 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Inicio - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<!-- Sección 1 -->
<section id="inicio-section-1">
<h2>Sección 1</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 2 -->
<section id="inicio-section-2">
<h2>Sección 2</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 3 -->
<section id="inicio-section-3">
<h2>Sección 3</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 4 -->
<section id="inicio-section-4">
<h2>Sección 4</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 5 -->
<section id="inicio-section-5">
<h2>Sección 5</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 6 -->
<section id="inicio-section-6">
<h2>Sección 6</h2>
<p>Contenido pendiente de definir.</p>
</section>
<!-- Sección 7 -->
<section id="inicio-section-7">
<h2>Sección 7</h2>
<p>Contenido pendiente de definir.</p>
</section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
+24
View File
@@ -0,0 +1,24 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Nosotros - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<section id="nosotros-section-1"><h2>Sección 1</h2><p>Contenido pendiente de definir.</p></section>
<section id="nosotros-section-2"><h2>Sección 2</h2><p>Contenido pendiente de definir.</p></section>
<section id="nosotros-section-3"><h2>Sección 3</h2><p>Contenido pendiente de definir.</p></section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
-43
View File
@@ -1,43 +0,0 @@
<footer class="footer">
<div class="footer-inner">
<div class="footer-brand">
<div class="footer-logo">
<img src="./assets/logos/logo_frio.png" alt="Amor & Roma" style="height:36px;width:auto;">
</div>
<p class="footer-desc">Branding, diseño web y marketing digital para marcas con esencia.</p>
</div>
<div class="footer-links">
<div class="footer-col">
<h4>Navegación</h4>
<a href="#servicios">Servicios</a>
<a href="#planes">Planes</a>
<a href="#cifras">Cifras</a>
<a href="#faq">FAQ</a>
</div>
<div class="footer-col">
<h4>Servicios</h4>
<a href="#servicios">Branding</a>
<a href="#servicios">Diseño Web</a>
<a href="#servicios">Marketing Digital</a>
<a href="#servicios">IA & Automatización</a>
</div>
<div class="footer-col">
<h4>Contacto</h4>
<a href="mailto:contacto@amoryroma.com.ar">contacto@amoryroma.com.ar</a>
<a href="https://wa.me/5493886118304" target="_blank">+54 9 388 611-8304</a>
<div class="footer-socials">
<a href="https://www.instagram.com/amoryroma.creativo/" target="_blank" aria-label="Instagram">IG</a>
<a href="https://www.linkedin.com/in/patricia-pugliese/" target="_blank" aria-label="LinkedIn">IN</a>
<a href="https://web.facebook.com/amoryroma.creativo" target="_blank" aria-label="Facebook">FB</a>
</div>
</div>
</div>
</div>
<div class="footer-bottom">
<span>&copy; 2026 Amor & Roma — Estudio Creativo. Todos los derechos reservados.</span>
<span class="footer-legal">
<a href="#">Política de privacidad</a>
<a href="#">Términos y condiciones</a>
</span>
</div>
</footer>
-71
View File
@@ -1,71 +0,0 @@
<!-- ===== OVERLAY ===== -->
<div class="overlay" id="overlay" onclick="toggleMenu()"></div>
<!-- ===== MENU BOTTOM SHEET ===== -->
<nav class="sheet" id="sheet" aria-label="Menú principal">
<div class="sheet-handle"></div>
<div class="sheet-top">
<div class="logo">
<a href="index.html">
<img src="./assets/logos/logo_ciruela.png" alt="Amor & Roma" class="logo-img">
</a>
</div>
<button class="close-btn" onclick="toggleMenu()" aria-label="Cerrar menú">✕</button>
</div>
<div class="sheet-body">
<div class="sheet-col">
<div class="sheet-col-title">Soluciones Web</div>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Diseño Web</span>
<span class="sheet-link-desc">Sitios informativos modernos</span>
</a>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">E-commerce</span>
<span class="sheet-link-desc">Tiendas online con todas las funcionalidades</span>
</a>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Google Ads</span>
<span class="sheet-link-desc">Publicidad en Search y Display</span>
</a>
</div>
<div class="sheet-col">
<div class="sheet-col-title">Redes Sociales</div>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Community Manager</span>
<span class="sheet-link-desc">Administración profesional de redes</span>
</a>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Creación de Contenido</span>
<span class="sheet-link-desc">Contenido original y atractivo</span>
</a>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Meta Ads</span>
<span class="sheet-link-desc">Publicidad en Facebook e Instagram</span>
</a>
</div>
<div class="sheet-col">
<div class="sheet-col-title">Branding</div>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Diseño de Logos</span>
<span class="sheet-link-desc">Personalizados y profesionales</span>
</a>
<a href="#servicios" onclick="toggleMenu()" class="sheet-link">
<span class="sheet-link-icon">⊞</span>
<span class="sheet-link-main">Identidad de Marca</span>
<span class="sheet-link-desc">Creación y desarrollo de marca</span>
</a>
<a href="#contacto" onclick="toggleMenu()" class="sheet-link highlight">
<span class="sheet-link-icon">✉</span>
<span class="sheet-link-main">Contacto</span>
<span class="sheet-link-desc">Empezá tu proyecto</span>
</a>
</div>
</div>
</nav>
+28
View File
@@ -0,0 +1,28 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Planes - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<section id="planes-section-1"><h2>Sección 1</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-2"><h2>Sección 2</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-3"><h2>Sección 3</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-4"><h2>Sección 4</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-5"><h2>Sección 5</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-6"><h2>Sección 6</h2><p>Contenido pendiente de definir.</p></section>
<section id="planes-section-7"><h2>Sección 7</h2><p>Contenido pendiente de definir.</p></section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
+26
View File
@@ -0,0 +1,26 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Portfolio - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<section id="portfolio-section-1"><h2>Sección 1</h2><p>Contenido pendiente de definir.</p></section>
<section id="portfolio-section-2"><h2>Sección 2</h2><p>Contenido pendiente de definir.</p></section>
<section id="portfolio-section-3"><h2>Sección 3</h2><p>Contenido pendiente de definir.</p></section>
<section id="portfolio-section-4"><h2>Sección 4</h2><p>Contenido pendiente de definir.</p></section>
<section id="portfolio-section-5"><h2>Sección 5</h2><p>Contenido pendiente de definir.</p></section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
View File
+582
View File
@@ -0,0 +1,582 @@
"use strict";
// ===== CONFIGURACIÓN DEL EFECTO =====
const config = {
TEXTURE_DOWNSAMPLE: 1,
DENSITY_DISSIPATION: 0.975,
VELOCITY_DISSIPATION: 0.98,
PRESSURE_DISSIPATION: 0.8,
PRESSURE_ITERATIONS: 20,
CURL: 30,
SPLAT_RADIUS: 0.003
};
// ===== INICIALIZAR CANVAS =====
let canvas = document.getElementById("fluidCanvas");
console.log("Canvas encontrado:", canvas);
if (!canvas) {
console.error("ERROR: No se encontró el canvas con id 'fluidCanvas'");
}
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
// ===== CONTEXTO WEBGL =====
let pointers = [];
let splatStack = [];
function getWebGLContext(canvas) {
let params = {
alpha: false,
depth: false,
stencil: false,
antialias: false
};
let gl = canvas.getContext("webgl2", params);
let isWebGL2 = !!gl;
if (!isWebGL2)
gl =
canvas.getContext("webgl", params) ||
canvas.getContext("experimental-webgl", params);
let halfFloat = gl.getExtension("OES_texture_half_float");
let support_linear_float = gl.getExtension("OES_texture_half_float_linear");
if (isWebGL2) {
gl.getExtension("EXT_color_buffer_float");
support_linear_float = gl.getExtension("OES_texture_float_linear");
}
gl.clearColor(0.0, 0.0, 0.0, 1.0);
let internalFormat = isWebGL2 ? gl.RGBA16F : gl.RGBA;
let internalFormatRG = isWebGL2 ? gl.RG16F : gl.RGBA;
let formatRG = isWebGL2 ? gl.RG : gl.RGBA;
let texType = isWebGL2 ? gl.HALF_FLOAT : halfFloat.HALF_FLOAT_OES;
return {
gl: gl,
ext: {
internalFormat: internalFormat,
internalFormatRG: internalFormatRG,
formatRG: formatRG,
texType: texType
},
support_linear_float: support_linear_float
};
}
let _getWebGLContext = getWebGLContext(canvas);
let gl = _getWebGLContext.gl;
let ext = _getWebGLContext.ext;
let support_linear_float = _getWebGLContext.support_linear_float;
// ===== POINTER =====
function pointerPrototype() {
this.id = -1;
this.x = 0;
this.y = 0;
this.dx = 0;
this.dy = 0;
this.down = false;
this.moved = false;
this.color = [30, 0, 300];
}
pointers.push(new pointerPrototype());
// ===== SHADERS =====
let GLProgram = (function () {
function GLProgram(vertexShader, fragmentShader) {
if (!(this instanceof GLProgram))
throw new TypeError("Cannot call a class as a function");
this.uniforms = {};
this.program = gl.createProgram();
gl.attachShader(this.program, vertexShader);
gl.attachShader(this.program, fragmentShader);
gl.linkProgram(this.program);
if (!gl.getProgramParameter(this.program, gl.LINK_STATUS))
throw gl.getProgramInfoLog(this.program);
let uniformCount = gl.getProgramParameter(this.program, gl.ACTIVE_UNIFORMS);
for (let i = 0; i < uniformCount; i++) {
let uniformName = gl.getActiveUniform(this.program, i).name;
this.uniforms[uniformName] = gl.getUniformLocation(
this.program,
uniformName
);
}
}
GLProgram.prototype.bind = function bind() {
gl.useProgram(this.program);
};
return GLProgram;
})();
function compileShader(type, source) {
let shader = gl.createShader(type);
gl.shaderSource(shader, source);
gl.compileShader(shader);
if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS))
throw gl.getShaderInfoLog(shader);
return shader;
}
// ===== VERTEX SHADER =====
let baseVertexShader = compileShader(
gl.VERTEX_SHADER,
"precision highp float; precision mediump sampler2D; attribute vec2 aPosition; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform vec2 texelSize; void main () { vUv = aPosition * 0.5 + 0.5; vL = vUv - vec2(texelSize.x, 0.0); vR = vUv + vec2(texelSize.x, 0.0); vT = vUv + vec2(0.0, texelSize.y); vB = vUv - vec2(0.0, texelSize.y); gl_Position = vec4(aPosition, 0.0, 1.0); }"
);
// ===== FRAGMENT SHADERS =====
let clearShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; uniform sampler2D uTexture; uniform float value; void main () { gl_FragColor = value * texture2D(uTexture, vUv); }"
);
let displayShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; uniform sampler2D uTexture; void main () { gl_FragColor = texture2D(uTexture, vUv); }"
);
let splatShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; uniform sampler2D uTarget; uniform float aspectRatio; uniform vec3 color; uniform vec2 point; uniform float radius; void main () { vec2 p = vUv - point.xy; p.x *= aspectRatio; vec3 splat = exp(-dot(p, p) / radius) * color; vec3 base = texture2D(uTarget, vUv).xyz; gl_FragColor = vec4(base + splat, 1.0); }"
);
let advectionManualFilteringShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; uniform sampler2D uVelocity; uniform sampler2D uSource; uniform vec2 texelSize; uniform float dt; uniform float dissipation; vec4 bilerp (in sampler2D sam, in vec2 p) { vec4 st; st.xy = floor(p - 0.5) + 0.5; st.zw = st.xy + 1.0; vec4 uv = st * texelSize.xyxy; vec4 a = texture2D(sam, uv.xy); vec4 b = texture2D(sam, uv.zy); vec4 c = texture2D(sam, uv.xw); vec4 d = texture2D(sam, uv.zw); vec2 f = p - st.xy; return mix(mix(a, b, f.x), mix(c, d, f.x), f.y); } void main () { vec2 coord = gl_FragCoord.xy - dt * texture2D(uVelocity, vUv).xy; gl_FragColor = dissipation * bilerp(uSource, coord); gl_FragColor.a = 1.0; }"
);
let advectionShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; uniform sampler2D uVelocity; uniform sampler2D uSource; uniform vec2 texelSize; uniform float dt; uniform float dissipation; void main () { vec2 coord = vUv - dt * texture2D(uVelocity, vUv).xy * texelSize; gl_FragColor = dissipation * texture2D(uSource, coord); }"
);
let divergenceShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform sampler2D uVelocity; vec2 sampleVelocity (in vec2 uv) { vec2 multiplier = vec2(1.0, 1.0); if (uv.x < 0.0) { uv.x = 0.0; multiplier.x = -1.0; } if (uv.x > 1.0) { uv.x = 1.0; multiplier.x = -1.0; } if (uv.y < 0.0) { uv.y = 0.0; multiplier.y = -1.0; } if (uv.y > 1.0) { uv.y = 1.0; multiplier.y = -1.0; } return multiplier * texture2D(uVelocity, uv).xy; } void main () { float L = sampleVelocity(vL).x; float R = sampleVelocity(vR).x; float T = sampleVelocity(vT).y; float B = sampleVelocity(vB).y; float div = 0.5 * (R - L + T - B); gl_FragColor = vec4(div, 0.0, 0.0, 1.0); }"
);
let curlShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform sampler2D uVelocity; void main () { float L = texture2D(uVelocity, vL).y; float R = texture2D(uVelocity, vR).y; float T = texture2D(uVelocity, vT).x; float B = texture2D(uVelocity, vB).x; float vorticity = R - L - T + B; gl_FragColor = vec4(vorticity, 0.0, 0.0, 1.0); }"
);
let vorticityShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform sampler2D uVelocity; uniform sampler2D uCurl; uniform float curl; uniform float dt; void main () { float L = texture2D(uCurl, vL).y; float R = texture2D(uCurl, vR).y; float T = texture2D(uCurl, vT).x; float B = texture2D(uCurl, vB).x; float C = texture2D(uCurl, vUv).x; vec2 force = vec2(abs(T) - abs(B), abs(R) - abs(L)); force *= 1.0 / length(force + 0.00001) * curl * C; vec2 vel = texture2D(uVelocity, vUv).xy; gl_FragColor = vec4(vel + force * dt, 0.0, 1.0); }"
);
let pressureShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform sampler2D uPressure; uniform sampler2D uDivergence; vec2 boundary (in vec2 uv) { uv = min(max(uv, 0.0), 1.0); return uv; } void main () { float L = texture2D(uPressure, boundary(vL)).x; float R = texture2D(uPressure, boundary(vR)).x; float T = texture2D(uPressure, boundary(vT)).x; float B = texture2D(uPressure, boundary(vB)).x; float C = texture2D(uPressure, vUv).x; float divergence = texture2D(uDivergence, vUv).x; float pressure = (L + R + B + T - divergence) * 0.25; gl_FragColor = vec4(pressure, 0.0, 0.0, 1.0); }"
);
let gradientSubtractShader = compileShader(
gl.FRAGMENT_SHADER,
"precision highp float; precision mediump sampler2D; varying vec2 vUv; varying vec2 vL; varying vec2 vR; varying vec2 vT; varying vec2 vB; uniform sampler2D uPressure; uniform sampler2D uVelocity; vec2 boundary (in vec2 uv) { uv = min(max(uv, 0.0), 1.0); return uv; } void main () { float L = texture2D(uPressure, boundary(vL)).x; float R = texture2D(uPressure, boundary(vR)).x; float T = texture2D(uPressure, boundary(vT)).x; float B = texture2D(uPressure, boundary(vB)).x; vec2 velocity = texture2D(uVelocity, vUv).xy; velocity.xy -= vec2(R - L, T - B); gl_FragColor = vec4(velocity, 0.0, 1.0); }"
);
// ===== FRAMEBUFFERS =====
let textureWidth, textureHeight;
let density, velocity, divergence, curl, pressure;
function initFramebuffers() {
textureWidth = gl.drawingBufferWidth >> config.TEXTURE_DOWNSAMPLE;
textureHeight = gl.drawingBufferHeight >> config.TEXTURE_DOWNSAMPLE;
let iFormat = ext.internalFormat;
let iFormatRG = ext.internalFormatRG;
let formatRG = ext.formatRG;
let texType = ext.texType;
density = createDoubleFBO(
0,
textureWidth,
textureHeight,
iFormat,
gl.RGBA,
texType,
support_linear_float ? gl.LINEAR : gl.NEAREST
);
velocity = createDoubleFBO(
2,
textureWidth,
textureHeight,
iFormatRG,
formatRG,
texType,
support_linear_float ? gl.LINEAR : gl.NEAREST
);
divergence = createFBO(
4,
textureWidth,
textureHeight,
iFormatRG,
formatRG,
texType,
gl.NEAREST
);
curl = createFBO(
5,
textureWidth,
textureHeight,
iFormatRG,
formatRG,
texType,
gl.NEAREST
);
pressure = createDoubleFBO(
6,
textureWidth,
textureHeight,
iFormatRG,
formatRG,
texType,
gl.NEAREST
);
}
function createFBO(texId, w, h, internalFormat, format, type, param) {
gl.activeTexture(gl.TEXTURE0 + texId);
let texture = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, texture);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, param);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, param);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.texImage2D(gl.TEXTURE_2D, 0, internalFormat, w, h, 0, format, type, null);
let fbo = gl.createFramebuffer();
gl.bindFramebuffer(gl.FRAMEBUFFER, fbo);
gl.framebufferTexture2D(
gl.FRAMEBUFFER,
gl.COLOR_ATTACHMENT0,
gl.TEXTURE_2D,
texture,
0
);
gl.viewport(0, 0, w, h);
gl.clear(gl.COLOR_BUFFER_BIT);
return [texture, fbo, texId];
}
function createDoubleFBO(texId, w, h, internalFormat, format, type, param) {
let fbo1 = createFBO(texId, w, h, internalFormat, format, type, param);
let fbo2 = createFBO(texId + 1, w, h, internalFormat, format, type, param);
return {
get first() {
return fbo1;
},
get second() {
return fbo2;
},
swap: function swap() {
let temp = fbo1;
fbo1 = fbo2;
fbo2 = temp;
}
};
}
initFramebuffers();
// ===== PROGRAMS =====
let clearProgram = new GLProgram(baseVertexShader, clearShader);
let displayProgram = new GLProgram(baseVertexShader, displayShader);
let splatProgram = new GLProgram(baseVertexShader, splatShader);
let advectionProgram = new GLProgram(
baseVertexShader,
support_linear_float ? advectionShader : advectionManualFilteringShader
);
let divergenceProgram = new GLProgram(baseVertexShader, divergenceShader);
let curlProgram = new GLProgram(baseVertexShader, curlShader);
let vorticityProgram = new GLProgram(baseVertexShader, vorticityShader);
let pressureProgram = new GLProgram(baseVertexShader, pressureShader);
let gradienSubtractProgram = new GLProgram(
baseVertexShader,
gradientSubtractShader
);
// ===== BLIT =====
let blit = (function () {
gl.bindBuffer(gl.ARRAY_BUFFER, gl.createBuffer());
gl.bufferData(
gl.ARRAY_BUFFER,
new Float32Array([-1, -1, -1, 1, 1, 1, 1, -1]),
gl.STATIC_DRAW
);
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, gl.createBuffer());
gl.bufferData(
gl.ELEMENT_ARRAY_BUFFER,
new Uint16Array([0, 1, 2, 0, 2, 3]),
gl.STATIC_DRAW
);
gl.vertexAttribPointer(0, 2, gl.FLOAT, false, 0, 0);
gl.enableVertexAttribArray(0);
return function (destination) {
gl.bindFramebuffer(gl.FRAMEBUFFER, destination);
gl.drawElements(gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0);
};
})();
// ===== SPLAT =====
function splat(x, y, dx, dy, color) {
splatProgram.bind();
gl.uniform1i(splatProgram.uniforms.uTarget, velocity.first[2]);
gl.uniform1f(splatProgram.uniforms.aspectRatio, canvas.width / canvas.height);
gl.uniform2f(
splatProgram.uniforms.point,
x / canvas.width,
1.0 - y / canvas.height
);
gl.uniform3f(splatProgram.uniforms.color, dx, -dy, 1.0);
gl.uniform1f(splatProgram.uniforms.radius, config.SPLAT_RADIUS);
blit(velocity.second[1]);
velocity.swap();
gl.uniform1i(splatProgram.uniforms.uTarget, density.first[2]);
gl.uniform3f(
splatProgram.uniforms.color,
color[0] * 0.3,
color[1] * 0.3,
color[2] * 0.3
);
blit(density.second[1]);
density.swap();
}
// ===== RESIZE =====
function resizeCanvas() {
(canvas.width !== canvas.clientWidth ||
canvas.height !== canvas.clientHeight) &&
((canvas.width = canvas.clientWidth),
(canvas.height = canvas.clientHeight),
initFramebuffers());
}
// ===== COLORES DE LA MARCA CON TRANSICIÓN =====
const brandColors = [
//[0.874, 0.741, 0.725], // Rosa (#DFBDB9)
[0.729, 0.071, 0.302], // Bordo (#BA124D)
[0.000, 0.247, 0.322] // Teal (#003F52)
];
let currentColor = brandColors[0];
let targetColor = brandColors[1];
let transitionProgress = 0;
const transitionSpeed = 0.008;
function lerpColor(colorA, colorB, t) {
return [
colorA[0] + (colorB[0] - colorA[0]) * t,
colorA[1] + (colorB[1] - colorA[1]) * t,
colorA[2] + (colorB[2] - colorA[2]) * t
];
}
let colorArr = currentColor;
let count = 0;
// ===== DETECTAR ELEMENTOS DE TEXTO =====
function isMouseOverTextElement(target) {
// Listado de selectores que necesitan "modo apaciguado"
const textSelectors = [
'p', '.hero-content p','h1', 'h2', 'h3', 'h4', 'h5', '.hero-content h1',
'.hero-content h2', '.eyebrow', 'a.sheet-link', '.sheet-link span',
'.menu-btn', '.sheet-link-desc', '.sheet-link-main'
];
// Verificar si el target o sus ancestros coinciden con algún selector
for (const selector of textSelectors) {
if (target.closest(selector)) {
return true;
}
}
return false;
}
// ===== EVENTOS CON COLORES DE MARCA =====
document.addEventListener("mousemove", function (e) {
// Detectar si estamos sobre un elemento de texto
const overText = isMouseOverTextElement(e.target);
count++;
if (count > 1) {
transitionProgress += transitionSpeed;
if (transitionProgress >= 1) {
transitionProgress = 0;
let currentIndex = brandColors.indexOf(currentColor);
let nextIndex = (currentIndex + 1) % brandColors.length;
currentColor = targetColor;
targetColor = brandColors[nextIndex];
}
colorArr = lerpColor(currentColor, targetColor, transitionProgress);
count = 0;
}
pointers[0].down = true;
pointers[0].color = colorArr;
pointers[0].moved = pointers[0].down;
// Aplicar multiplicador diferente según si estamos sobre texto o no
const multiplier = overText ? 8 : 10.0; // Reducido a 4x sobre texto (vs 10x)
pointers[0].dx = (e.clientX - canvas.offsetLeft - pointers[0].x) * multiplier;
pointers[0].dy = (e.clientY - canvas.offsetTop - pointers[0].y) * multiplier;
pointers[0].x = e.clientX - canvas.offsetLeft;
pointers[0].y = e.clientY - canvas.offsetTop;
});
canvas.addEventListener(
"touchmove",
function (e) {
e.preventDefault();
let touches = e.targetTouches;
count++;
if (count > 20) {
transitionProgress += transitionSpeed;
if (transitionProgress >= 1) {
transitionProgress = 0;
let currentIndex = brandColors.indexOf(currentColor);
let nextIndex = (currentIndex + 1) % brandColors.length;
currentColor = targetColor;
targetColor = brandColors[nextIndex];
}
colorArr = lerpColor(currentColor, targetColor, transitionProgress);
count = 0;
}
for (let i = 0, len = touches.length; i < len; i++) {
if (i >= pointers.length) pointers.push(new pointerPrototype());
pointers[i].id = touches[i].identifier;
pointers[i].down = true;
pointers[i].x = touches[i].pageX;
pointers[i].y = touches[i].pageY;
pointers[i].color = colorArr;
let pointer = pointers[i];
pointer.moved = pointer.down;
pointer.dx = (touches[i].pageX - pointer.x) * 10.0;
pointer.dy = (touches[i].pageY - pointer.y) * 10.0;
pointer.x = touches[i].pageX;
pointer.y = touches[i].pageY;
}
},
false
);
// ===== LOOP PRINCIPAL =====
let lastTime = Date.now();
function update() {
resizeCanvas();
let dt = Math.min((Date.now() - lastTime) / 1000, 0.016);
lastTime = Date.now();
gl.viewport(0, 0, textureWidth, textureHeight);
advectionProgram.bind();
gl.uniform2f(
advectionProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(advectionProgram.uniforms.uVelocity, velocity.first[2]);
gl.uniform1i(advectionProgram.uniforms.uSource, velocity.first[2]);
gl.uniform1f(advectionProgram.uniforms.dt, dt);
gl.uniform1f(
advectionProgram.uniforms.dissipation,
config.VELOCITY_DISSIPATION
);
blit(velocity.second[1]);
velocity.swap();
gl.uniform1i(advectionProgram.uniforms.uVelocity, velocity.first[2]);
gl.uniform1i(advectionProgram.uniforms.uSource, density.first[2]);
gl.uniform1f(
advectionProgram.uniforms.dissipation,
config.DENSITY_DISSIPATION
);
blit(density.second[1]);
density.swap();
for (let i = 0, len = pointers.length; i < len; i++) {
let pointer = pointers[i];
if (pointer.moved) {
splat(pointer.x, pointer.y, pointer.dx, pointer.dy, pointer.color);
pointer.moved = false;
}
}
curlProgram.bind();
gl.uniform2f(
curlProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(curlProgram.uniforms.uVelocity, velocity.first[2]);
blit(curl[1]);
vorticityProgram.bind();
gl.uniform2f(
vorticityProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(vorticityProgram.uniforms.uVelocity, velocity.first[2]);
gl.uniform1i(vorticityProgram.uniforms.uCurl, curl[2]);
gl.uniform1f(vorticityProgram.uniforms.curl, config.CURL);
gl.uniform1f(vorticityProgram.uniforms.dt, dt);
blit(velocity.second[1]);
velocity.swap();
divergenceProgram.bind();
gl.uniform2f(
divergenceProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(divergenceProgram.uniforms.uVelocity, velocity.first[2]);
blit(divergence[1]);
clearProgram.bind();
let pressureTexId = pressure.first[2];
gl.activeTexture(gl.TEXTURE0 + pressureTexId);
gl.bindTexture(gl.TEXTURE_2D, pressure.first[0]);
gl.uniform1i(clearProgram.uniforms.uTexture, pressureTexId);
gl.uniform1f(clearProgram.uniforms.value, config.PRESSURE_DISSIPATION);
blit(pressure.second[1]);
pressure.swap();
pressureProgram.bind();
gl.uniform2f(
pressureProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(pressureProgram.uniforms.uDivergence, divergence[2]);
pressureTexId = pressure.first[2];
gl.activeTexture(gl.TEXTURE0 + pressureTexId);
for (let _i = 0; _i < config.PRESSURE_ITERATIONS; _i++) {
gl.bindTexture(gl.TEXTURE_2D, pressure.first[0]);
gl.uniform1i(pressureProgram.uniforms.uPressure, pressureTexId);
blit(pressure.second[1]);
pressure.swap();
}
gradienSubtractProgram.bind();
gl.uniform2f(
gradienSubtractProgram.uniforms.texelSize,
1.0 / textureWidth,
1.0 / textureHeight
);
gl.uniform1i(gradienSubtractProgram.uniforms.uPressure, pressure.first[2]);
gl.uniform1i(gradienSubtractProgram.uniforms.uVelocity, velocity.first[2]);
blit(velocity.second[1]);
velocity.swap();
gl.viewport(0, 0, gl.drawingBufferWidth, gl.drawingBufferHeight);
displayProgram.bind();
gl.uniform1i(displayProgram.uniforms.uTexture, density.first[2]);
blit(null);
requestAnimationFrame(update);
}
update();
// ===== REDIMENSIONAR AL CAMBIAR TAMAÑO DE VENTANA =====
window.addEventListener("resize", function() {
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
initFramebuffers();
});
+108 -136
View File
@@ -1,150 +1,122 @@
// ===== MENU ===== /* ============================================
function toggleMenu() { CARGA DE INCLUDES (menu y footer)
document.getElementById('sheet').classList.toggle('open'); ============================================ */
document.getElementById('overlay').classList.toggle('open'); async function loadInclude(selector, url) {
try {
const response = await fetch(url);
if (!response.ok) throw new Error(`HTTP ${response.status}`);
const html = await response.text();
const container = document.querySelector(selector);
if (container) container.innerHTML = html;
} catch (error) {
console.error(`Error cargando ${url}:`, error);
}
} }
// ===== TABS ===== /* ============================================
function showTab(i, el) { SWITCH DE TEMA (claro por defecto)
document.querySelectorAll('.tab').forEach(t => t.classList.remove('active')); ============================================ */
document.querySelectorAll('.panel').forEach(p => p.classList.remove('active')); function initTheme() {
el.classList.add('active'); const savedTheme = localStorage.getItem('theme') || 'light';
document.querySelector('.panel[data-panel="' + i + '"]').classList.add('active'); document.documentElement.setAttribute('data-theme', savedTheme);
} }
// ===== ACCORDION ===== function toggleTheme() {
function toggleAcc(head) { const current = document.documentElement.getAttribute('data-theme') || 'light';
const item = head.parentElement; const next = current === 'dark' ? 'light' : 'dark';
document.querySelectorAll('.acc-item').forEach(i => { if (i !== item) i.classList.remove('open'); }); document.documentElement.setAttribute('data-theme', next);
item.classList.toggle('open'); localStorage.setItem('theme', next);
} }
// ===== FAQ ===== // Ejecutar al cargar la página
function toggleFaq(head) { document.addEventListener('DOMContentLoaded', () => {
const item = head.parentElement; initTheme();
const isOpen = item.classList.contains('open');
document.querySelectorAll('.faq-item').forEach(i => { const themeBtn = document.querySelector('.theme-toggle');
i.classList.remove('open'); if (themeBtn) {
const t = i.querySelector('.faq-toggle'); themeBtn.addEventListener('click', toggleTheme);
if (t) t.textContent = '+'; }
}); });
if (!isOpen) { /* ============================================
item.classList.add('open'); CALCULAR ANCHO DEL SCROLLBAR
const toggle = item.querySelector('.faq-toggle'); ============================================ */
if (toggle) toggle.textContent = '−'; function getScrollbarWidth() {
return window.innerWidth - document.documentElement.clientWidth;
}
function applyScrollbarCompensation() {
const scrollbarWidth = getScrollbarWidth();
document.documentElement.style.setProperty('--scrollbar-width', `${scrollbarWidth}px`);
}
/* ============================================
MENÚ FULLSCREEN
============================================ */
function openMenu() {
const menu = document.getElementById('fullscreen-menu');
const overlay = document.getElementById('menu-overlay');
const menuToggle = document.querySelector('.menu-toggle');
if (menu && overlay) {
applyScrollbarCompensation();
menu.classList.add('is-open');
overlay.classList.add('is-open');
document.body.classList.add('menu-open');
menuToggle.setAttribute('aria-expanded', 'true');
} }
} }
// ===== COTIZADOR ===== function closeMenu() {
const answers = [null, null, null]; const menu = document.getElementById('fullscreen-menu');
let current = 0; const overlay = document.getElementById('menu-overlay');
const menuToggle = document.querySelector('.menu-toggle');
document.querySelectorAll('.opt').forEach(opt => { if (menu && overlay) {
opt.addEventListener('click', function() { menu.classList.remove('is-open');
const group = this.parentElement; overlay.classList.remove('is-open');
const q = parseInt(group.dataset.q); document.body.classList.remove('menu-open');
group.querySelectorAll('.opt').forEach(o => o.classList.remove('selected')); menuToggle.setAttribute('aria-expanded', 'false');
this.classList.add('selected'); }
answers[q] = parseInt(this.dataset.val); }
document.getElementById('next' + q).disabled = false;
const step = this.closest('.step'); /* ============================================
const qNum = step.querySelector('.q-num'); INICIALIZACIÓN
if (qNum) qNum.classList.add('active'); ============================================ */
}); document.addEventListener('DOMContentLoaded', async () => {
// Cargar menú y footer
await Promise.all([
loadInclude('#menu-container', 'includes/menu.html'),
loadInclude('#footer-container', 'includes/footer.html')
]);
// Inicializar tema
initTheme();
// Eventos del tema
const themeBtn = document.querySelector('.theme-toggle');
if (themeBtn) themeBtn.addEventListener('click', toggleTheme);
// Eventos del menú
const menuToggle = document.querySelector('.menu-toggle');
const menuClose = document.querySelector('.menu-close');
const menuOverlay = document.getElementById('menu-overlay');
const menuLinks = document.querySelectorAll('.fullscreen-menu a');
if (menuToggle) menuToggle.addEventListener('click', openMenu);
if (menuClose) menuClose.addEventListener('click', closeMenu);
if (menuOverlay) menuOverlay.addEventListener('click', closeMenu);
// Cerrar menú al hacer clic en un enlace
menuLinks.forEach(link => {
link.addEventListener('click', closeMenu);
}); });
function updateProgress() { // Cerrar menú con tecla Escape
for (let i = 0; i < 3; i++) { document.addEventListener('keydown', (e) => {
document.getElementById('p' + (i + 1)).style.width = i <= current ? '100%' : '0%'; if (e.key === 'Escape') closeMenu();
} });
}
function next() { // Año dinámico en el footer
document.querySelector('.step[data-step="' + current + '"]').classList.remove('active'); const yearEl = document.getElementById('current-year');
current++; if (yearEl) yearEl.textContent = new Date().getFullYear();
document.querySelector('.step[data-step="' + current + '"]').classList.add('active'); });
updateProgress();
}
function prev() {
document.querySelector('.step[data-step="' + current + '"]').classList.remove('active');
current--;
document.querySelector('.step[data-step="' + current + '"]').classList.add('active');
updateProgress();
}
const plans = [
{ name: 'Esencial', price: '$250.000 ARS', desc: 'Ideal para arrancar con presencia digital profesional y consistente, sin sobre-invertir todavía.' },
{ name: 'Impulso', price: '$420.000 ARS', desc: 'Pensado para marcas en crecimiento que necesitan más alcance, leads y una primera campaña de publicidad.' },
{ name: 'Premium', price: '$650.000 ARS + pauta', desc: 'Nuestro plan más recomendado: gestión integral de contenido, publicidad y estrategia para consolidar y expandir.' },
{ name: 'Elite', price: '$1.000.000 ARS', desc: 'Máximo posicionamiento y gestión de marca completa, para negocios listos para escalar en serio.' }
];
function showResult() {
document.querySelector('.step[data-step="2"]').classList.remove('active');
const avg = Math.round((answers[0] + answers[1] + answers[2]) / 3);
const idx = Math.min(Math.max(avg - 1, 0), 3);
document.getElementById('rp-name').textContent = plans[idx].name;
document.getElementById('rp-price').innerHTML = plans[idx].price + ' <small>/ mes</small>';
document.getElementById('rp-desc').textContent = plans[idx].desc;
document.getElementById('result').classList.add('active');
}
function restart() {
answers[0] = answers[1] = answers[2] = null;
current = 0;
document.querySelectorAll('.opt').forEach(o => o.classList.remove('selected'));
document.querySelectorAll('[id^="next"]').forEach(b => b.disabled = true);
document.querySelectorAll('.q-num').forEach(q => q.classList.remove('active'));
document.getElementById('result').classList.remove('active');
document.querySelectorAll('.step').forEach(s => s.classList.remove('active'));
document.querySelector('.step[data-step="0"]').classList.add('active');
updateProgress();
}
// ===== FILTRO DE SERVICIOS EN CONTACTO =====
function selectFilter(event) {
const el = event.currentTarget;
const container = el.parentElement;
container.querySelectorAll('.filter-tag').forEach(t => t.classList.remove('active'));
el.classList.add('active');
const value = el.dataset.value;
document.getElementById('servicioSeleccionado').value = value;
const otroInput = document.getElementById('servicioOtro');
if (value === 'otro') {
otroInput.style.display = 'block';
otroInput.required = true;
} else {
otroInput.style.display = 'none';
otroInput.required = false;
otroInput.value = '';
}
}
// ===== FORMULARIO =====
function handleSubmit(e) {
e.preventDefault();
const form = document.getElementById('contactForm');
const data = new FormData(form);
const nombre = data.get('nombre');
const email = data.get('email');
const mensaje = data.get('mensaje');
if (!nombre || !email || !mensaje) {
alert('Por favor, completá todos los campos obligatorios.');
return false;
}
const btn = form.querySelector('button[type="submit"]');
const originalText = btn.textContent;
btn.textContent = 'Enviando...';
btn.disabled = true;
setTimeout(() => {
alert('¡Mensaje enviado con éxito! Te responderemos a la brevedad.');
form.reset();
btn.textContent = originalText;
btn.disabled = false;
document.querySelectorAll('.filter-tag').forEach(t => t.classList.remove('active'));
document.querySelector('.filter-tag[data-value="todos"]').classList.add('active');
document.getElementById('servicioOtro').style.display = 'none';
}, 1500);
return false;
}
+29
View File
@@ -0,0 +1,29 @@
<!DOCTYPE html>
<html lang="es" data-theme="light">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="description" content="">
<title>Servicios - [Nombre de la agencia]</title>
<link rel="stylesheet" href="style/main.css">
</head>
<body>
<div id="menu-container"></div>
<main>
<section id="servicios-section-1"><h2>Sección 1</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-2"><h2>Sección 2</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-3"><h2>Sección 3</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-4"><h2>Sección 4</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-5"><h2>Sección 5</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-6"><h2>Sección 6</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-7"><h2>Sección 7</h2><p>Contenido pendiente de definir.</p></section>
<section id="servicios-section-8"><h2>Sección 8</h2><p>Contenido pendiente de definir.</p></section>
</main>
<div id="footer-container"></div>
<script src="scripts/main.js"></script>
<script src="scripts/efecto.js"></script>
</body>
</html>
View File
+492
View File
@@ -0,0 +1,492 @@
/* ============================================
VARIABLES DE TEMA (modo claro por defecto)
============================================ */
:root {
/* Paleta Base / Primitivas de Marca */
--brand-plum: #221728;
--brand-crimson: #ba124d;
--brand-teal: #003f52;
--brand-sage-light: #eaf0ee;
--brand-rose-muted: #dfbdb9;
/* Tema Claro (Por Defecto) */
--bg-base: var(--brand-sage-light);
--bg-surface: #ffffff;
--bg-surface-elevated: #f5f9f8;
--text-primary: var(--brand-plum);
--text-secondary: var(--brand-teal);
--text-muted: rgba(34, 23, 40, 0.65);
--text-on-accent: #ffffff;
--btn-primary-bg: var(--brand-crimson);
--btn-primary-hover: #9c0f40;
--btn-secondary-bg: var(--brand-teal);
--btn-secondary-hover: #002c3a;
--badge-bg: var(--brand-rose-muted);
--badge-text: var(--brand-plum);
--border: rgba(0, 63, 82, 0.12);
--shadow: 0 4px 20px -2px rgba(34, 23, 40, 0.08);
--glow-animation: rgba(186, 18, 77, 0.25);
/* Tipografía - se completará */
--font-family-base: sans-serif;
--font-size-base: 16px;
/* Espaciados - se completarán */
--spacing-xs: 0.5rem;
--spacing-sm: 1rem;
--spacing-md: 2rem;
--spacing-lg: 4rem;
}
/* Modo oscuro */
[data-theme="dark"] {
--bg-base: var(--brand-plum);
--bg-surface: #2d2034;
--bg-surface-elevated: #392842;
--text-primary: var(--brand-sage-light);
--text-secondary: var(--brand-rose-muted);
--text-muted: rgba(234, 240, 238, 0.65);
--text-on-accent: #ffffff;
--btn-primary-bg: var(--brand-crimson);
--btn-primary-hover: #d81a5c;
--btn-secondary-bg: #0b5066;
--btn-secondary-hover: #10637d;
--badge-bg: rgba(223, 189, 185, 0.18);
--badge-text: var(--brand-rose-muted);
--border: rgba(234, 240, 238, 0.12);
--shadow: 0 4px 24px -2px rgba(0, 0, 0, 0.45);
--glow-animation: rgba(186, 18, 77, 0.45);
}
/* ============================================
RESET BÁSICO
============================================ */
*,
*::before,
*::after {
box-sizing: border-box;
margin: 0;
padding: 0;
}
html {
font-size: var(--font-size-base);
scroll-behavior: smooth;
}
body {
font-family: var(--font-family-base);
background-color: var(--bg-base);
color: var(--text-primary);
line-height: 1.5;
min-height: 100vh;
display: flex;
flex-direction: column;
transition: background-color 0.3s ease, color 0.3s ease;
}
body.menu-open {
overflow: hidden;
padding-right: var(--scrollbar-width, 0px);
}
main {
flex: 1;
}
img,
video {
max-width: 100%;
display: block;
}
a {
color: inherit;
text-decoration: none;
}
ul {
list-style: none;
}
/* ============================================
HEADER Y NAVEGACIÓN
============================================ */
.site-header {
background-color: var(--bg-surface);
border-bottom: 1px solid var(--border);
padding: var(--spacing-sm);
position: sticky;
top: 0;
z-index: 100;
box-shadow: var(--shadow);
}
.main-nav {
display: flex;
justify-content: space-between;
align-items: center;
max-width: 1400px;
margin: 0 auto;
}
/* Logo */
.logo {
display: flex;
align-items: center;
}
.logo img {
height: 40px;
width: auto;
}
.logo-light {
display: block;
}
.logo-dark {
display: none;
}
[data-theme="dark"] .logo-light {
display: none;
}
[data-theme="dark"] .logo-dark {
display: block;
}
/* ============================================
ESTILOS DE BARRA DE NAVEGACIÓN (BOTONES)
============================================ */
/* Contenedor general de acciones */
.nav-actions {
display: flex;
gap: var(--spacing-sm);
align-items: center;
}
/* Base común para botones (menú y tema) */
.menu-toggle,
.theme-toggle {
background: none;
border: 1px solid var(--border);
color: var(--text-primary);
padding: 0.5rem 1rem;
cursor: pointer;
font-size: 1rem;
border-radius: 4px;
transition: all 0.3s ease;
}
.menu-toggle:hover,
.theme-toggle:hover {
background-color: var(--bg-surface-elevated);
border-color: var(--text-primary);
}
/* ============================================
SWITCH DE TEMA (ESPECÍFICO CON ANIMACIÓN)
============================================ */
/* Ajustes del botón contenedor para que sea relativo y un círculo */
.theme-toggle {
padding: 0; /* Removemos el padding para controlar el centrado */
width: 40px;
height: 40px;
display: flex;
align-items: center;
justify-content: center;
border-radius: 50%; /* Es más estético como un círculo */
overflow: hidden; /* Mantiene la rotación dentro del botón */
position: relative; /* Esencial para superponer los iconos */
}
/* Estilos base para los iconos SVG */
.theme-icon {
width: 20px;
height: 20px;
display: block;
position: absolute; /* Superponemos los iconos uno encima del otro */
/* === EL EFECTO: Transiciones suaves de opacidad y rotación === */
transition: transform 0.5s ease, opacity 0.5s ease;
}
/* --- LÓGICA DE VISIBILIDAD Y ANIMACIÓN CON DATA-THEME --- */
/* 1. MODO CLARO (POR DEFECTO) O INICIAL */
/* Sol (oculto en modo claro, rotado 180 grados y transparente) */
[data-theme="light"] .icon-sun,
:root:not([data-theme="dark"]) .icon-sun {
opacity: 0;
transform: rotate(180deg);
pointer-events: none; /* No interactuable */
}
/* Luna (visible en modo claro, posición normal y opaca) */
[data-theme="light"] .icon-moon,
:root:not([data-theme="dark"]) .icon-moon {
opacity: 1;
transform: rotate(0deg);
pointer-events: auto; /* Interactuable */
}
/* 2. MODO OSCURO */
/* Sol (visible en modo oscuro, posición normal y opaco) */
[data-theme="dark"] .icon-sun {
opacity: 1;
transform: rotate(0deg);
pointer-events: auto; /* Interactuable */
}
/* Luna (oculta en modo oscuro, rotada negativamente y transparente) */
[data-theme="dark"] .icon-moon {
opacity: 0;
transform: rotate(-180deg); /* Rota en dirección opuesta al sol */
pointer-events: none; /* No interactuable */
}
/* ============================================
MENÚ DESPLEGABLE (desde abajo)
============================================ */
.menu-overlay {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(0, 0, 0, 0.5);
opacity: 0;
visibility: hidden;
transition: opacity 0.3s ease, visibility 0.3s ease;
z-index: 998;
}
.menu-overlay.is-open {
opacity: 1;
visibility: visible;
}
.fullscreen-menu {
position: fixed;
bottom: 0;
left: 0;
width: 100%;
height: 50vh; /* Mitad del alto en desktop */
background-color: var(--bg-surface);
transform: translateY(100%);
transition: transform 0.4s cubic-bezier(0.4, 0, 0.2, 1);
z-index: 999;
overflow-y: auto;
padding: var(--spacing-md) var(--spacing-lg);
box-shadow: 0 -4px 20px -2px rgba(0, 0, 0, 0.15);
}
.fullscreen-menu.is-open {
transform: translateY(0);
}
.menu-close {
position: absolute;
top: var(--spacing-sm);
right: var(--spacing-md);
background: none;
border: 1px solid var(--border);
color: var(--text-primary);
font-size: 1.5rem;
width: 40px;
height: 40px;
cursor: pointer;
border-radius: 4px;
display: flex;
align-items: center;
justify-content: center;
transition: all 0.3s ease;
}
.menu-close:hover {
background-color: var(--bg-surface-elevated);
border-color: var(--text-primary);
}
.menu-content {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: var(--spacing-md);
max-width: 1400px;
margin: 0 auto;
height: 100%;
align-content: start;
}
.menu-column h3 {
font-size: 1rem;
margin-bottom: var(--spacing-sm);
color: var(--text-secondary);
font-weight: 600;
text-transform: uppercase;
letter-spacing: 0.5px;
}
.menu-column ul {
display: flex;
flex-direction: column;
gap: var(--spacing-xs);
}
.menu-column a {
color: var(--text-primary);
font-size: 0.95rem;
transition: color 0.3s ease;
display: block;
padding: 0.2rem 0;
}
.menu-column a:hover {
color: var(--btn-primary-bg);
}
/* Columna 3 - Contacto y botones */
.menu-contact-info {
margin-bottom: var(--spacing-sm);
}
.menu-contact-info p {
margin-bottom: 0.25rem;
color: var(--text-muted);
font-size: 0.9rem;
}
.menu-social {
display: flex;
gap: var(--spacing-sm);
margin-top: var(--spacing-xs);
}
.menu-social a {
font-size: 0.9rem;
color: var(--text-secondary);
}
.menu-buttons {
display: flex;
flex-direction: column;
gap: var(--spacing-xs);
margin-top: var(--spacing-sm);
}
.btn-menu {
display: block;
padding: 0.6rem 1.2rem;
text-align: center;
border-radius: 4px;
font-weight: 600;
font-size: 0.9rem;
transition: all 0.3s ease;
}
.btn-menu-primary {
background-color: var(--btn-primary-bg);
color: var(--text-on-accent);
}
.btn-menu-primary:hover {
background-color: var(--btn-primary-hover);
}
.btn-menu-secondary {
background-color: var(--btn-secondary-bg);
color: var(--text-on-accent);
}
.btn-menu-secondary:hover {
background-color: var(--btn-secondary-hover);
}
/* Responsive - Mobile */
@media (max-width: 768px) {
.fullscreen-menu {
height: 85vh; /* En mobile ocupa más espacio */
padding: var(--spacing-md);
}
.menu-content {
grid-template-columns: 1fr;
gap: var(--spacing-md);
}
.menu-column h3 {
font-size: 1.1rem;
}
.menu-column a {
font-size: 1rem;
}
}
/* Pantallas muy pequeñas */
@media (max-width: 480px) {
.fullscreen-menu {
height: 90vh;
}
}
/* ============================================
SECCIONES BÁSICAS
============================================ */
main section {
padding: var(--spacing-md) var(--spacing-sm);
border-bottom: 1px dashed var(--border);
}
main section h2 {
margin-bottom: var(--spacing-sm);
font-size: 1.5rem;
}
/* ============================================
FOOTER
============================================ */
.site-footer {
border-top: 1px solid var(--border);
padding: var(--spacing-md) var(--spacing-sm);
margin-top: auto;
background-color: var(--bg-surface);
}
.footer-content {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: var(--spacing-md);
margin-bottom: var(--spacing-md);
max-width: 1400px;
margin-left: auto;
margin-right: auto;
}
.footer-col h4 {
margin-bottom: var(--spacing-xs);
color: var(--text-secondary);
}
.footer-bottom {
border-top: 1px solid var(--border);
padding-top: var(--spacing-sm);
text-align: center;
font-size: 0.875rem;
color: var(--text-muted);
}
-768
View File
@@ -1,768 +0,0 @@
/* ===== FUENTES ===== */
@import url('https://fonts.googleapis.com/css2?family=Literata:ital,wght@0,400;0,500;0,600;0,700;0,800;1,400;1,500;1,600;1,700;1,800&family=Raleway:wght@300;400;500;600;700&family=Jost:wght@300;400;500;600;700&display=swap');
/* ===== VARIABLES ===== */
:root {
--teal: #003F52;
--ligth-teal: #006d8f;
--bordo: #BA124D;
--oscuro: #110916;
--casi-negro: #0B060E;
--dusty: #cec7d1;
--claro: #EAF0EE;
--rose-gold-1: #DFBDB9;
--rose-gold-2: #BA8B7A;
--rose-gold-3: #C89A82;
--font-display: 'Literata', serif;
--font-ui: 'Raleway', sans-serif;
--font-body: 'Jost', sans-serif;
--font-name: 'Kaleagnetta', handwriting;
}
* { box-sizing: border-box; margin: 0; padding: 0; }
body {
font-family: var(--font-body);
background: var(--oscuro);
color: var(--claro);
overflow-x: hidden;
font-weight: 300;
}
/* ===== LOGO ===== */
.logo-img { height: 32px; width: auto; display: block; }
/* ===== CANVAS FLUIDO ===== */
#fluidCanvas {
display: block;
width: 100%;
height: 100vh;
position: fixed;
top: 0;
left: 0;
z-index: 0;
pointer-events: auto;
background: var(--oscuro);
}
/* Asegurar que el contenido esté por encima */
.hero, section, .footer {
position: relative;
z-index: 1;
}
/* ===== HEADER ===== */
header {
position: fixed; top: 0; left: 0; right: 0; z-index: 50;
display: flex; align-items: center; justify-content: space-between;
padding: 26px 48px;
background: linear-gradient(180deg, rgba(17,9,22,.9) 0%, rgba(17,9,22,0) 100%);
}
.menu-btn {
display: flex; align-items: center; gap: 10px;
background: transparent; border: 1px solid rgba(234,240,238,.2);
border-radius: 100px; padding: 10px 20px;
color: var(--claro); font-family: var(--font-ui); font-size: 12px;
letter-spacing: .14em; text-transform: uppercase; font-weight: 500;
cursor: pointer; transition: .25s;
}
.menu-btn:hover { border-color: var(--claro); color: var(--claro); }
.menu-btn .bars { display: flex; flex-direction: column; gap: 3px; }
.menu-btn .bars span { width: 14px; height: 1.4px; background: currentColor; display: block; }
/* ===== OVERLAY & SHEET ===== */
.overlay {
position: fixed; inset: 0; background: rgba(0,0,0,1);
opacity: 0; pointer-events: none; transition: .35s; z-index: 90;
}
.overlay.open { opacity: 1; pointer-events: auto; }
.sheet {
position: fixed; left: 0; right: 0; bottom: 0; z-index: 100;
background: var(--claro); border-radius: 22px 22px 0 0;
padding: 10px 36px 30px;
transform: translateY(102%);
transition: transform .4s cubic-bezier(.2,.8,.2,1);
max-height: 55vh; overflow-y: auto;
color: var(--oscuro); box-shadow: 0 -8px 40px rgba(0,0,0,.3);
}
.sheet.open { transform: translateY(0); }
.sheet-handle { width: 44px; height: 4px; background: rgba(34,23,40,.2); border-radius: 100px; margin: 0 auto 16px; }
.sheet-top { display: flex; justify-content: space-between; align-items: center; margin-bottom: 20px; }
.sheet-top .logo { font-size: 0; }
.sheet-top .logo img { height: 28px; width: auto; }
.close-btn {
width: 32px; height: 32px; border-radius: 100px;
border: 1px solid rgba(34,23,40,.2);
background: transparent; color: var(--oscuro); font-size: 14px;
cursor: pointer; display: flex; align-items: center; justify-content: center;
transition: .2s;
}
.close-btn:hover { border-color: var(--bordo); color: var(--bordo); }
.sheet-body { display: grid; grid-template-columns: 1fr 1fr 1fr; gap: 30px; align-items: start; }
.sheet-col { display: flex; flex-direction: column; gap: 2px; }
.sheet-col-title {
font-family: var(--font-ui); font-size: 18px; font-weight: 500;
letter-spacing: .12em; text-transform: uppercase;
color: var(--bordo); margin-bottom: 8px; padding-right: 12px; text-align: right;
}
.sheet-link {
display: grid; grid-template-columns: 1fr 20px; align-items: center;
gap: 8px; padding: 6px 12px; border-radius: 6px;
text-decoration: none; color: var(--oscuro); transition: .2s;
background: transparent; text-align: right;
}
.sheet-link:hover { background: rgba(186,18,77,.06); }
.sheet-link-icon { font-size: 16px; color: var(--bordo); opacity: .4; text-align: center; grid-row: 1/3; grid-column: 2; }
.sheet-link-main {
font-family: var(--font-display); font-style: italic; font-weight: 600;
font-size: 18px; color: var(--oscuro); line-height: 1.2; grid-column: 1;
}
.sheet-link-desc {
font-family: var(--font-ui); font-size: 14px; color: var(--oscuro);
font-weight: 500; opacity: .8; grid-column: 1; margin-top: -2px;
}
.sheet-link.highlight {
background: var(--bordo); border-radius: 6px; padding: 10px 14px; margin-top: 6px;
}
.sheet-link.highlight .sheet-link-icon { color: #fff; opacity: 1; }
.sheet-link.highlight .sheet-link-main { color: #fff; }
.sheet-link.highlight .sheet-link-desc { color: rgba(255,255,255,.7); }
.sheet-link.highlight:hover { background: #9c0f40; }
/* ===== HERO ===== */
.hero {
min-height: 100vh;
display: flex;
flex-direction: column;
justify-content: center;
position: relative;
padding: 0 80px;
max-width: 1200px;
margin: 0 auto;
text-align: center;
pointer-events: none;
}
.hero-content {
position: relative;
z-index: 2;
max-width: 900px;
margin: 0 auto;
pointer-events: auto;
}
/* ===== TIPOGRAFÍA ===== */
.eyebrow {
font-family: var(--font-ui); font-size: 12px; letter-spacing: .28em;
text-transform: uppercase; color: var(--claro); margin-bottom: 22px;
display: flex; align-items: center; gap: 12px; opacity: 0.6;
}
.eyebrow::before {
content: ''; width: 30px; height: 1px;
background: linear-gradient(90deg, var(--rose-gold-3), var(--rose-gold-1));
}
h1, h2 {
font-family: var(--font-display); font-weight: 500; font-style: italic;
font-size: clamp(40px, 6vw, 72px);
max-width: 900px;
line-height: 1.05;
margin-bottom: 16px;
}
.grad-word {
background: linear-gradient(100deg, var(--rose-gold-1) 0%, var(--bordo) 70%, var(--ligth-teal) 100%);
-webkit-background-clip: text; background-clip: text; color: transparent;
}
p, .lede {
font-family: var(--font-ui); font-size: 22px; line-height: 1.7;
color: var(--claro); max-width: 600px; margin: 0 auto 16px; opacity: 0.8;
font-weight: 400;
}
.lede { font-size: 18px; opacity: 0.7; max-width: 640px; }
/* ===== BOTONES ===== */
.btn {
font-family: var(--font-ui); font-size: 13px; font-weight: 500;
letter-spacing: .05em; padding: 16px 30px; border-radius: 2px;
cursor: pointer; transition: .25s; text-decoration: none;
display: inline-flex; align-items: center; gap: 8px;
}
.btn-solid {
background: var(--bordo); color: #fff; border: 1px solid var(--bordo);
}
.btn-solid:hover { background: #9c0f40; }
.btn-outline {
background: transparent; color: var(--claro);
border: 1px solid rgba(234,240,238,.2);
}
.btn-outline:hover { border-color: var(--claro); color: var(--claro); }
.hero-actions { display: flex; gap: 16px; justify-content: center; margin-top: 40px; }
.hero-actions .btn {
pointer-events: auto;
}
/* ===== HOME BUTTON ===== */
.home-btn {
position: absolute; right: 20px; bottom: 20px;
font-size: 20px; color: var(--rose-gold-1);
text-decoration: none; transition: .3s; z-index: 10;
pointer-events: auto;
}
.home-btn:hover { color: rgba(234,240,238,.4); }
/* ===== SCROLL HINT ===== */
.scroll-hint {
position: absolute; bottom: 36px; left: 50%; transform: translateX(-50%);
font-family: var(--font-ui); font-size: 10.5px; letter-spacing: .2em;
text-transform: uppercase; color: rgba(234,240,238,.7);
display: flex; flex-direction: column; align-items: center; gap: 8px;
pointer-events: auto;
}
.scroll-hint .line { width: 1px; height: 36px; background: rgba(234,240,238,.5); }
/* ===== SECCIONES GENERALES ===== */
section { padding: 80px 48px; max-width: 1200px; margin: 0 auto; position: relative; }
section .eyebrow { justify-content: center; }
section h2 { text-align: center; max-width: 800px; margin: 0 auto 12px; }
section .lede { text-align: center; max-width: 900px; margin-bottom: 38px; }
/* ===== SERVICIOS ===== */
.tabs {
display: flex; gap: 8px; flex-wrap: wrap; justify-content: center;
margin-bottom: 44px; border-bottom: 1px solid rgba(234,240,238,.06);
}
.tab {
font-family: var(--font-ui); font-size: 20px; font-weight: 400;
letter-spacing: .03em; color: var(--claro);
background: none; border: none; cursor: pointer;
padding: 14px 22px; position: relative; transition: .2s;
}
.tab .num {
font-family: var(--font-display); font-style: italic; font-size: 13px;
color: var(--claro); margin-right: 8px;
}
.tab.active { color: var(--claro); }
.tab.active::after {
content: ''; position: absolute; left: 0; right: 0; bottom: -1px;
height: 2px; background: linear-gradient(90deg, var(--rose-gold-3), var(--bordo));
}
.tab:hover { color: var(--claro); }
.panel { display: none; animation: fade .4s ease; }
.panel.active { display: grid; grid-template-columns: 1fr 1fr; gap: 60px; align-items: start; }
@keyframes fade { from { opacity: 0; transform: translateY(8px); } to { opacity: 1; transform: translateY(0); } }
.panel-copy h3 {
font-family: var(--font-display); font-style: italic; font-weight: 500;
font-size: 25px; margin-bottom: 16px;
}
.panel-copy h3 em { color: var(--bordo); font-style: italic; }
.panel-copy p { font-size: 15px; max-width: 600px; margin-bottom: 26px; }
.panel-list { display: flex; flex-direction: column; border-top: 1px solid rgba(234,240,238,.06); }
.panel-list .item {
display: flex; align-items: center; gap: 14px;
padding: 14px 0; border-bottom: 1px solid rgba(234,240,238,.06);
font-family: var(--font-ui); font-size: 15px; color: var(--claro); opacity: 0.8;
}
.icon-min {
font-size: 14px; color: var(--rose-gold-1); opacity: 0.5;
flex-shrink: 0; width: 24px; text-align: center;
}
/* ===== PLANES ===== */
.plans-grid {
display: grid; grid-template-columns: repeat(4, 1fr); gap: 18px; margin-bottom: 40px;
}
.plan-card {
background: rgba(22, 22, 9, 0.85); /* Antes era rgba(234,240,238,.03) */
border: 1px solid rgba(234,240,238,.1);
border-radius: 10px;
padding: 30px 24px;
display: flex;
flex-direction: column;
text-align: center;
backdrop-filter: blur(4px); /* Opcional: agrega desenfoque al fondo */
}
.plan-card.reco {
border: 1px solid rgba(223,189,185,.2);
background: rgba(234,240,238,.04);
box-shadow: 0 0 30px rgba(186,18,77,.2);
}
.badge {
align-self: center; font-family: var(--font-ui); font-size: 9px; font-weight: 700;
letter-spacing: .1em; text-transform: uppercase;
color: var(--bordo); border: 1px solid var(--bordo);
padding: 4px 14px; border-radius: 100px; margin-bottom: 14px;
}
.plan-name {
font-family: var(--font-display); font-style: italic; font-weight: 500;
font-size: 28px; margin-bottom: 4px;
}
.plan-stars { color: var(--claro); font-size: 11px; letter-spacing: 2px; margin-bottom: 14px; }
.plan-obj {
font-family: var(--font-ui); font-size: 18px; line-height: 1.5;
color: var(--claro); margin-bottom: 22px; min-height: 52px;
}
.plan-feats { list-style: none; flex: 1; margin-bottom: 24px; text-align: left; }
.plan-feats li {
font-family: var(--font-body); font-size: 18px; line-height: 1.5;
padding: 8px 0; border-top: 1px solid rgba(234,240,238,.08);
color: rgba(234,240,238,.7);
}
.plan-feats li:first-child { border-top: none; }
.plan-feats li::before { content: '— '; color: var(--claro); opacity: 1; }
.plan-cta {
font-family: var(--font-ui); font-size: 12px; font-weight: 500;
letter-spacing: .04em; text-align: center; padding: 12px;
border-radius: 2px; text-decoration: none;
border: 1px solid rgba(234,240,238,.15); color: var(--claro);
transition: .25s;
}
.plan-cta:hover { border-color: var(--claro); color: var(--claro); }
.plan-main-cta { display: block; max-width: 300px; margin: 0 auto; text-align: center; }
/* ===== ACCORDION ===== */
.acc { border-top: 1px solid rgba(234,240,238,.06); }
.acc-item {
border-bottom: 1px solid rgba(234,240,238,.06);
background: rgba(17, 9, 22, 0.7); /* Fondo sutil para cada item */
border-radius: 10px;
padding: 2px 0
}
.acc-head {
display: flex;
align-items: center;
justify-content: space-between;
padding: 20px 24px;
cursor: pointer;
}
.acc-head-left { display: flex; align-items: center; gap: 16px; }
.acc-num { font-family: var(--font-display); font-style: italic; color: var(--dusty); font-size: 14px; opacity: 1; }
.acc-name { font-family: var(--font-ui); font-size: 26px; font-weight: 400; }
.acc-toggle {
width: 26px;
height: 26px;
border-radius: 100px;
border: 1px solid rgba(234,240,238,.15);
display: flex;
align-items: center;
justify-content: center;
font-size: 14px;
color: var(--claro);
transition: .25s;
line-height: 1;
position: relative;
}
.acc-toggle::before {
content: '+';
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
.acc-item.open .acc-toggle { transform: rotate(45deg); border-color: var(--bordo); color: var(--bordo); }
.acc-body { max-height: 0; overflow: hidden; transition: .35s ease; }
.acc-item.open .acc-body { max-height: 600px; }
.acc-body-inner {
padding: 0 24px 24px 24px;
display: grid;
grid-template-columns: 1fr 1fr;
gap: 16px;
}
.service-row {
font-family: var(--font-ui); font-size: 14px; color: rgba(234,240,238,.8);
padding: 12px 0; border-top: 1px solid rgba(234,240,238,.04);
}
.service-row b {
display: block;
color: var(--claro);
font-family: var(--font-display);
font-style: italic;
font-size: 20px;
margin-bottom: 3px;
font-weight: 400;
}
.service-row .price { color: var(--dusty); font-family: var(--font-display); font-style: italic; font-size: 13px; }
/* ===== PROCESO ===== */
.arcade-grid { display: grid; grid-template-columns: repeat(6, 1fr); gap: 14px; }
.column { position: relative; padding: 0 6px; text-align: center; }
.column:not(:last-child)::after {
content: ''; position: absolute; right: -7px; top: 14%; bottom: 44px;
width: 1px; background: rgba(234,240,238,0.4);
}
.arch {
width: 100%; aspect-ratio: 1/1; max-height: 110px;
border: 1.5px solid rgba(223,189,185,0.67); border-bottom: none;
border-radius: 100px 100px 0 0;
display: flex; align-items: flex-end; justify-content: center;
padding-bottom: 16px; margin-bottom: 16px;
transition: .3s;
}
.column:hover .arch { border-color: rgba(223,189,185,.3); }
.arch .num {
font-family: var(--font-display);
font-style: italic; font-weight: 500;
font-size: 16px; color: var(--claro);
opacity: 0.5; }
.arch.final { background: var(--bordo);
border-color: var(--bordo); }
.arch.final svg { width: 22px; height: 22px; stroke: #fff; fill: none; stroke-width: 2; }
.cat {
font-family: var(--font-ui); font-size: 14px; letter-spacing: .14em;
text-transform: uppercase; color: var(--ligth-teal); font-weight: 600;
margin-bottom: 12px;
}
.column:nth-child(even) .cat { color: var(--bordo); }
.step-title {
font-family: var(--font-display); font-style: italic; font-weight: 500;
font-size: 16px; margin-bottom: 6px;
margin-bottom: 10px;
}
.step-desc {
font-family: var(--font-ui); font-size: 12px; line-height: 1.5;
color: var(--claro);
}
/* ===== CIFRAS ===== */
.cifras-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; }
.cifra-card {
background: rgba(17, 9, 22, 0.85);
border: 1px solid rgba(234,240,238,.05);
border-radius: 10px;
padding: 34px 30px;
text-align: center;
backdrop-filter: blur(4px);
}
.cifra-icon {
width: 100px; height: 100px; margin: 0 auto 20px;
border: 1.5px solid rgba(223,189,185,0.67); border-bottom: none;
border-radius: 100px 100px 0 0;
}
.cifra-label {
font-family: var(--font-body); font-size: 16px; letter-spacing: .18em;
text-transform: uppercase; color: var(--claro); font-weight: 500; margin-bottom: 12px;
}
.cifra-value {
font-family: var(--font-display); font-style: italic; font-weight: 500;
font-size: 20px; color: var(--ligth-teal); margin-bottom: 14px;
}
.cifra-desc {
font-family: var(--font-body); font-size: 16px; line-height: 1.6;
color: var(--dusty);
}
.cifra-desc b { color: var(--claro); font-weight: 400; }
/* ===== COTIZADOR ===== */
.card {
background: rgba(17, 9, 22, 0.85);
border: 1px solid rgba(234,240,238,.1);
border-radius: 14px;
padding: 48px 52px;
max-width: 800px;
margin: 0 auto;
backdrop-filter: blur(4px);
}
.progress { display: flex; gap: 6px; margin-bottom: 36px; }
.progress .seg { height: 3px; flex: 1; background: rgba(234,240,238,.1); border-radius: 100px; overflow: hidden; }
.progress .seg i { display: block; height: 100%; width: 0%; background: -gradient(90deg, var(--rose-gold-3), var(--bordo)linear); transition: .4s; }
.step { display: none; }
.step.active { display: block; animation: fade .35s ease; }
.q-num { font-family: var(--font-display); font-style: italic; color: var(--dusty); font-size: 18px; margin-bottom: 10px; }
.q-title { font-family: var(--font-display); font-style: italic; font-weight: 500; font-size: 26px; margin-bottom: 28px; }
.options { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin-bottom: 32px; }
.opt {
border: 1px solid rgba(234,240,238,.15);
border-radius: 8px;
padding: 18px 20px;
cursor: pointer;
transition: .2s;
font-family: var(--font-ui);
background: rgba(17, 9, 22, 0.7); /* Fondo semi-transparente para opciones */
}
.opt:hover { border-color: rgba(223,189,185,.3); }
.opt.selected {
border-color: var(--bordo);
background: rgba(186, 18, 77, 0.2);
}
.opt-title { font-size: 18px; font-weight: 500; color: var(--claro); margin-bottom: 3px; }
.opt-sub { font-size: 16px; color: var(--dusty); }
.nav-row { display: flex; justify-content: space-between; align-items: center; }
.btn-cotizador {
font-family: var(--font-ui); font-size: 13px; font-weight: 500;
padding: 12px 28px; border-radius: 4px; cursor: pointer; transition: .3s;
border: 1px solid var(--bordo); background: transparent; color: var(--bordo);
}
.btn-cotizador:hover:not(:disabled) { background: var(--bordo); color: #fff; }
.btn-cotizador:disabled { opacity: .2; cursor: not-allowed; border-color: #444; color: #666; }
.btn-cotizador-back {
font-family: var(--font-ui); font-size: 13px; font-weight: 500;
padding: 12px 28px; border-radius: 4px; cursor: pointer; transition: .3s;
border: 1px solid transparent; background: transparent; color: var(--dusty);
}
.btn-cotizador-back:hover { color: var(--claro); border-color: rgba(234,240,238,.1); }
.btn-cotizador-restart {
font-family: var(--font-ui); font-size: 13px; font-weight: 500;
padding: 12px 28px; border-radius: 4px; cursor: pointer; transition: .3s;
border: 1px solid var(--bordo); background: transparent; color: var(--bordo);
}
.btn-cotizador-restart:hover { background: var(--bordo); color: #fff; }
.result { display: none; text-align: center; padding-top: 10px; }
.result.active { display: block; animation: fade .4s ease; }
.result-badge {
font-family: var(--font-ui); font-size: 11px; letter-spacing: .14em;
text-transform: uppercase; color: var(--bordo); margin-bottom: 10px;
}
.result-plan { font-family: var(--font-display); font-style: italic; font-weight: 500; font-size: 32px; margin-bottom: 6px; }
.result-price { font-family: var(--font-display); font-style: italic; font-weight: 500; font-size: 22px; color: var(--bordo); margin-bottom: 18px; }
.result-desc { font-family: var(--font-body); font-size: 14px; color: var(--dusty); max-width: 400px; margin: 0 auto 30px; line-height: 1.6; }
.result-actions { display: flex; gap: 12px; justify-content: center; flex-wrap: wrap; }
/* ===== NOSOTROS ===== */
.team-grid-simple { display: grid; grid-template-columns: 1fr 1fr; gap: 30px; max-width: 800px; margin: 0 auto; }
.team-card-simple {
background: rgba(17, 9, 22, 0.85);
border: 1px solid rgba(234,240,238,.1);
border-radius: 12px;
padding: 40px 32px;
text-align: center;
backdrop-filter: blur(4px);
}
.team-name {
font-family: var(--font-name); font-weight: 500;
font-size: 50px; margin-bottom: 8px;
}
.team-role {
font-family: var(--font-ui); font-size: 16px; font-weight: 400;
letter-spacing: .06em; text-transform: uppercase; color: var(--dusty);
margin-bottom: 12px; opacity: 0.6;
}
.team-detail {
font-family: var(--font-display);
font-weight: 200;
font-size: 16px;
line-height: 1.6;
color: var(--claro);
}
.team-footer {
margin-top: 10px; padding-top: 32px;
border-top: 1px solid rgba(234,240,238,.04);
text-align: center;
}
.team-footer-text {
font-family: var(--font-ui); font-size: 16px; color: var(--dusty);
max-width: 700px; margin: 0 auto; line-height: 1.6;
}
/* ===== FAQ ===== */
.faq-grid { border-top: 1px solid rgba(234,240,238,.06); max-width: 900px; margin: 0 auto; }
.faq-item { border-bottom: 1px solid rgba(234,240,238,.06); }
.faq-head {
display: flex; justify-content: space-between; align-items: center;
padding: 20px 4px; cursor: pointer; transition: .2s;
}
.faq-head:hover .faq-q { color: var(--claro); }
.faq-q {
font-family: var(--font-display); font-weight: 200;
font-size: 20px; transition: .2s;
}
.faq-toggle {
font-family: var(--font-body); font-size: 18px; font-weight: 300;
color: var(--rose-gold-1); width: 28px; height: 28px;
display: flex; align-items:center; justify-content: center;
border-radius: 100px; border: 1px solid rgba(234,240,238,.1);
transition: .25s; flex-shrink: 0;
}
.faq-item.open .faq-toggle { border-color: var(--bordo); color: var(--bordo); }
.faq-body { max-height: 0; overflow: hidden; transition: .4s ease; }
.faq-item.open .faq-body { max-height: 100px; }
.faq-body p {
font-family: var(--font-ui); font-size: 16px; line-height: 1.7;
color: var(--claro); padding: 0 4px 14px; max-width: 800px;
}
/* ===== CONTACTO ===== */
.contact-grid { display: grid; grid-template-columns: 1.6fr 1fr; gap: 48px; align-items: start; }
.contact-form-wrap {
background: rgba(17, 9, 22, 0.85);
border: 1px solid rgba(234,240,238,.1);
border-radius: 12px;
padding: 40px 36px;
backdrop-filter: blur(4px);
}
.contact-form { display: flex; flex-direction: column; gap: 18px; }
.form-row { display: flex; gap: 18px; }
.form-group { flex: 1; display: flex; flex-direction: column; gap: 4px; }
.form-group.full { flex: 0 0 100%; }
.form-group label {
font-family: var(--font-ui); font-size: 14px; font-weight: 500;
letter-spacing: .04em; text-transform: uppercase; color: rgba(234,240,238,0.8);
}
.form-group .req { color: var(--bordo); }
.form-group input, .form-group textarea {
font-family: var(--font-body); font-size: 16px; font-weight: 300;
padding: 12px 14px; border-radius: 6px;
border: 1px solid rgba(234,240,238,.08);
background: rgba(234,240,238,.03); color: var(--claro);
transition: .25s; width: 100%;
}
.form-group input:focus, .form-group textarea:focus {
outline: none; border-color: var(--bordo);
background: rgba(234,240,238,.06);
}
.filter-tags { display: flex; flex-wrap: wrap; gap: 8px; }
.filter-tag {
font-family: var(--font-ui); font-size: 13px; font-weight: 500;
padding: 6px 16px; border-radius: 100px;
border: 1px solid rgba(234,240,238,.5); background: transparent;
color: rgba(234,240,238,.4); cursor: pointer; transition: .2s;
}
.filter-tag:hover { border-color: var(--claro); color: var(--claro); }
.filter-tag.active { background: var(--bordo); border-color: var(--bordo); color: #fff; }
.checkbox-label {
display: flex; align-items: center; gap: 10px;
font-family: var(--font-body); font-size: 13px; color: rgba(234,240,238,.6);
cursor: pointer;
}
.checkbox-label input[type="checkbox"] { width: 16px; height: 16px; accent-color: var(--bordo); }
.contact-direct { display: flex; flex-direction: column; gap: 16px; }
.contact-card {
display: flex;
align-items: flex-start;
gap: 16px;
padding: 18px 20px;
background: rgba(17, 9, 22, 0.85);
border: 1px solid rgba(234,240,238,.08);
border-radius: 10px;
backdrop-filter: blur(4px);
}
.contact-icon { font-size: 20px; line-height: 1.2; flex-shrink: 0; margin-top: 2px; }
.contact-label {
font-family: var(--font-ui); font-size: 14px; font-weight: 500;
letter-spacing: .08em; text-transform: uppercase; color: var(--claro); opacity: 0.5;
}
.contact-info a { font-family: var(--font-body); font-size: 14px; color: var(--claro); text-decoration: none; }
.contact-info a:hover { color: var(--claro); }
.contact-info span { font-family: var(--font-body); font-size: 13px; color: var(--claro); }
.contact-socials { display: flex; gap: 12px; }
.contact-socials a {
font-family: var(--font-ui); font-size: 13px; font-weight: 400;
color: var(--claro); text-decoration: none; opacity: 1;
}
.contact-socials a:hover { opacity: 1; }
/* ===== FOOTER ===== */
.footer {
background: rgba(0,0,0,.7); border-top: 1px solid rgba(234,240,238,.04);
padding: 60px 48px 20px;
}
.footer-inner {
max-width: 1200px; margin: 0 auto; display: grid;
grid-template-columns: 1fr 2fr; gap: 60px; padding-bottom: 40px;
border-bottom: 1px solid rgba(234,240,238,.04);
}
.footer-brand { display: flex; flex-direction: column; gap: 12px; }
.footer-desc { font-family: var(--font-ui); font-size: 16px; line-height: 1.6; color: var(--claro); max-width: 320px; }
.footer-links { display: grid; grid-template-columns: repeat(3, 1fr); gap: 40px; }
.footer-col h4 {
font-family: var(--font-ui); font-size: 12px; font-weight: 700;
letter-spacing: .1em; text-transform: uppercase; color: var(--dusty); opacity: 1;
margin-bottom: 12px;
}
.footer-col a {
display: block; font-family: var(--font-body); font-size: 13px;
color: var(--dusty); text-decoration: none; padding: 4px 0;
transition: .2s;
}
.footer-col a:hover { color: var(--claro); }
.footer-socials { display: flex; gap: 12px; margin-top: 8px; }
.footer-socials a {
font-family: var(--font-ui); font-size: 11px; font-weight: 500;
color: var(--claro); text-decoration: none; padding: 4px 12px;
border: 1px solid rgba(234,240,238,.08); border-radius: 100px;
transition: .2s;
}
.footer-socials a:hover { border-color: var(--claro); color: var(--claro); }
.footer-bottom {
max-width: 1200px; margin: 0 auto; padding-top: 20px;
display: flex; justify-content: space-between; align-items: center;
flex-wrap: wrap; gap: 12px;
}
.footer-bottom span { font-family: var(--font-body); font-size: 12px; color: rgba(234,240,238,.2); }
.footer-legal { display: flex; gap: 20px; }
.footer-legal a { font-family: var(--font-body); font-size: 12px; color: rgba(234,240,238,.2); text-decoration: none; }
.footer-legal a:hover { color: rgba(234,240,238,.5); }
/* Todas las cards con fondo oscuro y blur */
.plan-card,
.cifra-card,
.team-card-simple,
.contact-card,
.contact-form-wrap,
.card {
background: rgba(11, 5, 14, 0.85) !important;
backdrop-filter: blur(8px) !important;
-webkit-backdrop-filter: blur(8px) !important;
border: 1px solid rgba(234,240,238,0.08);
}
/* ===== MENU (fondo claro) ===== */
.sheet {
background: rgba(234, 240, 238, 0.95) !important;
backdrop-filter: blur(8px) !important;
-webkit-backdrop-filter: blur(8px) !important;
border: 1px solid rgba(34,23,40,0.08) !important;
}
/* ===== RESPONSIVE ===== */
@media (max-width: 980px) {
.plans-grid { grid-template-columns: 1fr 1fr; }
.arcade-grid { grid-template-columns: repeat(3, 1fr); row-gap: 40px; }
.column:nth-child(3)::after, .column:nth-child(6)::after { display: none; }
.cifras-grid { grid-template-columns: 1fr; }
}
@media (max-width: 820px) {
.sheet-body { grid-template-columns: 1fr 1fr; }
.sheet-col:last-child { grid-column: 1 / -1; }
.contact-grid { grid-template-columns: 1fr; }
.footer-inner { grid-template-columns: 1fr; gap: 40px; }
.team-grid-simple { grid-template-columns: 1fr; }
}
@media (max-width: 720px) {
header { padding: 20px 22px; }
.hero { padding: 0 30px; }
section { padding: 60px 22px; }
.panel.active { grid-template-columns: 1fr; gap: 30px; }
.plans-grid { grid-template-columns: 1fr; }
.arcade-grid { grid-template-columns: 1fr 1fr; row-gap: 30px; }
.column:nth-child(2n)::after { display: none; }
.options { grid-template-columns: 1fr; }
.card { padding: 32px 24px; }
.acc-body-inner { grid-template-columns: 1fr; }
.footer-links { grid-template-columns: 1fr 1fr; gap: 24px; }
.footer { padding: 40px 22px 16px; }
.footer-bottom { flex-direction: column; text-align: center; }
}
@media (max-width: 520px) {
.sheet {
position: fixed;
left: 0;
right: 0;
bottom: 0;
z-index: 100;
background: rgba(234, 240, 238, 0.95); /* Más opaco */
border-radius: 22px 22px 0 0;
padding: 10px 36px 30px;
transform: translateY(102%);
transition: transform .4s cubic-bezier(.2,.8,.2,1);
max-height: 55vh;
overflow-y: auto;
color: var(--oscuro);
box-shadow: 0 -8px 40px rgba(0,0,0,.5);
backdrop-filter: blur(8px); }
.sheet-body { grid-template-columns: 1fr; gap: 16px; }
.sheet-col:last-child { grid-column: auto; }
.home-btn { right: 12px; bottom: 12px; font-size: 10px; }
}