/* ──────────────────────────────────────────────────────────────────────────────
   RouterMate Theme — "Signal" Design System
   A flat, professional, no-shadow theme built on a Paper & Ink neutral base
   with a Deep Teal primary, Signal Cyan highlight, and Rust warm accent —
   a technical, editorial palette.
   Loaded after dashlite.css + theme.css — acts as the single source of truth
   for brand color and enforces a shadow-free visual language across the app.
   ────────────────────────────────────────────────────────────────────────────── */

:root {
    /* Brand */
    --color-primary: #0F5C5C;
    --color-primary-dark: #0B4545;
    --color-primary-darker: #083333;
    --color-primary-light: #3ED6C4;
    --color-primary-soft: #E9F4F3;

    --color-accent: #C4633B;
    --color-accent-dark: #9A4E2E;
    --color-accent-soft: #F8EDE7;

    /* Signal Cyan — highlights, hover states, active/live indicators */
    --color-signal: #3ED6C4;
    --color-signal-soft: #E5FAF7;

    /* Status */
    --color-success: #15803d;
    --color-success-soft: #EAF7EF;
    --color-warning: #C4633B;
    --color-warning-soft: #F8EDE7;
    --color-danger: #b91c1c;
    --color-danger-soft: #FBEAE9;
    --color-info: #0369a1;
    --color-info-soft: #EAF3FA;

    /* Neutrals — Paper & Ink scale */
    --color-dark: #1C1D21;
    --color-gray-900: #1C1D21;
    --color-gray-800: #26272C;
    --color-gray-700: #3B3C42;
    --color-gray-600: #53555C;
    --color-gray-500: #6B6D73;
    --color-gray-400: #8D8F95;
    --color-gray-300: #B7B5AC;
    --color-gray-200: #D4D2C9;
    --color-gray-100: #EDEBE3;
    --color-gray-50: #FAF9F6;
    --color-light: #ffffff;

    /* Gradients (flat color transitions — not shadows) */
    --gradient-primary: linear-gradient(135deg, #0F5C5C 0%, #0B4545 100%);
    --gradient-accent: linear-gradient(135deg, #C4633B 0%, #9A4E2E 100%);
    --gradient-dark: linear-gradient(160deg, #1C1D21 0%, #26272C 100%);

    /* Shadows — intentionally disabled everywhere. Kept as tokens so any
       component still referencing var(--shadow-*) resolves to no shadow
       instead of an undefined value. Do not reintroduce blur/offset values. */
    --shadow-xs: none;
    --shadow-sm: none;
    --shadow-md: none;
    --shadow-lg: none;
    --shadow-xl: none;

    /* Radius */
    --radius-xs: 4px;
    --radius-sm: 6px;
    --radius-md: 8px;
    --radius-lg: 10px;
    --radius-xl: 14px;

    /* Spacing */
    --spacing-xs: 4px;
    --spacing-sm: 8px;
    --spacing-md: 12px;
    --spacing-lg: 16px;
    --spacing-xl: 24px;
    --spacing-2xl: 32px;

    /* Typography — Inter carries body/UI text, Baloo 2 carries headings,
       page titles, card titles, and sidebar nav labels (see the h1-h6 rule
       below and the Sidebar section for where each is applied). */
    --font-sans: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
    --font-heading: "Baloo 2", "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
    --font-mono: "Monaco", "Courier New", monospace;

    /* Transitions — color/border only, no elevation transforms */
    --transition-fast: 150ms cubic-bezier(0.4, 0, 0.2, 1);
    --transition-base: 200ms cubic-bezier(0.4, 0, 0.2, 1);
    --transition-slow: 300ms cubic-bezier(0.4, 0, 0.2, 1);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Base Styles
   ────────────────────────────────────────────────────────────────────────────── */

body {
    background-color: var(--color-gray-50);
    color: var(--color-gray-900);
    font-family: var(--font-sans);
    font-size: 14px;
    line-height: 1.6;
}

body.dark {
    background-color: var(--color-gray-900);
    color: var(--color-gray-200, #D4D2C9);
}

a {
    color: var(--color-primary);
}

a:hover {
    color: var(--color-primary-dark);
}

.text-primary,
.text-primary-alt {
    color: var(--color-primary) !important;
}

.bg-primary {
    background-color: var(--color-primary) !important;
}

/* Headings — dashlite.css hard-codes `font-family: Nunito` on the grouped
   h1..h6/.h1..h6 selector (and Roboto on body text). Same specificity,
   later source, so this is enough to win without !important. */
h1, h2, h3, h4, h5, h6,
.h1, .h2, .h3, .h4, .h5, .h6,
.card-title,
.nk-block-title,
.nk-block-title-group .title {
    font-family: var(--font-heading);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Cards — flat, bordered, no elevation
   ────────────────────────────────────────────────────────────────────────────── */

.card {
    background: var(--color-light);
    border: 1px solid var(--color-gray-200);
    border-radius: var(--radius-lg);
    box-shadow: none;
    transition: border-color var(--transition-base), background-color var(--transition-base);
}

.card:hover {
    border-color: var(--color-gray-300);
}

.card.is-dark {
    background: var(--color-gray-800);
    border-color: var(--color-gray-700);
    color: var(--color-gray-200, #D4D2C9);
}

.card-inner {
    padding: var(--spacing-xl);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Stat Cards — bordered instead of shadowed, subtle hover via border only
   ────────────────────────────────────────────────────────────────────────────── */

.stat-card {
    display: flex;
    align-items: center;
    gap: var(--spacing-lg);
    padding: var(--spacing-xl);
    background: var(--color-light);
    border: 1px solid var(--color-gray-200);
    border-radius: var(--radius-lg);
    border-left: 4px solid var(--color-primary);
    box-shadow: none;
    transition: border-color var(--transition-base);
}

.stat-card:hover {
    border-color: var(--color-primary-light);
}

.stat-card.success { border-left-color: var(--color-success); }
.stat-card.warning { border-left-color: var(--color-warning); }
.stat-card.danger { border-left-color: var(--color-danger); }

.stat-icon {
    width: 56px;
    height: 56px;
    display: flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--radius-lg);
    font-size: 24px;
    flex-shrink: 0;
}

.stat-icon.primary { background: var(--color-primary-soft); color: var(--color-primary); }
.stat-icon.success { background: var(--color-success-soft); color: var(--color-success); }
.stat-icon.warning { background: var(--color-warning-soft); color: var(--color-warning); }
.stat-icon.danger  { background: var(--color-danger-soft); color: var(--color-danger); }

.stat-content h3 {
    margin: 0 0 var(--spacing-xs) 0;
    font-size: 12px;
    font-weight: 600;
    color: var(--color-gray-600);
    text-transform: uppercase;
    letter-spacing: 0.5px;
}

.stat-content .value {
    font-family: var(--font-heading);
    font-size: 24px;
    font-weight: 700;
    color: var(--color-dark);
}

.stat-content .value.dark { color: var(--color-light); }

.stat-content .subtitle {
    font-size: 12px;
    color: var(--color-gray-500);
    margin-top: var(--spacing-xs);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Buttons — flat, color-driven interaction (no shadow lift)
   ────────────────────────────────────────────────────────────────────────────── */

.btn {
    /* dashlite.css drives .btn's font off --bs-btn-font-family, which it
       sets to Nunito — override explicitly so buttons stay on the body
       font (Inter) rather than inheriting the heading font. */
    font-family: var(--font-sans);
    border-radius: var(--radius-md);
    font-weight: 600;
    font-size: 14px;
    padding: 10px 16px;
    transition: background-color var(--transition-fast), border-color var(--transition-fast), color var(--transition-fast);
    border: 1px solid transparent;
    cursor: pointer;
    box-shadow: none !important;
}

.btn:focus-visible {
    outline: 2px solid var(--color-primary-light);
    outline-offset: 2px;
}

.btn-primary {
    background: var(--color-primary);
    border-color: var(--color-primary);
    color: #fff;
}

.btn-primary:hover {
    background: var(--color-primary-dark);
    border-color: var(--color-primary-dark);
    color: #fff;
}

.btn-accent {
    background: var(--color-accent);
    border-color: var(--color-accent);
    color: #fff;
}

.btn-accent:hover {
    background: var(--color-accent-dark);
    border-color: var(--color-accent-dark);
    color: #fff;
}

.btn-success { background: var(--color-success); border-color: var(--color-success); color: #fff; }
.btn-success:hover { background: #116329; border-color: #116329; }

.btn-outline-primary {
    background: transparent;
    border: 1px solid var(--color-primary);
    color: var(--color-primary);
}

.btn-outline-primary:hover {
    background: var(--color-primary-soft);
}

.btn-white {
    background: #fff;
    border-color: #fff;
    color: var(--color-primary);
}

.btn-white:hover {
    background: var(--color-gray-100);
    border-color: var(--color-gray-100);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Badges
   ────────────────────────────────────────────────────────────────────────────── */

.badge {
    display: inline-block;
    padding: 4px 12px;
    border-radius: 20px;
    font-size: 12px;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.3px;
}

.badge-success { background: var(--color-success-soft); color: var(--color-success); }
.badge-warning { background: var(--color-warning-soft); color: var(--color-accent-dark); }
.badge-danger  { background: var(--color-danger-soft); color: var(--color-danger); }
.badge-info    { background: var(--color-info-soft); color: var(--color-info); }
.badge-primary { background: var(--color-primary-soft); color: var(--color-primary); }

/* ──────────────────────────────────────────────────────────────────────────────
   Loading & Empty States
   ────────────────────────────────────────────────────────────────────────────── */

.empty-state {
    text-align: center;
    padding: var(--spacing-2xl);
    color: var(--color-gray-500);
}

.empty-state-icon {
    font-size: 48px;
    margin-bottom: var(--spacing-lg);
    opacity: 0.5;
}

.empty-state h3 {
    margin: 0 0 var(--spacing-sm) 0;
    color: var(--color-gray-700);
    font-size: 16px;
}

.loading-spinner {
    display: inline-block;
    width: 16px;
    height: 16px;
    border: 2px solid var(--color-primary-soft);
    border-top-color: var(--color-primary);
    border-radius: 50%;
    animation: spin 0.6s linear infinite;
}

@keyframes spin {
    to { transform: rotate(360deg); }
}

/* ──────────────────────────────────────────────────────────────────────────────
   Table Enhancements — bordered, not shadowed
   ────────────────────────────────────────────────────────────────────────────── */

.table-wrapper {
    border-radius: var(--radius-lg);
    border: 1px solid var(--color-gray-200);
    overflow: hidden;
    box-shadow: none;
}

.table {
    border-collapse: collapse;
    width: 100%;
}

.table thead th {
    background: var(--color-gray-50);
    color: var(--color-gray-700);
    font-weight: 700;
    padding: 12px 16px;
    text-align: left;
    border-bottom: 1px solid var(--color-gray-200);
    font-size: 12px;
    text-transform: uppercase;
    letter-spacing: 0.5px;
}

.table tbody td {
    padding: 16px;
    border-bottom: 1px solid var(--color-gray-100);
}

.table tbody tr:hover {
    background: var(--color-gray-50);
}

.table.dark thead th {
    background: var(--color-gray-800);
    color: var(--color-gray-300);
    border-bottom-color: var(--color-gray-700);
}

.table.dark tbody tr:hover {
    background: var(--color-gray-800);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Sidebar layout
   The vendored dashlite.css bundle here is the top-nav variant of the
   template — it ships zero position/width rules for .nk-sidebar (only
   color rules, in dark-mode selectors). The tenant layout's markup
   (.nk-app-root > .nk-sidebar + .nk-wrap) assumes the classic fixed-left-
   sidebar layout, so without this the sidebar is just a full-width block
   div stacking above the content instead of a column beside it. This
   block supplies that missing structural layout, matching the same
   fixed-sidebar + offset-content pattern already used in the admin panel.
   ────────────────────────────────────────────────────────────────────────────── */

:root {
    --tenant-sidebar-width: 260px;
}

.tenant-layout-shell {
    display: flex;
    min-height: 100vh;
}

.tenant-layout .nk-sidebar,
.tenant-layout .nk-sidebar-fixed {
    background: var(--color-light);
    border-right: 1px solid var(--color-gray-200);
    box-shadow: none;
    width: var(--tenant-sidebar-width) !important;
    min-width: var(--tenant-sidebar-width) !important;
    position: fixed !important;
    top: 0 !important;
    left: 0 !important;
    height: 100vh !important;
    z-index: 1050;
    display: flex;
    flex-direction: column;
    overflow: hidden;
    transition: transform var(--transition-base);
}

.tenant-layout .nk-sidebar-fixed {
    transform: translateX(-100%);
}

.nk-sidebar-element {
    display: flex;
    flex-direction: column;
}

.nk-sidebar-element:last-child {
    flex: 1;
    min-height: 0;
}

.nk-sidebar-head {
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: space-between;
    height: 65px;
    min-height: 65px;
    flex-shrink: 0;
    padding: 0 20px;
    border-bottom: 1px solid var(--color-gray-100);
}

.nk-sidebar-brand {
    display: flex;
    align-items: center;
    min-width: 0;
}

.nk-sidebar-brand .nk-sidebar-logo {
    display: flex;
    align-items: center;
    position: relative;
}

.nk-sidebar-head .nk-menu-trigger {
    flex-shrink: 0;
    margin-left: 12px;
}

.nk-sidebar-content {
    flex: 1;
    min-height: 0;
    display: flex;
    flex-direction: column;
}

.nk-sidebar-menu {
    flex: 1;
    overflow-y: auto;
    padding: 12px 0 24px;
}

.nk-wrap {
    min-width: 0;
}

.nk-header {
    background: var(--color-light);
    border-bottom: 1px solid var(--color-gray-200);
}

.nk-header-fixed {
    position: sticky;
    top: 0;
    z-index: 999;
}

/* Desktop (xl and up): sidebar is always visible, content offsets beside it. */
@media (min-width: 1200px) {
    .tenant-layout .nk-sidebar-fixed {
        transform: translateX(0);
    }

    .tenant-layout .nk-wrap {
        margin-left: var(--tenant-sidebar-width) !important;
        flex: 1;
        min-width: 0;
    }
}

/* Below xl: sidebar is off-canvas, opened via the hamburger trigger
   (scripts.js toggles `.mobile-menu` on the sidebar and `.nav-shown` on
   body — same convention the admin panel already uses). */
@media (max-width: 1199.98px) {
    .tenant-layout .nk-sidebar-fixed.mobile-menu {
        transform: translateX(0);
    }

    .tenant-layout .nk-wrap {
        margin-left: 0 !important;
    }

    body.nav-shown {
        overflow: hidden;
    }

    .nk-sidebar-overlay {
        display: none;
        position: fixed;
        inset: 0;
        background: rgba(28, 25, 23, 0.5);
        z-index: 1040;
    }

    body.nav-shown .nk-sidebar-overlay {
        display: block;
    }
}

/* ── Menu — sizing, color, and a second, hidden problem ──────────────────
   dashlite.css bundles TWO menu skins under the same class names
   (.nk-menu/.nk-menu-link/.nk-menu-sub etc.): the vertical sidebar skin
   (unconditional rules) and a horizontal top-nav skin gated behind
   `@media (min-width: 992px)` — meant for a different layout variant, but
   since it targets the same classes it still matches our sidebar markup
   at desktop widths. Several of those top-nav rules out-specificity the
   plain sidebar overrides below (e.g. `.nk-menu > li.nk-menu-item > .nk-
   menu-link` beats a bare `.nk-menu-link`), and one — `.nk-menu .nk-menu-
   sub { display: block !important; position: absolute; opacity: 0; }` —
   turns our click-to-expand accordion into an invisible hover flyout and
   hides `.nk-menu-icon` outright (`display: none`) above 992px. Every
   selector below is deliberately scoped with `.nk-sidebar` and, where
   needed, matched or exceeded in specificity (or !important, where the
   vendor rule itself uses !important) so it wins regardless of viewport
   width, without touching dashlite.css. */

/* The container itself has the same problem: dashlite's top-nav skin sets
   `.nk-menu { padding: 0 1.5rem 0 2rem; }` at >=992px (a 32px left inset
   meant for the horizontal bar's own centering), on top of dashlite's
   unconditional `.nk-menu { padding-top: 0.75rem; }`. .nk-sidebar-menu
   above already owns the vertical spacing, so zero this out entirely —
   otherwise every row (headings most visibly, since they have no icon to
   visually anchor the extra gap) sits ~32px further right than intended. */
.nk-sidebar .nk-menu {
    padding: 0;
}

.nk-sidebar .nk-menu-item {
    margin-bottom: 0;
    position: relative;
}

/* Alignment matches the admin panel's .sidebar-link exactly: zero
   container padding (above), 20px built entirely into the link's own
   padding, flush edge-to-edge rows (no rounded pill inset), and a 3px
   left accent border on the active row instead of a framed background. */
.nk-sidebar .nk-menu-item .nk-menu-link,
.nk-sidebar .nk-menu > .nk-menu-item > .nk-menu-link {
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 9px 20px;
    color: var(--color-gray-600);
    text-decoration: none;
    border-radius: 0;
    transition: background-color var(--transition-fast), color var(--transition-fast);
    font-family: var(--font-heading);
    font-size: 14px;
    font-weight: 600;
    letter-spacing: normal;
    line-height: 1.4;
    text-transform: none;
    position: relative;
}

.nk-sidebar .nk-menu-item .nk-menu-link:hover,
.nk-sidebar .nk-menu-item.active > .nk-menu-link {
    color: var(--color-primary-dark);
    background: var(--color-primary-soft);
}

.nk-sidebar .nk-menu-item.active > .nk-menu-link:after {
    content: '';
    position: absolute;
    left: 0;
    top: 0;
    bottom: 0;
    width: 3px;
    background: var(--color-primary);
}

.nk-sidebar .nk-menu-item .nk-menu-link:before {
    content: none;
}

/* Toggle links (Hotspot, PPPoE, ...) render their chevron as an
   absolutely-positioned dashlite :after at right:20px — reserve room so
   long labels don't run under it. */
.nk-sidebar .nk-menu-item .nk-menu-link.nk-menu-toggle {
    padding-right: 40px;
}

.nk-sidebar .nk-menu-icon,
.nk-sidebar .nk-menu .nk-menu-icon {
    display: flex !important;
    flex-shrink: 0;
    width: 20px;
    justify-content: center;
    color: var(--color-gray-400);
}

.nk-sidebar .nk-menu-item .nk-menu-link:hover .nk-menu-icon,
.nk-sidebar .nk-menu-item.active > .nk-menu-link .nk-menu-icon {
    color: var(--color-primary);
}

.nk-sidebar .nk-menu-icon .icon {
    font-size: 17px;
}

.nk-sidebar .nk-menu-sub {
    display: none !important;
    position: static !important;
    opacity: 1 !important;
    visibility: visible !important;
    width: auto !important;
    left: auto !important;
    top: auto !important;
    margin: 0 !important;
    padding: 0 !important;
    background: transparent !important;
    border: none !important;
    box-shadow: none !important;
    border-radius: 0 !important;
}

.nk-sidebar .nk-menu-item.active > .nk-menu-sub {
    display: block !important;
}

.nk-sidebar .nk-menu-sub .nk-menu-item {
    margin-bottom: 0;
}

.nk-sidebar .nk-menu-sub .nk-menu-link {
    padding: 7px 20px 7px 50px !important;
    font-family: var(--font-sans);
    font-size: 13px;
    font-weight: 500;
    line-height: 1.4;
    letter-spacing: normal;
    color: var(--color-gray-500);
}

.nk-sidebar .nk-menu-sub .nk-menu-link:hover,
.nk-sidebar .nk-menu-sub .nk-menu-item.active > .nk-menu-link {
    color: var(--color-primary-dark);
    background: var(--color-primary-soft);
}

.nk-sidebar .nk-menu-item .nk-menu-toggle:after {
    color: var(--color-gray-400);
}

.nk-sidebar .nk-menu-heading {
    padding: 16px 20px 6px;
}

.nk-sidebar .nk-menu-heading span,
.nk-sidebar .nk-menu-heading .overline-title {
    font-size: 11px;
    font-weight: 700;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: var(--color-primary);
}

.nk-sidebar .nk-menu-hr {
    margin: 14px 0;
    border-bottom-color: var(--color-gray-100);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Forms — focus rings via outline, not box-shadow
   ────────────────────────────────────────────────────────────────────────────── */

.form-control,
.form-select {
    border: 1px solid var(--color-gray-300);
    border-radius: var(--radius-md);
    padding: 10px 12px;
    font-size: 14px;
    transition: border-color var(--transition-fast);
    background: var(--color-light);
    color: var(--color-gray-900);
    box-shadow: none;
}

.form-control:focus,
.form-select:focus {
    border-color: var(--color-primary);
    outline: 2px solid var(--color-primary-soft);
    outline-offset: 0;
    box-shadow: none;
}

.form-control.error,
.form-control.is-invalid {
    border-color: var(--color-danger);
}

.form-control.error:focus,
.form-control.is-invalid:focus {
    outline-color: var(--color-danger-soft);
}

.form-label {
    display: block;
    margin-bottom: var(--spacing-sm);
    font-weight: 600;
    font-size: 13px;
    color: var(--color-gray-700);
    text-transform: uppercase;
    letter-spacing: 0.3px;
}

.form-help-text {
    font-size: 12px;
    color: var(--color-gray-500);
    margin-top: var(--spacing-xs);
}

.form-error-text {
    font-size: 12px;
    color: var(--color-danger);
    margin-top: var(--spacing-xs);
}

/* ──────────────────────────────────────────────────────────────────────────────
   Alerts
   ────────────────────────────────────────────────────────────────────────────── */

.alert {
    padding: var(--spacing-lg);
    border-radius: var(--radius-md);
    border-left: 4px solid;
    display: flex;
    gap: var(--spacing-md);
    align-items: flex-start;
    margin-bottom: var(--spacing-lg);
    box-shadow: none;
}

.alert-success { background: var(--color-success-soft); border-left-color: var(--color-success); color: #14532d; }
.alert-warning { background: var(--color-warning-soft); border-left-color: var(--color-warning); color: var(--color-accent-dark); }
.alert-danger  { background: var(--color-danger-soft); border-left-color: var(--color-danger); color: var(--color-danger); }
.alert-info    { background: var(--color-info-soft); border-left-color: var(--color-info); color: #075985; }

.alert-icon { flex-shrink: 0; font-size: 18px; }
.alert-content { flex: 1; }
.alert-title { font-weight: 700; margin-bottom: var(--spacing-xs); font-size: 14px; }

/* ──────────────────────────────────────────────────────────────────────────────
   Responsive
   ────────────────────────────────────────────────────────────────────────────── */

@media (max-width: 768px) {
    .card-inner { padding: var(--spacing-lg); }
    .stat-card { padding: var(--spacing-lg); }
    .btn { padding: 8px 12px; font-size: 13px; }
    .table { font-size: 12px; }
    .table thead th,
    .table tbody td { padding: 8px 12px; }
}

@media (max-width: 576px) {
    .stat-content .value { font-size: 20px; }
    .card-inner { padding: var(--spacing-md); }
}

/* ──────────────────────────────────────────────────────────────────────────────
   Global shadow removal
   DashLite's compiled CSS bakes in ~180 box-shadow declarations across cards,
   dropdowns, modals, toasts, popovers, buttons, etc. Rather than track every
   one, this rule is the single source of truth for "no shadows" across the
   whole application. It is deliberately the last rule in the last stylesheet
   loaded on every page, so nothing after it can reintroduce a shadow.
   ────────────────────────────────────────────────────────────────────────────── */

*,
*::before,
*::after {
    box-shadow: none !important;
    text-shadow: none !important;
}
