/* ─── Reset ────────────────────────────────────────────────────────────────── */ *, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; } html, body { width: 100%; height: 100%; overflow: hidden; background: #1a1a2e; color: #fff; font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif; user-select: none; -webkit-user-select: none; touch-action: manipulation; -webkit-tap-highlight-color: transparent; } /* ─── Layout ──────────────────────────────────────────────────────────────── */ #app { display: flex; flex-direction: column; height: 100vh; padding: 10px; gap: 8px; } #header { text-align: center; font-size: 13px; color: #888; padding: 2px 0; flex-shrink: 0; letter-spacing: 0.5px; text-transform: uppercase; opacity: 0.7; display: flex; align-items: center; justify-content: center; gap: 8px; } #ws-status { font-size: 10px; transition: color 0.3s; } #ws-status.ws-online { color: #4ade80; } #ws-status.ws-offline { color: #f87171; } #fullscreen-btn { background: none; border: 1px solid #555; color: #888; border-radius: 6px; font-size: 14px; cursor: pointer; padding: 2px 8px; line-height: 1.4; -webkit-tap-highlight-color: transparent; touch-action: manipulation; } #fullscreen-btn:active { background: rgba(255,255,255,0.1); } .button { position: relative; border: none; border-radius: 16px; background: #16213e; color: #fff; font-size: 18px; font-weight: 600; cursor: pointer; display: flex; flex-direction: column; align-items: center; justify-content: center; padding: 10px; transition: all 0.1s ease; box-shadow: 0 3px 12px rgba(0,0,0,0.4); line-height: 1.2; text-align: center; word-break: break-word; overflow: hidden; font-family: inherit; } .button .icon { font-size: 48px; margin-bottom: 6px; line-height: 1; } .button .label { font-size: 16px; opacity: 0.95; max-width: 100%; } /* Pressed state */ .button:active, .button.pressed { transform: scale(0.92); filter: brightness(1.3); } /* Color variants */ .button.color-blue { background: #0f3460; } .button.color-green { background: #1b4332; } .button.color-red { background: #5c1a1a; } .button.color-purple { background: #3b1f6e; } .button.color-orange { background: #5c3a1a; } .button.color-teal { background: #1a4a4a; } .button.color-pink { background: #5c1a3a; } .button.color-yellow { background: #5c4a1a; color: #ffe066; } .button.color-white { background: #2a2a3e; } .button.color-dark { background: #0d0d1a; } /* Transparent (image only) */ .button.color-transparent { background: transparent; box-shadow: none; } .button.color-transparent:active { filter: brightness(1.5); } /* ─── Grid wrapper with side arrows ──────────────────────────────────────── */ #grid-wrapper { position: relative; flex: 1; display: flex; align-items: center; } #grid { flex: 1; display: grid; gap: 10px; align-content: stretch; } .nav-arrow { position: absolute; top: 0; bottom: 0; width: 56px; border: none; background: rgba(255,255,255,0.05); color: rgba(255,255,255,0.35); font-size: 40px; cursor: pointer; display: flex; align-items: center; justify-content: center; z-index: 10; transition: all 0.2s; -webkit-tap-highlight-color: transparent; touch-action: manipulation; padding: 0; } .nav-arrow:active { background: rgba(255,255,255,0.15); color: #fff; } #nav-prev { left: 0; border-radius: 0 10px 10px 0; } #nav-next { right: 0; border-radius: 10px 0 0 10px; } /* ─── Navigation dots ─────────────────────────────────────────────────────── */ #nav { display: flex; justify-content: center; gap: 12px; padding: 8px 0; flex-shrink: 0; } .nav-dot { width: 18px; height: 18px; border-radius: 50%; background: #444; border: 2px solid transparent; cursor: pointer; transition: all 0.2s; padding: 0; -webkit-tap-highlight-color: transparent; touch-action: manipulation; } .nav-dot:active { background: #666; transform: scale(0.9); } .nav-dot.active { background: #4a9eff; border-color: #6bb4ff; box-shadow: 0 0 10px #4a9eff; transform: scale(1.15); } /* ─── Page indicator text ────────────────────────────────────────────────── */ #page-indicator { text-align: center; font-size: 12px; color: #555; padding: 2px 0; flex-shrink: 0; } /* ─── Responsive ──────────────────────────────────────────────────────────── */ /* Ultrawide landscape (e.g. 1920×480) — the touchscreen */ @media (min-aspect-ratio: 3/1) { .button { padding: 10px 14px; } .button .icon { font-size: 48px; } .button .label { font-size: 16px; } #app { padding: 8px 12px; } } /* Small portrait (e.g. 1024×768) */ @media (max-aspect-ratio: 4/3) { .button { border-radius: 20px; } .button .icon { font-size: 56px; } .button .label { font-size: 20px; } } /* ─── Animations ──────────────────────────────────────────────────────────── */ @keyframes flash { 0%, 100% { opacity: 1; } 50% { opacity: 0.5; } } .button.executing { animation: flash 0.3s ease 2; } /* ─── Drag scroll (for pages with many rows) ──────────────────────────────── */ #grid.drag-scroll { overflow-y: auto; scroll-behavior: smooth; flex: 1; } #grid.drag-scroll::-webkit-scrollbar { width: 3px; } #grid.drag-scroll::-webkit-scrollbar-track { background: transparent; } #grid.drag-scroll::-webkit-scrollbar-thumb { background: #555; border-radius: 3px; } /* ─── Monitor dashboard ───────────────────────────────────────────────────── */ #monitor-dashboard { display: grid; grid-template-columns: 1fr 1fr; grid-template-rows: 1fr 1fr; gap: 8px; height: 100%; padding: 4px; } .monitor-section { background: #16213e; border-radius: 12px; padding: 10px 14px; display: flex; flex-direction: column; box-shadow: 0 2px 8px rgba(0,0,0,0.3); } .monitor-title { font-size: 11px; text-transform: uppercase; letter-spacing: 1px; color: #888; margin-bottom: 6px; flex-shrink: 0; } .monitor-bar-bg { height: 20px; background: #0d1b2a; border-radius: 10px; overflow: hidden; flex-shrink: 0; margin-bottom: 4px; } .monitor-bar { height: 100%; border-radius: 10px; transition: width 0.6s ease; } .monitor-bar-cpu { background: linear-gradient(90deg, #4a9eff, #6bb4ff); } .monitor-bar-mem { background: linear-gradient(90deg, #4ade80, #6ee7a0); } .monitor-value { font-size: 20px; font-weight: 700; margin-bottom: 4px; flex-shrink: 0; } /* Per-core bars */ .monitor-cores { display: flex; flex-direction: column; gap: 3px; flex: 1; justify-content: center; margin-top: 4px; } .core-bar-bg { height: 14px; background: #0d1b2a; border-radius: 7px; overflow: hidden; display: flex; align-items: center; position: relative; } .core-label { position: absolute; left: 6px; font-size: 8px; color: #aaa; z-index: 1; font-weight: 600; } .core-bar-fill { height: 100%; border-radius: 7px; background: linear-gradient(90deg, #4a9eff, #7bb8ff); transition: width 0.6s ease; } .core-pct { position: absolute; right: 6px; font-size: 8px; color: #ddd; z-index: 1; } /* System info section */ #monitor-sys { grid-column: 1 / 3; } .monitor-line { font-size: 13px; color: #bbb; padding: 3px 0; flex-shrink: 0; } /* Ultrawide tuning */ @media (min-aspect-ratio: 3/1) { #monitor-dashboard { gap: 6px; padding: 2px; } .monitor-section { padding: 6px 10px; border-radius: 8px; } .monitor-title { font-size: 10px; } .monitor-value { font-size: 16px; } .monitor-bar-bg { height: 16px; } .core-bar-bg { height: 12px; } .monitor-line { font-size: 11px; } }