PageSourceSearch

https://lunarapp-urania-production.up.railway.app/calendario

html lunarapp-urania-production.up.railway.app collected 2026-10-03 12:12:51 UTC 36,155 bytes, 745 lines download raw bytes

1<!DOCTYPE html>
2<html lang="es">
3<head>
4    <meta charset="UTF-8">
5    <meta name="viewport" content="width=device-width, initial-scale=1.0">
6    <meta name="description" content="Calendario Lunar Mensual">
7    <meta name="theme-color" content="#1a1a2e">
8    
9    <title>Calendario - Lunar App</title>
10    
11    <!-- Google Fonts -->
12    <link rel="preconnect" href="https://fonts.googleapis.com">
13    <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
14    <link href="https://fonts.googleapis.com/css2?family=Cinzel:wght@400;600&family=Cormorant+Garamond:wght@300;400;600&display=swap" rel="stylesheet">
15    
16    <link rel="manifest" href="/static/manifest.json">
17    <link rel="stylesheet" href="/static/css/style.css">
18    
19    
19<script src="/static/js/luna-realista.js"></script>
19
20    
20<script src="https://unpkg.com/@astrodraw/astrochart"></script>
20
21    <link rel="stylesheet" href="https://unpkg.com/[email protected]/dist/leaflet.css" />
22    
22<script src="https://unpkg.com/[email protected]/dist/leaflet.js"></script>
22
23    
24    <style>
25        * {
26            box-sizing: border-box;
27        }
28        
29        body {
30            overflow-x: hidden;
31        }
32        
33        .main-container {
34            width: 100%;
35            max-width: 100%;
36            overflow-x: hidden;
37            padding: 1rem;
38        }
39        
40        .card {
41            width: 100%;
42            max-width: 100%;
43            overflow-x: hidden;
44        }
45        
46        .calendario-controles {
47            display: flex;
48            justify-content: space-between;
49            align-items: center;
50            margin-bottom: 2rem;
51            flex-wrap: wrap;
52            gap: 1rem;
53        }
54        
55        .calendario-mes {
56            font-size: 1.5rem;
57            color: var(--color-luna);
58        }
59        
60        .calendario-botones button {
61            background: var(--color-acento);
62            color: var(--color-texto);
63            border: none;
64            padding: 0.5rem 1rem;
65            margin: 0 0.25rem;
66            border-radius: 6px;
67            cursor: pointer;
68            transition: var(--transicion);
69        }
70        
71        .calendario-botones button:hover {
72            background: var(--color-destacado);
73        }
74        
75        .calendario-grid {
76            display: grid;
77            grid-template-columns: repeat(7, 1fr);
78            gap: 0.5rem;
79            width: 100%;
80            max-width: 100%;
81            overflow-x: hidden;
82        }
83        
84        .calendario-header {
85            background: var(--color-acento);
86            padding: 0.75rem;
87            text-align: center;
88            font-weight: bold;
89            border-radius: 6px;
90            font-size: 0.9rem;
91        }
92        
93        .calendario-dia {
94            background: var(--color-secundario);
95            padding: 1rem;
96            border-radius: 8px;
97            text-align: center;
98            min-height: 100px;
99            display: flex;
100            flex-direction: column;
101            justify-content: space-between;
102            transition: var(--transicion);
103            cursor: pointer;
104        }
105        
106        .calendario-dia:hover {
107            background: var(--color-acento);
108            transform: translateY(-2px);
109        }
110        
111        .dia-numero {
112            font-size: 1.2rem;
113            font-weight: bold;
114            color: var(--color-texto);
115        }
116        
117        .dia-fase {
118            width: 50px;
119            height: 50px;
120            margin: 0.5rem auto;
121            display: flex;
122            align-items: center;
123            justify-content: center;
124        }
125        
126        .dia-fase canvas {
127            max-width: 100%;
128            max-height: 100%;
129        }
130        
131        .dia-signo {
132            font-size: 1.2rem;
133            color: var(--color-texto-secundario);
134        }
135        
136        .dia-otro-mes {
137            opacity: 0.3;
138        }
139        
140        @media (max-width: 768px) {
141            .calendario-grid {
142                grid-template-columns: repeat(7, 1fr);
143                gap: 2px;
144                width: 100%;
145                padding: 0;
146            }
147            
148            .calendario-header {
149                padding: 0.4rem 0.1rem;
150                font-size: 0.65rem;
151                border-radius: 4px;
152            }
153            
154            .calendario-dia {
155                padding: 0.3rem 0.1rem;
156                min-height: 60px;
157                border-radius: 4px;
158            }
159            
160            .dia-numero {
161                font-size: 0.85rem;
162            }
163            
164            .dia-fase {
165                width: 30px;
166                height: 30px;
167                margin: 0.2rem auto;
168            }
169            
170            .dia-signo {
171                font-size: 0.6rem;
172                display: none; /* Ocultar en móvil para ahorrar espacio */
173            }
174            
175            .main-container {
176                padding: 0.5rem;
177            }
178            
179            .calendario-controles {
180                flex-direction: column;
181                gap: 1rem;
182            }
183            
184            .calendario-mes {
185                font-size: 1.2rem;
186                order: -1;
187            }
188            
189            .calendario-botones {
190                width: 100%;
191                display: flex;
192                justify-content: space-between;
193            }
194            
195            .calendario-botones button {
196                font-size: 0.8rem;
197                padding: 0.5rem 0.8rem;
198            }
199        }
200    </style>
201</head>
202<body>
203    <!-- Header -->
204    <header class="header">
205        <div class="container">
206            <div class="logo-section">
207                <img src="/static/images/logo_urania.png" alt="La Nación de Urania" class="logo-img">
208                <div class="logo-text-container">
209                    <h1 class="logo">LA NACIÓN DE URANIA</h1>
210                    <p class="logo-subtitle">Organización Astrológica</p>
211                </div>
212            </div>
213            
214            <!-- Botón hamburguesa (solo móvil) -->
215            <button class="menu-toggle" id="menu-toggle">
216                <span class="hamburger-line"></span>
217                <span class="hamburger-line"></span>
218                <span class="hamburger-line"></span>
219            </button>
220            
221            <nav class="nav" id="main-nav">
222                <a href="/" class="nav-link">Inicio</a>
223                <a href="/calendario" class="nav-link active">Calendario</a>
224                <a href="/eclipses" class="nav-link">Eclipses</a>
225                <a href="/streaming" class="nav-link">Streaming</a>
226                <a href="/carta-natal" class="nav-link">Carta Natal</a>
227                <a href="/notificaciones" class="nav-link">Notificaciones</a>
228            </nav>
229        </div>
230    </header>
231    
232    <!-- Overlay para cerrar menú al hacer click fuera (solo móvil) -->
233    <div class="menu-overlay" id="menu-overlay"></div>
234
235    <!-- Contenedor Principal -->
236    <main class="main-container">
237        <section class="card">
238            <div class="calendario-controles">
239                <div class="calendario-botones">
240                    <button onclick="cambiarMes(-1)">← Anterior</button>
241                    <button onclick="mesActual()">Hoy</button>
242                    <button onclick="cambiarMes(1)">Siguiente →</button>
243                </div>
244                <input type="month" id="selector-mes" onchange="irAMesSeleccionado()" 
245                       style="padding: 0.7rem 1rem; border-radius: 8px; background: #ffffff; color: #000000; border: 3px solid #d4af37; font-family: 'Cormorant Garamond', serif; cursor: pointer; font-size: 1.1rem; font-weight: 600; box-shadow: 0 4px 12px rgba(212, 175, 55, 0.5); min-width: 180px;">
246                <h2 class="calendario-mes" id="titulo-mes">Cargando...</h2>
247            </div>
248            
249            <!-- Días de la semana -->
250            <div class="calendario-grid">
251                <div class="calendario-header">Dom</div>
252                <div class="calendario-header">Lun</div>
253                <div class="calendario-header">Mar</div>
254                <div class="calendario-header">Mié</div>
255                <div class="calendario-header">Jue</div>
256                <div class="calendario-header">Vie</div>
257                <div class="calendario-header">Sáb</div>
258            </div>
259            
260            <!-- Días del mes -->
261            <div class="calendario-grid" id="calendario-dias">
262                <!-- Se llenará con JavaScript -->
263            </div>
264        </section>
265
266        <!-- Volver a inicio -->
267        <div class="acciones">
268            <button class="btn-actualizar" onclick="window.location.href='/'">
269                ← Volver a Inicio
270            </button>
271        </div>
272    </main>
273
274    <!-- Footer -->
275    <footer class="footer">
276        <p style="font-family: 'Cinzel', serif; color: var(--color-dorado); margin-bottom: 0.5rem;">© 2025 La Nación de Urania</p>
277        <p style="margin: 0.25rem 0;">
278            <a href="https://www.escuelaurania.com" target="_blank" style="color: var(--color-enlace); text-decoration: none;">www.escuelaurania.com</a>
279            -
280            <a id="email-link" style="color: var(--color-enlace); text-decoration: none; cursor: pointer;">cargando...</a>
281        </p>
282        <p style="margin: 0.25rem 0;">
283            📱 <a href="https://wa.me/5492944312096" target="_blank" style="color: var(--color-enlace); text-decoration: none;">WhatsApp: +54 9 294 431-2096</a>
284        </p>
285    </footer>
286
287    
287<script>
288        // Detectar zona horaria del usuario automáticamente
289        const userTimezone = Intl.DateTimeFormat().resolvedOptions().timeZone;
290        console.log(`🌍 Zona horaria detectada: ${userTimezone}`);
291        
292        let mesActualVista = new Date().getMonth() + 1;
293        let yearActualVista = new Date().getFullYear();
294        
295        const meses = [
296            'Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio',
297            'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre'
298        ];
299        
300        async function cargarCalendario() {
301            try {
302                const response = await fetch(`/api/calendario/mes?year=${yearActualVista}&month=${mesActualVista}`);
303                const data = await response.json();
304                
305                if (data.exito) {
306                    document.getElementById('titulo-mes').textContent = 
307                        `${meses[mesActualVista - 1]} ${yearActualVista}`;
308                    
309                    const calendarioDias = document.getElementById('calendario-dias');
310                    calendarioDias.innerHTML = '';
311                    
312                    // Calcular día de la semana del primer día del mes
313                    const primerDia = new Date(yearActualVista, mesActualVista - 1, 1);
314                    const diaSemana = primerDia.getDay();
315                    
316                    // Agregar días vacíos al inicio
317                    for (let i = 0; i < diaSemana; i++) {
318                        const diaVacio = document.createElement('div');
319                        diaVacio.className = 'calendario-dia dia-otro-mes';
320                        calendarioDias.appendChild(diaVacio);
321                    }
322                    
323                    // Agregar días del mes
324                    data.dias.forEach((dia, index) => {
325                        const diaDiv = document.createElement('div');
326                        diaDiv.className = 'calendario-dia';
327                        diaDiv.style.cursor = 'pointer'; // Indicar que es clickeable
328                        
329                        // Crear estructura HTML
330                        diaDiv.innerHTML = `
331                            <div class="dia-numero">${dia.dia}</div>
332                            <div class="dia-fase" id="dia-fase-${index}"></div>
333                            <div class="dia-signo">${dia.signo}</div>
334                        `;
335                        
336                        calendarioDias.appendChild(diaDiv);
337                        
338                        // Agregar evento click para abrir modal DESPUÉS de agregar al DOM
339                        diaDiv.addEventListener('click', () => {
340                            abrirModalDia(yearActualVista, mesActualVista, dia.dia);
341                        });
342                        
343                        // Renderizar luna realista después de agregar al DOM
344                        setTimeout(() => {
345                            const faseContainer = document.getElementById(`dia-fase-${index}`);
346                            if (window.lunaRealista && faseContainer) {
347                                window.lunaRealista.renderizar(
348                                    faseContainer,
349                                    dia.dia_ciclo,
350                                    50 // Tamaño pequeño para calendario
351                                );
352                            }
353                        }, 10);
354                    });
355                }
356            } catch (error) {
357                console.error('Error al cargar calendario:', error);
358                document.getElementById('calendario-dias').innerHTML = 
359                    '<div class="loading" style="grid-column: 1/-1;">Error al cargar calendario</div>';
360            }
361        }
362        
363        function cambiarMes(incremento) {
364            mesActualVista += incremento;
365            
366            if (mesActualVista > 12) {
367                mesActualVista = 1;
368                yearActualVista++;
369            } else if (mesActualVista < 1) {
370                mesActualVista = 12;
371                yearActualVista--;
372            }
373            
374            cargarCalendario();
375            actualizarSelectorMes();
376        }
377        
378        function mesActual() {
379            mesActualVista = new Date().getMonth() + 1;
380             yearActualVista = new Date().getFullYear();
381            cargarCalendario();
382            actualizarSelectorMes();
383        }
384        
385        function irAMesSeleccionado() {
386            const selector = document.getElementById('selector-mes');
387            if (!selector.value) return; // Si no hay valor, salir
388            
389            const [year, month] = selector.value.split('-');
390            const yearNum = parseInt(year);
391            const monthNum = parseInt(month);
392            
393            // Validar valores
394            if (isNaN(yearNum) || isNaN(monthNum)) return;
395            if (yearNum < 1900 || yearNum > 2100) return;
396            if (monthNum < 1 || monthNum > 12) return;
397            
398            yearActualVista = yearNum;
399            mesActualVista = monthNum;
400            cargarCalendario();
401        }
402        
403        function actualizarSelectorMes() {
404            const selector = document.getElementById('selector-mes');
405            const mesStr = mesActualVista.toString().padStart(2, '0');
406            selector.value = `${yearActualVista}-${mesStr}`;
407        }
408        
409        // ===== MODAL DE DATOS DEL DÍA =====
410        
411        let modalDiaActual = { year: null, month: null, day: null };
412
413        async function abrirModalDia(year, month, day) {
414            modalDiaActual = { year, month, day };
415            const modal = document.getElementById('modal-dia');
416            const overlay = document.getElementById('modal-dia-overlay');
417            const titulo = document.getElementById('modal-dia-titulo');
418            const body = document.getElementById('modal-dia-body');
419            
420            // Mostrar modal con loading
421            overlay.classList.add('active');
422            document.body.style.overflow = 'hidden';
423            titulo.textContent = `${day} de ${meses[month - 1]} ${year}`;
424            body.innerHTML = `
425                <div class="loading-container">
426                    <div class="loading-spinner">
427                        <div class="loading-spinner-luna">🌙</div>
428                    </div>
429                    <div class="loading-text">Cargando datos lunares...</div>
430                </div>
431            `;
432            
433            try {
434                // Llamar a la API
435                const response = await fetch(`/api/calendario/dia?year=${year}&month=${month}&day=${day}&timezone=${encodeURIComponent(userTimezone)}`);
436                const data = await response.json();
437                
438                if (data.exito) {
439                    mostrarDatosEnModal(data);
440                } else {
441                    body.innerHTML = '<div class="error">Error al cargar datos</div>';
442                }
443            } catch (error) {
444                console.error('Error al cargar datos del día:', error);
445                body.innerHTML = '<div class="error">Error al cargar datos</div>';
446            }
447        }
448        
449        // Función GLOBAL para símbolos
450        function getSignoSimbolo(signo) {
451            const simbolos = {
452                'Aries': '♈', 'Tauro': '♉', 'Géminis': '♊', 'Cáncer': '♋',
453                'Leo': '♌', 'Virgo': '♍', 'Libra': '♎', 'Escorpio': '♏',
454                'Sagitario': '♐', 'Capricornio': '♑', 'Acuario': '♒', 'Piscis': '♓'
455            };
456            return simbolos[signo] || signo;
457        }
458        
459        // Función GLOBAL para símbolos zodiacales
460        function getSignoSimbolo(signo) {
461            const simbolos = {
462                'Aries': '♈', 'Tauro': '♉', 'Géminis': '♊', 'Cáncer': '♋',
463                'Leo': '♌', 'Virgo': '♍', 'Libra': '♎', 'Escorpio': '♏',
464                'Sagitario': '♐', 'Capricornio': '♑', 'Acuario': '♒', 'Piscis': '♓'
465            };
466            return simbolos[signo] || signo;
467        }
468        
469        // Formatear fecha legible (24/dic/2025 - 22:54:13)
470        function formatearFecha(fechaStr) {
471            if (!fechaStr) return "";
472            const meses = ["ene", "feb", "mar", "abr", "may", "jun", "jul", "ago", "sep", "oct", "nov", "dic"];
473            const partes = fechaStr.split(" ");
474            if (partes.length !== 2) return fechaStr;
475            const [fecha, hora] = partes;
476            const [año, mes, dia] = fecha.split("-");
477            return `${dia}/${meses[parseInt(mes)-1]}/${año} - ${hora}`;
478        }
479        
480        function mostrarDatosEnModal(data) {
481            const body = document.getElementById('modal-dia-body');
482            
483            const LILITH = '⚸';
484            const PRIAPO = '⚮';
485            
486            const tipoIcono = data.tipo_modal === 'actual' ? '⏰' : 
487                            data.tipo_modal === 'futuro' ? '🔮' : '📅';
488            const tipoTexto = data.tipo_modal === 'actual' ? 'Tiempo Real' :
489                            data.tipo_modal === 'futuro' ? 'Datos Futuros' : 'Datos Pasados';
490            
491            let html = `
492                <div style="display: flex; justify-content: space-between; margin-bottom: 1rem; gap: 1rem;">
493                    <button onclick="navegarModalDia(-1)" style="flex: 1; padding: 0.5rem; cursor: pointer; background: var(--color-acento); border: none; border-radius: 6px; color: var(--color-texto); font-weight: bold;">← Anterior</button>
494                    <button onclick="navegarModalDia(1)" style="flex: 1; padding: 0.5rem; cursor: pointer; background: var(--color-acento); border: none; border-radius: 6px; color: var(--color-texto); font-weight: bold;">Siguiente →</button>
495                </div>
496                
497                <div class="modal-luna-visual">
498                    <div class="modal-luna-container" id="modal-luna-render"></div>
499                </div>
500                
501                <div style="text-align: center; padding: 0.5rem; background: rgba(100, 149, 237, 0.1); border-radius: 6px; margin-bottom: 1rem; font-size: 0.9rem;">
502                    ${tipoIcono} ${tipoTexto}${data.hora_calculo ? ': ' + data.hora_calculo : ''}
503                </div>
504            `;
505            
506            if (data.fase_lunar.es_fase_exacta) {
507                html += `
508                <div style="background: rgba(212, 175, 55, 0.2); border: 2px solid var(--color-dorado); border-radius: 6px; padding: 0.8rem; margin-bottom: 1rem;">
509                    <div style="font-weight: bold; margin-bottom: 0.5rem;">⭐ Fase Exacta</div>
510                    <div style="font-size: 0.9rem;">${data.fase_lunar.emoji} ${data.fase_lunar.nombre} a las ${data.fase_lunar.hora_exacta}</div>
511                    <div style="font-size: 0.85rem; color: var(--color-texto-secundario);">Posici&oacute;n: <span class="signo-simbolo">${getSignoSimbolo(data.fase_lunar.signo_fase_exacta)}</span> ${data.fase_lunar.grado_fase_exacta}</div>
512                </div>
513                `;
514            }
515            
516            html += `
517                <div style="background: var(--color-secundario); padding: 1rem; border-radius: 8px; line-height: 2; font-size: 0.95rem;">
518                    <div><strong>🌙 Fase:</strong> ${data.fase_lunar.emoji} ${data.fase_lunar.nombre}</div>
519                    <div><strong>💡 Iluminación:</strong> ${data.fase_lunar.iluminacion}%</div>
520            `;
521            
522            if (data.posicion) {
523                if (data.tipo_modal === 'actual') {
524                    html += `<div><strong>Signo:</strong> <span class="signo-simbolo">
524${getSignoSimbolo(data.posicion.signo)}</span> ${data.posicion.signo} ${data.posicion.grado_sexagesimal}</div>`;
525                } else {
526                    html += `<div><strong>Signo:</strong> <span class="signo-simbolo">${getSignoSimbolo(data.posicion.signo)}</span> ${data.posicion.signo} <em>(valor medio)</em></div>`;
527                }
528            }
529            
530            html += `<div><strong>📅 Día Lunar:</strong> ${data.fase_lunar.dia_lunar}</div>`;
531            
532            if (data.nodo_norte) {
533                if (data.tipo_modal === 'actual') {
534                    html += `<div><strong>☊ Nodo Norte:</strong> <span class="signo-simbolo">${getSignoSimbolo(data.nodo_norte.signo)}</span> ${data.nodo_norte.signo} ${data.nodo_norte.grado_sexagesimal}</div>`;
535                } else {
536                    html += `<div><strong>☊ Nodo Norte:</strong> <span class="signo-simbolo">${getSignoSimbolo(data.nodo_norte.signo)}</span> ${data.nodo_norte.signo} <em>(valor medio)</em></div>`;
537                }
538            }
539            
540            if (data.distancia) {
541                html += `<div><strong>📏 Valor Distancia:</strong> ${data.distancia.porcentaje}%`;
542                if (data.distancia.lilith) {
543                    html += ` ${LILITH} <strong style="color: #D4AF37;">Luna con Lilith</strong>`;
544                }
545                if (data.distancia.priapo) {
546                    html += ` ${PRIAPO} <strong style="color: #D4AF37;">Luna con Príapo</strong>`;
547                }
548                html += `</div>`;
549            }
550            
551            if (data.proximo_ingreso) {
552                html += `<div><strong>🚪 Próximo Ingreso:</strong> ${formatearFecha(data.proximo_ingreso.fecha + " " + data.proximo_ingreso.hora)} → <span class="signo-simbolo">${getSignoSimbolo(data.proximo_ingreso.signo)}</span> ${data.proximo_ingreso.signo} 0°00'00"</div>`;
553            }
554            
555            if (data.void_of_course) {
556                if (data.void_of_course.mayores.activo) {
557                    html += `<div><strong>🌑 Vacía de Curso (Aspectos Mayores):</strong> <span style="color: #FF6347;">ACTIVA</span> ${formatearFecha(data.void_of_course.mayores.inicio)} hasta ${formatearFecha(data.void_of_course.mayores.fin)}</div>`;
558                } else {
559                    html += `<div><strong>🌑 Vacía de Curso (Aspectos Mayores):</strong> <span style="color: #90EE90;">No activa</span></div>`;
560                }
561                
562                if (data.void_of_course.todos.activo) {
563                    html += `<div><strong>🌑 Vacía de Curso (Menores y Mayores):</strong> <span style="color: #FF6347;">ACTIVA</span> ${formatearFecha(data.void_of_course.todos.inicio)} hasta ${formatearFecha(data.void_of_course.todos.fin)}</div>`;
564                } else {
565                    html += `<div><strong>🌑 Vacía de Curso (Menores y Mayores):</strong> <span style="color: #90EE90;">No activa</span></div>`;
566                }
567            }
568            
569            // Tithi Hindú
570            if (data.fase_lunar.tithi_nombre) {
571                html += `
572                <div style="margin-top: 1rem; padding: 0.8rem; background: rgba(255, 165, 0, 0.1); border-radius: 6px;">
573                    <div style="font-weight: bold; margin-bottom: 0.5rem;">🕉️ Zodiaco Hindú (Tithi): ${data.fase_lunar.tithi_nombre}</div>
574                    <div style="font-size: 0.85rem; font-style: italic; color: var(--color-texto-secundario);">
575                        ${data.fase_lunar.tithi_interpretacion}
576                    </div>
577                </div>
578                `;
579            }
580            
581            html += `</div>`;
582            
583            // BOTON VER CARTA NATAL para TODOS los dias
584            if (data.fase_lunar.es_fase_exacta && data.fase_lunar.jd_fase_exacta) {
585                // Fases exactas: usar JD del momento exacto de la fase
586                html += `<div style="text-align:center;margin-top:1rem;"><button onclick="cfAbrirCarta(${data.fase_lunar.jd_fase_exacta}, '${data.fase_lunar.emoji} ${data.fase_lunar.nombre}')" style="background:linear-gradient(135deg,#d4af37,#b8962e);color:#0f0f1e;border:none;padding:0.6rem 1.5rem;border-radius:8px;font-weight:700;font-size:0.9rem;cursor:pointer;font-family:Cinzel,serif;">&#128302; VER CARTA NATAL</button></div>`;
587            } else if (typeof cfJDParaDia === 'function') {
588                // Dias normales: usar hora local del momento de consulta
589                var jdLocal = cfJDParaDia(modalDiaActual.year, modalDiaActual.month, modalDiaActual.day);
590                html += `<div style="text-align:center;margin-top:1rem;"><button onclick="cfAbrirCarta(${jdLocal}, '${data.fase_lunar.emoji} ${data.fase_lunar.nombre} (hora local)')" style="background:linear-gradient(135deg,#d4af37,#b8962e);color:#0f0f1e;border:none;padding:0.6rem 1.5rem;border-radius:8px;font-weight:700;font-size:0.9rem;cursor:pointer;font-family:Cinzel,serif;">&#128302; VER CARTA NATAL</button></div>`;
591            }
592            
593            body.innerHTML = html;
594            
595            setTimeout(() => {
596                const lunaContainer = document.getElementById('modal-luna-render');
597                if (window.lunaRealista && lunaContainer) {
598                    window.lunaRealista.renderizar(lunaContainer, data.fase_lunar.dia_ciclo, 150);
599                }
600            }, 50);
601        }
602        
603        function navegarModalDia(direccion) {
604            let { year, month, day } = modalDiaActual;
605            let fecha = new Date(year, month - 1, day);
606            fecha.setDate(fecha.getDate() + direccion);
607            abrirModalDia(fecha.getFullYear(), fecha.getMonth() + 1, fecha.getDate());
608        }
609
610        function cerrarModal() {
611            const overlay = document.getElementById('modal-dia-overlay');
612            overlay.classList.remove('active');
613            document.body.style.overflow = '';
614        }
615        
616        // Cargar calendario al iniciar
617        window.onload = function() {
618            // Inicializar variables con mes actual
619            const hoy = new Date();
620            currentMonth = hoy.getMonth() + 1;
621            currentYear = hoy.getFullYear();
622            
623            // Inicializar selector de fecha
624            actualizarSelectorMes();
625            
626            // Cargar calendario
627            cargarCalendario(currentMonth, currentYear);
628            
629            // Event listeners del modal (después de que el DOM esté listo)
630            document.getElementById('modal-dia-close').addEventListener('click', cerrarModal);
631            document.getElementById('modal-dia-overlay').addEventListener('click', function(e) {
632                if (e.target === this) {
633                    cerrarModal();
634                }
635            });
636        };
637    </script>
637
638    
639    <!-- JavaScript del menú hamburguesa -->
640    
640<script>
641        const menuToggle = document.getElementById('menu-toggle');
642        const mainNav = document.getElementById('main-nav');
643        const menuOverlay = document.getElementById('menu-overlay');
644        
645        // Abrir/cerrar menú
646        menuToggle.addEventListener('click', function() {
647            menuToggle.classList.toggle('active');
648            mainNav.classList.toggle('active');
649            menuOverlay.classList.toggle('active');
650            
651            // Bloquear scroll del body cuando menú abierto
652            document.body.style.overflow = mainNav.classList.contains('active') ? 'hidden' : '';
653            
654            // Tracking Firebase (si está disponible)
655            if (window.trackEvent) {
656                window.trackEvent('menu_toggle', {
657                    accion: mainNav.classList.contains('active') ? 'abrir' : 'cerrar'
658                });
659            }
660        });
661        
662        // Cerrar al hacer click en overlay
663        menuOverlay.addEventListener('click', function() {
664            menuToggle.classList.remove('active');
665            mainNav.classList.remove('active');
666            menuOverlay.classList.remove('active');
667            document.body.style.overflow = '';
668        });
669        
670        // Cerrar al hacer click en un link
671        mainNav.querySelectorAll('.nav-link').forEach(link => {
672            link.addEventListener('click', function() {
673                menuToggle.classList.remove('active');
674                mainNav.classList.remove('active');
675                menuOverlay.classList.remove('active');
676                document.body.style.overflow = '';
677            });
678        });
679    </script>
679
680    
681    <!-- Modal de datos del día -->
682    <div class="modal-overlay" id="modal-dia-overlay">
683        <div class="modal-calendario" id="modal-dia">
684            <div class="modal-header">
685                <h2 class="modal-titulo" id="modal-dia-titulo">Cargando...</h2>
686                <button class="modal-close" id="modal-dia-close">×</button>
687            </div>
688            <div class="modal-body" id="modal-dia-body">
689                <div class="loading-container">
690                    <div class="loading-spinner">
691                        <div class="loading-spinner-luna">🌙</div>
692                    </div>
693                    <div class="loading-text">Cargando fases lunares...</div>
694                </div>
695            </div>
696        </div>
697    </div>
698
699<!-- Modal Carta Natal Fases (z-index 10000 > modal calendario 9998) -->
700<div id="cf-modal-carta" style="display:none;position:fixed;top:0;left:0;right:0;bottom:0;background:rgba(0,0,0,0.92);z-index:10000;overflow-y:auto;padding:0.5rem;">
701    <div style="max-width:960px;margin:0 auto;background:#0f0f1e;border-radius:12px;border:1px solid #2a2a4a;overflow:hidden;">
702        <div style="display:flex;justify-content:space-between;align-items:center;padding:1rem 1.5rem;background:linear-gradient(135deg,#1a1a3e,#0d0d2a);border-bottom:1px solid #d4af37;">
703            <h2 id="cf-carta-titulo" style="color:#d4af37;font-family:'Cinzel',serif;font-size:1.1rem;margin:0;">Carta Natal</h2>
704            <button id="cf-btn-cerrar" style="background:none;border:none;color:#eee;font-size:2rem;cursor:pointer;padding:0 0.5rem;">&times;</button>
705        </div>
706        <div style="padding:1rem 1.5rem;">
707            <div style="display:flex;gap:0.5rem;align-items:center;flex-wrap:wrap;margin-bottom:1rem;padding:0.7rem;background:#1a1a3e;border-radius:8px;font-size:0.85rem;">
708                <span style="color:#888;">&#128205;</span>
709                <strong id="cf-ubicacion-texto" style="color:#d4af37;">Detectando...</strong>
710                <button onclick="cfCambiarUbicacion()" style="padding:0.35rem 0.7rem;background:#2a2a4a;border:none;border-radius:4px;color:#ccc;cursor:pointer;font-size:0.8rem;">&#128205; Cambiar</button>
711                <button onclick="cfUsarGPS()" style="padding:0.35rem 0.7rem;background:#2a2a4a;border:none;border-radius:4px;color:#ccc;cursor:pointer;font-size:0.8rem;">&#128752; GPS</button>
712            </div>
713            <div style="display:flex;gap:0.4rem;margin-bottom:1.2rem;flex-wrap:wrap;">
714                <button class="cf-tab-btn" data-tab="cf-carta" style="padding:0.5rem 1rem;background:linear-gradient(135deg,#d4af37,#b8962e);border:1px solid #d4af37;border-radius:6px;color:#0f0f1e;cursor:pointer;font-size:0.85rem;font-weight:600;">&#128302; Carta</button>
715                <button class="cf-tab-btn" data-tab="cf-posiciones" style="padding:0.5rem 1rem;background:#1a1a3e;border:1px solid #2a2a4a;border-radius:6px;color:#ccc;cursor:pointer;font-size:0.85rem;">&#128202; Posiciones</button>
716                <button class="cf-tab-btn" data-tab="cf-aspectos" style="padding:0.5rem 1rem;background:#1a1a3e;border:1px solid #2a2a4a;border-radius:6px;color:#ccc;cursor:pointer;font-size:0.85rem;">&#9889; Aspectos</button>
717                <button class="cf-tab-btn" data-tab="cf-casas" style="padding:0.5rem 1rem;background:#1a1a3e;border:1px solid #2a2a4a;border-radius:6px;color:#ccc;cursor:pointer;font-size:0.85rem;">&#127968; Casas</button>
718                <button class="cf-tab-btn" data-tab="cf-tecnicos" style="padding:0.5rem 1rem;background:#1a1a3e;border:1px solid #2a2a4a;border-radius:6px;color:#ccc;cursor:pointer;font-size:0.85rem;">&#128203; Tecnicos</button>
719                <button class="cf-tab-btn" data-tab="cf-astrocarto" style="padding:0.5rem 1rem;background:#1a1a3e;border:1px solid #2a2a4a;border-radius:6px;color:#ccc;cursor:pointer;font-size:0.85rem;">&#127757; Astrocartografia</button>
720            </div>
721            <div class="cf-tab-content" id="cf-carta" style="display:block;"><div id="cf-astrochart-container" style="display:flex;justify-content:center;overflow:hidden;"></div></div>
722            <div class="cf-tab-content" id="cf-posiciones" style="display:none;"><table id="cf-tabla-planetas" style="width:100%;border-collapse:collapse;font-size:0.9rem;"><thead><tr style="background:#1a1a3e;"><th style="color:#d4af37;padding:0.6rem;text-align:left;">Planeta</th><th style="color:#d4af37;padding:0.6rem;text-align:left;">Signo</th><th style="color:#d4af37;padding:0.6rem;text-align:left;">Grado</th><th style="color:#d4af37;padding:0.6rem;text-align:left;">Long.</th><th style="color:#d4af37;padding:0.6rem;"></th></tr></thead><tbody></tbody></table></div>
723            <div class="cf-tab-content" id="cf-aspectos" style="display:none;"><div id="cf-aspectos-lista"></div></div>
724            <div class="cf-tab-content" id="cf-casas" style="display:none;"><div id="cf-casas-info"></div></div>
725            <div class="cf-tab-content" id="cf-tecnicos" style="display:none;"><div id="cf-datos-tecnicos"></div></div>
726            <div class="cf-tab-content" id="cf-astrocarto" style="display:none;">
727                <div id="cf-astrocarto-map" style="width:100%;height:450px;border-radius:8px;background:#1a2332;"></div>
728                <div id="cf-astrocarto-leyenda" style="display:flex;flex-wrap:wrap;gap:0.6rem;margin-top:0.8rem;padding:0.6rem;background:rgba(0,0,0,0.3);border-radius:6px;font-size:0.78rem;"></div>
729                <div style="margin-top:0.6rem;padding:0.6rem;background:rgba(212,175,55,0.06);border-radius:6px;font-size:0.8rem;color:#888;border-left:3px solid #d4af37;">Las lineas muestran donde cada planeta es angular (ASC subiendo, DSC poniendose, MC culminando, IC en nadir). Tu ubicacion actual esta marcada con &#128205;.</div>
730            </div>
731        </div>
732    </div>
733</div>
734
735    
735<script src="/static/js/carta-fase.js"></script>
735
736
737    
737<script>
738    // Email anti-obfuscation
739    (function(){
740        var e=document.getElementById('email-link');
741        if(e){var u='informes',d='urania.ar';e.textContent=u+'@'+d;e.href='mai'+'lto:'+u+'@'+d;e.onclick=function(){window.location.href=this.href;};}
742    })();
743    </script>
vendor: 1 bytes, line 743
743
744<script src="/static/js/capacitor-fcm-init.js"></script>
744</body>
745</html>

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.