/* ============================================================================= ProxmoxPanel — Système de design Neumorphism Définit les classes utilitaires et les variables CSS du thème. Utilisé par tous les composants et les modules. ============================================================================= */ /* ── Reset / Base ───────────────────────────────────────────────────────────── */ *, *::before, *::after { box-sizing: border-box; } html, body { margin: 0; padding: 0; font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Inter', sans-serif; font-size: 14px; line-height: 1.5; -webkit-font-smoothing: antialiased; } body { min-height: 100vh; background-color: var(--neu-bg); color: var(--neu-text); } h1, h2, h3, h4, h5, h6 { margin: 0; } p { margin: 0; } a { color: inherit; } button { font-family: inherit; font-size: inherit; } input, select, textarea { font-family: inherit; font-size: inherit; } /* ── Variables CSS (surchargées par dark.css et light.css) ─────────────────── */ :root { /* Couleurs de base */ --neu-bg: #1e2130; --neu-surface: #252838; --neu-text: #e0e4f0; --neu-text-muted: #7f8899; --neu-border: #2e3348; /* Ombres Neumorphism */ --neu-shadow-dark: #161823; --neu-shadow-light: #2a2f48; /* Couleurs d'accent */ --neu-primary: #6c8ef4; --neu-primary-dim: #4a6bd4; --neu-success: #4cbb8a; --neu-warning: #f5a623; --neu-danger: #f05c6b; --neu-info: #3dbfcf; /* Typographie */ --neu-font-xs: 11px; --neu-font-sm: 12px; --neu-font-md: 14px; --neu-font-lg: 16px; --neu-font-xl: 20px; --neu-font-2xl: 24px; /* Espacements */ --neu-space-xs: 4px; --neu-space-sm: 8px; --neu-space-md: 16px; --neu-space-lg: 24px; --neu-space-xl: 32px; /* Rayons */ --neu-radius-sm: 8px; --neu-radius-md: 12px; --neu-radius-lg: 16px; --neu-radius-xl: 24px; --neu-radius-full: 9999px; /* Transitions */ --neu-transition: all 0.2s cubic-bezier(0.4, 0, 0.2, 1); /* Sidebar */ --sidebar-width: 240px; --sidebar-width-collapsed: 64px; /* Z-index */ --z-sidebar: 100; --z-navbar: 200; --z-modal: 300; --z-toast: 400; } /* ── Carte Neumorphism (élévation convexe) ─────────────────────────────────── */ .neu-card { background: var(--neu-surface); border-radius: var(--neu-radius-lg); box-shadow: 6px 6px 12px var(--neu-shadow-dark), -4px -4px 10px var(--neu-shadow-light); border: 1px solid var(--neu-border); padding: var(--neu-space-md); color: var(--neu-text); transition: var(--neu-transition); } .neu-card--flat { box-shadow: none; border: 1px solid var(--neu-border); } .neu-card--hover:hover { box-shadow: 8px 8px 16px var(--neu-shadow-dark), -6px -6px 14px var(--neu-shadow-light); transform: translateY(-1px); } /* ── Surface enfoncée (inputs, zones de saisie) ────────────────────────────── */ .neu-inset { background: var(--neu-bg); border-radius: var(--neu-radius-md); box-shadow: inset 3px 3px 7px var(--neu-shadow-dark), inset -2px -2px 5px var(--neu-shadow-light); border: 1px solid var(--neu-border); } /* ── Boutons ────────────────────────────────────────────────────────────────── */ .neu-btn { display: inline-flex; align-items: center; justify-content: center; gap: var(--neu-space-xs); padding: var(--neu-space-sm) var(--neu-space-md); border-radius: var(--neu-radius-md); font-size: var(--neu-font-md); font-weight: 500; cursor: pointer; border: none; outline: none; transition: var(--neu-transition); text-decoration: none; white-space: nowrap; user-select: none; color: var(--neu-text); background: var(--neu-surface); box-shadow: 4px 4px 8px var(--neu-shadow-dark), -3px -3px 6px var(--neu-shadow-light); } .neu-btn:hover:not(:disabled) { box-shadow: 6px 6px 12px var(--neu-shadow-dark), -4px -4px 8px var(--neu-shadow-light); transform: translateY(-1px); } .neu-btn:active:not(:disabled) { box-shadow: inset 2px 2px 5px var(--neu-shadow-dark), inset -1px -1px 3px var(--neu-shadow-light); transform: translateY(0); } .neu-btn:disabled { opacity: 0.5; cursor: not-allowed; } /* Variantes de boutons */ .neu-btn--primary { background: var(--neu-primary); color: #fff; box-shadow: 4px 4px 8px rgba(0,0,0,0.3), -2px -2px 6px rgba(255,255,255,0.05); } .neu-btn--primary:hover:not(:disabled) { background: var(--neu-primary-dim); box-shadow: 6px 6px 12px rgba(0,0,0,0.4), -3px -3px 8px rgba(255,255,255,0.06); } .neu-btn--success { background: var(--neu-success); color: #fff; } .neu-btn--danger { background: var(--neu-danger); color: #fff; } .neu-btn--warning { background: var(--neu-warning); color: #1a1a2e; } .neu-btn--sm { padding: 4px 10px; font-size: var(--neu-font-sm); border-radius: var(--neu-radius-sm); } .neu-btn--lg { padding: 12px 24px; font-size: var(--neu-font-lg); border-radius: var(--neu-radius-lg); } .neu-btn--icon { width: 40px; height: 40px; padding: 0; border-radius: var(--neu-radius-md); } .neu-btn--ghost { background: transparent; box-shadow: none; border: 1px solid var(--neu-border); } .neu-btn--ghost:hover:not(:disabled) { background: var(--neu-surface); box-shadow: 2px 2px 5px var(--neu-shadow-dark), -1px -1px 3px var(--neu-shadow-light); } /* ── Inputs ─────────────────────────────────────────────────────────────────── */ .neu-input { width: 100%; padding: var(--neu-space-sm) var(--neu-space-md); background: var(--neu-bg); color: var(--neu-text); border: 1px solid var(--neu-border); border-radius: var(--neu-radius-md); font-size: var(--neu-font-md); outline: none; transition: var(--neu-transition); box-shadow: inset 3px 3px 7px var(--neu-shadow-dark), inset -2px -2px 5px var(--neu-shadow-light); } .neu-input:focus { border-color: var(--neu-primary); box-shadow: inset 3px 3px 7px var(--neu-shadow-dark), inset -2px -2px 5px var(--neu-shadow-light), 0 0 0 2px rgba(108, 142, 244, 0.25); } .neu-input::placeholder { color: var(--neu-text-muted); } .neu-input--error { border-color: var(--neu-danger) !important; } /* ── Toggle switch ───────────────────────────────────────────────────────────── */ .neu-toggle { position: relative; display: inline-block; width: 44px; height: 24px; flex-shrink: 0; } .neu-toggle input { opacity: 0; width: 0; height: 0; } .neu-toggle__slider { position: absolute; inset: 0; background: var(--neu-bg); border-radius: var(--neu-radius-full); cursor: pointer; transition: var(--neu-transition); box-shadow: inset 2px 2px 5px var(--neu-shadow-dark), inset -1px -1px 3px var(--neu-shadow-light); } .neu-toggle__slider::before { content: ''; position: absolute; width: 18px; height: 18px; left: 3px; bottom: 3px; background: var(--neu-text-muted); border-radius: 50%; transition: var(--neu-transition); box-shadow: 2px 2px 4px var(--neu-shadow-dark); } .neu-toggle input:checked + .neu-toggle__slider { background: var(--neu-primary); box-shadow: inset 2px 2px 5px rgba(0,0,0,0.3), inset -1px -1px 3px rgba(255,255,255,0.1); } .neu-toggle input:checked + .neu-toggle__slider::before { transform: translateX(20px); background: #fff; } /* ── Badges / Tags ───────────────────────────────────────────────────────────── */ .neu-badge { display: inline-flex; align-items: center; padding: 2px 8px; border-radius: var(--neu-radius-full); font-size: var(--neu-font-xs); font-weight: 600; text-transform: uppercase; letter-spacing: 0.5px; } .neu-badge--success { background: rgba(76, 187, 138, 0.15); color: var(--neu-success); } .neu-badge--danger { background: rgba(240, 92, 107, 0.15); color: var(--neu-danger); } .neu-badge--warning { background: rgba(245, 166, 35, 0.15); color: var(--neu-warning); } .neu-badge--info { background: rgba(61, 191, 207, 0.15); color: var(--neu-info); } .neu-badge--primary { background: rgba(108, 142, 244, 0.15); color: var(--neu-primary); } /* ── Séparateurs ────────────────────────────────────────────────────────────── */ .neu-divider { height: 1px; background: linear-gradient(90deg, transparent, var(--neu-border), transparent); border: none; margin: var(--neu-space-md) 0; } /* ── Utilitaires de layout ──────────────────────────────────────────────────── */ .flex { display: flex; } .flex-col { flex-direction: column; } .items-center { align-items: center; } .justify-between { justify-content: space-between; } .justify-center { justify-content: center; } .gap-sm { gap: var(--neu-space-sm); } .gap-md { gap: var(--neu-space-md); } .gap-lg { gap: var(--neu-space-lg); } .w-full { width: 100%; } .h-full { height: 100%; } /* ── Grid responsive ────────────────────────────────────────────────────────── */ .neu-grid { display: grid; gap: var(--neu-space-md); grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); } /* ── Scrollbar personnalisée ────────────────────────────────────────────────── */ ::-webkit-scrollbar { width: 6px; height: 6px; } ::-webkit-scrollbar-track { background: var(--neu-bg); } ::-webkit-scrollbar-thumb { background: var(--neu-border); border-radius: 3px; } ::-webkit-scrollbar-thumb:hover { background: var(--neu-text-muted); } /* ── Animations ─────────────────────────────────────────────────────────────── */ @keyframes neu-pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.5; } } @keyframes neu-spin { to { transform: rotate(360deg); } } .neu-loading { animation: neu-spin 1s linear infinite; } .neu-pulse { animation: neu-pulse 2s ease-in-out infinite; } /* ── Responsive ─────────────────────────────────────────────────────────────── */ @media (max-width: 768px) { .neu-grid { grid-template-columns: 1fr; } :root { --sidebar-width: 100%; } } /* ── Layout Alpine (sidebar + navbar + page-content) ───────────────────────── */ :root { --navbar-height: 56px; } /* Sidebar (position:fixed, hors flux) */ .sidebar { width: var(--sidebar-width); height: 100vh; background: var(--neu-surface); border-right: 1px solid var(--neu-border); display: flex; flex-direction: column; transition: width 0.2s ease; position: fixed; top: 0; left: 0; z-index: var(--z-sidebar); overflow: hidden; } .sidebar.collapsed { width: var(--sidebar-width-collapsed); } .sidebar-header { display: flex; align-items: center; gap: 0.75rem; padding: 1rem; border-bottom: 1px solid var(--neu-border); min-height: var(--navbar-height); flex-shrink: 0; } .sidebar-logo { font-size: 1.5rem; color: var(--neu-primary); flex-shrink: 0; } .sidebar-title { font-weight: 700; font-size: 1rem; white-space: nowrap; overflow: hidden; color: var(--neu-text); } .sidebar-toggle { margin-left: auto; flex-shrink: 0; } .sidebar-nav { flex: 1; padding: 0.5rem; display: flex; flex-direction: column; gap: 0.25rem; overflow-y: auto; overflow-x: hidden; } .sidebar-link { display: flex; align-items: center; gap: 0.75rem; padding: 0.625rem 0.75rem; border-radius: var(--neu-radius-sm); text-decoration: none; color: var(--neu-text-muted); font-size: 0.875rem; font-weight: 500; transition: all 0.15s; white-space: nowrap; overflow: hidden; } .sidebar-link:hover { background: rgba(108, 142, 244, 0.08); color: var(--neu-text); } .sidebar-link.active { background: rgba(108, 142, 244, 0.15); color: var(--neu-primary); } .sidebar-icon { display: flex; align-items: center; justify-content: center; font-size: 1.2rem; flex-shrink: 0; width: 1.25rem; line-height: 1; } .sidebar-label { overflow: hidden; text-overflow: ellipsis; } .sidebar-footer { padding: 0.75rem; border-top: 1px solid var(--neu-border); display: flex; align-items: center; gap: 0.5rem; flex-shrink: 0; } .sidebar-user { flex: 1; font-size: 0.8rem; color: var(--neu-text-muted); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; } /* Main layout (marge pour compenser le sidebar fixe) */ .main-layout { display: flex; flex-direction: column; min-height: 100vh; margin-left: var(--sidebar-width); transition: margin-left 0.2s ease; } .sidebar.collapsed ~ .main-layout { margin-left: var(--sidebar-width-collapsed); } /* Navbar */ .navbar { height: var(--navbar-height); display: flex; align-items: center; justify-content: space-between; padding: 0 1.5rem; border-bottom: 1px solid var(--neu-border); background: var(--neu-bg); flex-shrink: 0; position: sticky; top: 0; z-index: var(--z-navbar); } .navbar-title { font-size: 1rem; font-weight: 700; margin: 0; color: var(--neu-text); } .navbar-actions { display: flex; align-items: center; gap: 0.5rem; } /* Page content */ .page-content { flex: 1; padding: 1.5rem; overflow-y: auto; background: var(--neu-bg); color: var(--neu-text); } /* Auth layout (login, install) */ .auth-layout { min-height: 100vh; width: 100%; display: flex; align-items: center; justify-content: center; padding: 1rem; background: var(--neu-bg); } /* Swup fade transition */ .transition-fade { transition: opacity 0.2s ease; } html.is-animating .transition-fade { opacity: 0; } /* Responsive */ @media (max-width: 768px) { .sidebar { width: var(--sidebar-width-collapsed); } .main-layout { margin-left: var(--sidebar-width-collapsed); } } [x-cloak] { display: none !important; } /* ── Sidebar droite ─────────────────────────────────────────────────────────── */ [data-sidebar="right"] .sidebar { left: auto; right: 0; border-right: none; border-left: 1px solid var(--neu-border); } [data-sidebar="right"] .main-layout { margin-left: 0; margin-right: var(--sidebar-width); transition: margin-right 0.2s ease; } [data-sidebar="right"] .sidebar.collapsed ~ .main-layout { margin-right: var(--sidebar-width-collapsed); } @media (max-width: 768px) { [data-sidebar="right"] .main-layout { margin-right: var(--sidebar-width-collapsed); } }