/* =============================================================================
 * manual.css — Pantalla manual con visor 3D y faceplates de devices
 * F2R Engineering
 *
 * Estructura:
 *   - Sidebar de devices (lista a la izquierda)
 *   - Visor 3D (centro)
 *   - Hotspots flotantes sobre el modelo
 *   - Popup flotante con el faceplate del device seleccionado
 *
 * REGLAS:
 *   - Colores estructurales (fondos, bordes, textos): variables del
 *     design system. Cambian con body.light-mode automáticamente.
 *   - Colores ilustrativos (pistón animado, válvulas, gradientes
 *     metálicos): hardcoded a propósito — son arte, no UI.
 *   - Estados de máquina (ok/fault/moving/warning/undef): variables
 *     semánticas del design system.
 * ============================================================================= */

/* ── Layout principal ────────────────────────────────────────────────────── */
body {
  margin: 0;
  display: flex;
  flex-direction: column;
  height: 100vh;
  width: 100vw;
  font-family: var(--font-main);
  background: var(--surface-base);
  color: var(--text-primary);
  overflow: hidden;
}

#main-content {
  display: flex;
  flex: 1;
  overflow: hidden;
}

/* ── Sidebar de devices ──────────────────────────────────────────────────── */
#sidebar {
  width: 280px;
  background: var(--surface-raised);
  border-right: 1px solid var(--border-base);
  display: flex;
  flex-direction: column;
  z-index: 10;
}
#sidebar h2 {
  padding: var(--space-3) var(--space-5);
  font-size: var(--fs-sm);
  background: var(--surface-base);
  margin: 0;
  text-align: center;
  border-bottom: 1px solid var(--border-base);
  letter-spacing: 1.5px;
  text-transform: uppercase;
  color: var(--text-secondary);
}
#item-list {
  flex: 1;
  overflow-y: auto;
  padding: var(--space-4);
}

.item-btn {
  width: 100%;
  padding: var(--space-3) var(--space-4);
  margin-bottom: var(--space-2);
  background: var(--surface-overlay);
  border: 1px solid var(--border-base);
  color: var(--text-primary);
  cursor: pointer;
  border-radius: var(--radius-md);
  border-left: 4px solid var(--accent);
  text-align: left;
  transition: var(--transition-base);
  font-family: var(--font-main);
  font-size: var(--fs-base);
}
.item-btn:hover {
  background: var(--surface-elevated);
  box-shadow: var(--shadow-glow-accent);
}
.item-btn.active {
  background: var(--surface-elevated);
  color: var(--accent);
  border-left-width: 6px;
  box-shadow: inset 0 0 15px var(--accent-soft);
}

/* ── Visor 3D ────────────────────────────────────────────────────────────── */
#viewer-container {
  flex: 1;
  position: relative;
  background: var(--surface-base);
  overflow: hidden;
}
model-viewer {
  width: 100%;
  height: 100%;
  outline: none;
}

.nodo-dot {
  width: 18px;
  height: 18px;
  background-color: transparent;
  border: 2px solid var(--accent);
  border-radius: 50%;
  box-shadow: var(--shadow-glow-accent);
  cursor: pointer;
  transform: translate(-50%, -50%);
  transition: var(--transition-slow);
  pointer-events: auto;
}
.nodo-dot::after {
  content: '';
  position: absolute;
  top: 50%;
  left: 50%;
  width: 6px;
  height: 6px;
  background: var(--accent);
  border-radius: 50%;
  transform: translate(-50%, -50%);
}
.nodo-dot:hover {
  transform: translate(-50%, -50%) scale(1.5);
  box-shadow: 0 0 25px var(--accent);
  background: var(--accent-soft);
}

#loading-overlay {
  position: absolute;
  top: 0; left: 0;
  width: 100%; height: 100%;
  background-color: var(--surface-base);
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  /* Por debajo de los popups globales (--z-overlay=1500, --z-modal=2000)
     para que abrir un popup mientras carga el GLB no quede tapado.
     La UI local dentro del visor (.station-banners, .prod-overlay-info,
     hotspots…) llega a z=10, así que 50 sobra para cubrirla. */
  z-index: 50;
  color: var(--accent);
  transition: opacity 0.5s ease;
  pointer-events: none;
}
.spinner-3d {
  width: 60px;
  height: 60px;
  margin-bottom: var(--space-5);
  border: 3px solid var(--accent-soft);
  border-top: 3px solid var(--accent);
  border-radius: 50%;
  animation: spin-3d 1s linear infinite;
  box-shadow: var(--shadow-glow-accent);
}
@keyframes spin-3d {
  0%   { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
}

/* =============================================================================
 * VENTANA FLOTANTE POPUP (contenedor del faceplate)
 * ============================================================================= */
.hmi-float-window {
  display: none;
  position: absolute;
  top: 20px;
  right: 20px;
  width: 440px;
  z-index: var(--z-modal);
  opacity: 0;
  pointer-events: none;
}
.hmi-float-window.active {
  display: block;
  opacity: 1;
}

/* Compat: el cuerpo del faceplate. La clase canónica es .faceplate (del
 * design system) y device-base la aplica también. .popup-faceplate se
 * mantiene como alias por si algún device legacy todavía la usa. */
.popup-faceplate,
.hmi-float-window > .faceplate {
  pointer-events: auto;
  margin: 0;
  width: 100%;
  box-sizing: border-box;
  padding: var(--space-6);
  border-radius: var(--radius-xl);
  border: 1px solid var(--border-base);
  background: var(--surface-raised);
  box-shadow: var(--shadow-xl);
  color: var(--text-primary);
  position: relative;
  transform: translateY(20px) scale(0.95);
  transition: all 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275);
}
.hmi-float-window.active .popup-faceplate,
.hmi-float-window.active > .faceplate {
  transform: translateY(0) scale(1);
}

/* Header legacy del popup (alias de .faceplate-header del design system) */
.popup-header {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  padding-bottom: var(--space-4);
  margin-bottom: var(--space-5);
  border-bottom: 1px solid var(--border-subtle);
}
.popup-title { display: flex; flex-direction: column; }
.popup-title .lbl {
  font-size: var(--fs-xs);
  color: var(--text-muted);
  letter-spacing: 1px;
  text-transform: uppercase;
  font-weight: var(--fw-bold);
}
.popup-title .val {
  font-size: var(--fs-xl);
  font-weight: var(--fw-black);
  color: var(--text-primary);
  margin-top: 2px;
}

/* =============================================================================
 * VISUAL DEL CILINDRO (geometría exacta — arte ilustrativo)
 * Los gradientes metálicos del pistón y los gradientes de las válvulas son
 * arte, no UI. Se mantienen hardcoded en ambos modos.
 * ============================================================================= */
.cylinder-visual-container {
  background: var(--surface-base);
  border: 1px solid var(--border-base);
  border-radius: var(--radius-xl);
  padding: 30px var(--space-5) var(--space-5);
  margin-bottom: var(--space-5);
  display: flex;
  flex-direction: column;
  align-items: center;
}

.cylinder-wrapper {
  position: relative;
  width: 240px;
  height: 40px;
  margin-top: 15px;
  margin-bottom: 25px;
}

.cylinder-shell {
  position: absolute;
  top: 0; left: 10px;
  width: 140px;
  height: 100%;
  border: 2px solid var(--neutral-700);
  border-radius: 6px;
  background: rgba(255,255,255,0.05);
  z-index: 3;
  pointer-events: none;
}
.cylinder-shell::before,
.cylinder-shell::after {
  content: '';
  position: absolute;
  top: -5px;
  width: 12px;
  height: 46px;
  background: linear-gradient(90deg, var(--color-neutral-hover), var(--neutral-300));
  border-radius: 4px;
  border: 2px solid var(--neutral-700);
}
.cylinder-shell::before { left: -8px; }
.cylinder-shell::after { right: -8px; }

.moving-part {
  position: absolute;
  left: 15px;
  top: 4px;
  display: flex;
  align-items: center;
  z-index: 2;
  transition: transform 0.6s cubic-bezier(0.175, 0.885, 0.32, 1.275);
}
.pos-home  { transform: translateX(0px); }
.pos-work  { transform: translateX(95px); }
.pos-undef { transform: translateX(45px); }

.piston-head {
  width: 22px; height: 32px;
  background: linear-gradient(90deg, var(--color-neutral-hover), var(--neutral-300));
  border-radius: 4px;
  box-shadow: 2px 0 5px rgba(0,0,0,0.5);
}
.piston-rod {
  width: 100px; height: 14px;
  background: linear-gradient(180deg, var(--neutral-100), var(--color-neutral));
  box-shadow: inset 0 -2px 5px rgba(0,0,0,0.3);
}
.piston-clevis {
  width: 12px; height: 24px;
  background: var(--color-success-strong);
  border-radius: 2px;
}

/* Válvulas */
.valve-assembly {
  position: absolute;
  top: -25px;
  display: flex;
  flex-direction: column;
  align-items: center;
  z-index: 4;
}
.valve-w { left: 25px; }
.valve-h { left: 135px; }

.air-pipe {
  width: 6px; height: 10px;
  background: #555;
  border: 1px solid #111;
  border-bottom: none;
}
.port {
  width: 20px; height: 14px;
  background: #222;
  border: 1px solid #555;
  border-radius: 2px;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: calc(9px * var(--font-scale));
  font-weight: bold;
  color: #888;
  transition: var(--transition-slow);
  margin-top: -1px;
}

/* Flujo de aire iluminado */
.flow-in .port {
  background: var(--color-moving);
  border-color: #fff;
  box-shadow: 0 0 10px var(--color-moving);
  color: #fff;
}
.flow-in .air-pipe {
  background: var(--color-moving);
  box-shadow: 0 0 10px var(--color-moving);
  border-color: var(--color-moving);
}
.flow-out .port {
  background: rgba(52, 152, 219, 0.2);
  border-color: rgba(52, 152, 219, 0.5);
  color: var(--color-moving);
}

/* Sensores físicos */
.phys-sensor {
  position: absolute;
  bottom: -20px;
  width: 16px;
  height: 16px;
  background: #222;
  border: 2px solid var(--color-warning-strong);
  border-radius: 2px;
  transition: var(--transition-base);
  z-index: 5;
}
.phys-sensor-home { left: 25px; }
.phys-sensor-work { left: 210px; }
.phys-sensor.on {
  background: var(--color-warning-strong);
  border-color: #fff;
  box-shadow: 0 0 10px var(--color-warning-strong);
}

/* Indicadores LED de sensores (debajo del cilindro) */
.sensors-row {
  display: flex;
  justify-content: space-around;
  width: 100%;
  margin-top: var(--space-3);
}
.sensor-item {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  color: var(--text-secondary);
  font-weight: var(--fw-bold);
  font-size: var(--fs-sm);
  letter-spacing: 1px;
}
.led-indicator {
  width: 16px;
  height: 16px;
  border-radius: 50%;
  background: var(--surface-overlay);
  border: 2px solid var(--border-strong);
  transition: var(--transition-slow);
}
.led-indicator.on {
  background: var(--color-warning-strong);
  border-color: #fff;
  box-shadow: 0 0 12px var(--color-warning-strong);
}

/* =============================================================================
 * VISOR DE ESTADO (la caja con icono coloreado + ESTADO ACTUAL)
 * Los estados (ok/fault/moving/warning/undef) usan colores semánticos del
 * design system, así que cambian de tono entre dark y light automáticamente.
 * ============================================================================= */
.status-visor {
  display: flex;
  align-items: center;
  gap: var(--space-4);
  padding: var(--space-4) var(--space-5);
  border-radius: var(--radius-lg);
  background: var(--surface-base);
  border: 1px solid var(--border-base);
  margin-bottom: var(--space-5);
}
.status-icon-box {
  width: 40px;
  height: 40px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  color: #fff;                /* contraste sobre el background coloreado */
  transition: var(--transition-slow);
  font-size: calc(24px * var(--font-scale));            /* tamaño del icono dentro */
}
.status-icon-box svg {
  width: 24px;
  height: 24px;
  stroke: currentColor;
  stroke-width: 2.5;
}
.status-text-box { display: flex; flex-direction: column; }
.status-text-box .lbl {
  font-size: var(--fs-xs);
  color: var(--text-muted);
  text-transform: uppercase;
  letter-spacing: 1px;
  margin-bottom: 3px;
}
.status-text-box .val {
  font-size: var(--fs-lg);
  font-weight: var(--fw-bold);
  font-family: var(--font-main);
  letter-spacing: 1px;
  color: var(--text-primary);
}

/* Estados — usan colores semánticos */
.state-ok           { border-color: var(--color-success-strong); box-shadow: inset 0 0 10px var(--color-success-soft); }
.state-ok      .status-icon-box { background: var(--color-success-strong); box-shadow: 0 0 15px var(--color-success-soft); }
.state-fault        { border-color: var(--color-danger);  box-shadow: inset 0 0 10px var(--color-danger-soft); }
.state-fault   .status-icon-box { background: var(--color-danger); box-shadow: 0 0 15px var(--color-danger-soft); }
.state-moving       { border-color: var(--color-moving); box-shadow: inset 0 0 10px rgba(52,152,219,0.1); }
.state-moving  .status-icon-box { background: var(--color-moving); box-shadow: 0 0 15px rgba(52,152,219,0.5); }
.state-warning      { border-color: var(--color-warning); }
.state-warning .status-icon-box { background: var(--color-warning); color: var(--text-inverse); }
.state-undef        { border-color: var(--border-strong); }
.state-undef   .status-icon-box { background: var(--border-strong); }

/* =============================================================================
 * MODO CLARO — overrides específicos
 *
 * El design system ya redefine los tokens (--surface-X, --text-X, etc.)
 * en body.light-mode. Como manual.css ahora usa esos tokens en todos los
 * elementos estructurales, la mayor parte del modo claro funciona solo.
 *
 * Aquí solo reaccionamos en sitios donde necesitamos un ajuste fino:
 * elementos con colores hardcoded que cambian de comportamiento entre
 * modos (sombras, glows, mezclas).
 * ============================================================================= */

body.light-mode .cylinder-visual-container {
  background: var(--surface-overlay);
}

body.light-mode .cylinder-shell {
  background: rgba(0, 0, 0, 0.04);
}

body.light-mode .status-visor {
  background: var(--surface-overlay);
}

body.light-mode .status-text-box .val {
  color: var(--text-primary);
}

/* En modo claro las luces de estado tienen menos brillo (no hace falta
 * tanto glow contra un fondo claro) */
body.light-mode .state-ok      { box-shadow: inset 0 0 8px rgba(46, 204, 113, 0.15); }
body.light-mode .state-fault   { box-shadow: inset 0 0 8px rgba(216, 59, 78, 0.15); }
body.light-mode .state-moving  { box-shadow: inset 0 0 8px rgba(52, 152, 219, 0.15); }
