/* ===========================================================================
   AddGen — matches the "Liquid Clipper" mockups (Dashboard.png / Settings.png).
   Tailwind (via Play CDN in App.razor) provides utility classes; this file adds
   the glass-panel look, the background gradient, and a few form-control resets.
   =========================================================================== */

html, body {
    background: #05070d;
    color: #f8fafc;
    margin: 0;
    padding: 0;
}

body {
    /* Same layered radial gradients as the mockup: subtle blue glow top-left,
       violet on the right, a deeper blue near the fold. Kept static (no JS). */
    background:
        radial-gradient(ellipse 900px 600px at 15% -10%, rgba(59, 130, 246, .22), transparent 60%),
        radial-gradient(ellipse 900px 700px at 90% 10%, rgba(139, 92, 246, .16), transparent 60%),
        radial-gradient(ellipse 1200px 900px at 50% 110%, rgba(37, 99, 235, .12), transparent 60%),
        #05070d;
    background-attachment: fixed;
    min-height: 100vh;
}

/* Glass panel — used for stat cards, table wrapper, settings sections. */
.glass-panel {
    background: rgba(20, 24, 39, .55);
    border: 1px solid rgba(255, 255, 255, .06);
    backdrop-filter: blur(14px);
    -webkit-backdrop-filter: blur(14px);
    box-shadow: 0 10px 30px -20px rgba(0, 0, 0, .8);
}

/* Text input with the same dark inset + subtle border as the reference. Uses !important so
   Tailwind's Preflight base styles (which reset every input to a white background) don't win. */
.glass-input {
    background-color: rgba(0, 0, 0, .35) !important;
    border: 1px solid rgba(255, 255, 255, .06);
    color: #f1f5f9;
    transition: border-color .15s ease, background-color .15s ease;
}
.glass-input:focus {
    outline: none;
    border-color: rgba(59, 130, 246, .5);
    background-color: rgba(0, 0, 0, .5) !important;
}
.glass-input::placeholder {
    color: #475569;
    opacity: 1;
}

/* Custom scrollbar — matches the dark theme. */
::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-thumb { background: rgba(255, 255, 255, .08); border-radius: 6px; }
::-webkit-scrollbar-thumb:hover { background: rgba(255, 255, 255, .16); }

/* Row hover highlight in the Generated Addresses table. */
.row-hover:hover { background: rgba(255, 255, 255, .025); }

/* ===========================================================================
   Instant click feedback — Blazor Server dispatches every click through
   SignalR (200-500 ms via Cloudflare RTT before the DOM updates). Without any
   :active styling the button LOOKS frozen for the whole round-trip and the
   operator thinks the click didn't register. These pure-CSS rules make every
   button "press down" the millisecond the mouse goes down, so perceived
   latency drops to ZERO even though the wire round-trip is unchanged.
   =========================================================================== */
button,
[role="button"],
a.nav-link,
input[type="button"],
input[type="submit"] {
    transition:
        transform 60ms cubic-bezier(.4, 0, .2, 1),
        background-color 120ms ease,
        border-color 120ms ease,
        color 120ms ease,
        box-shadow 120ms ease;
    will-change: transform;
    -webkit-tap-highlight-color: transparent;
}
button:active:not(:disabled),
[role="button"]:active,
a.nav-link:active,
input[type="button"]:active:not(:disabled),
input[type="submit"]:active:not(:disabled) {
    /* Slight scale-down + darker overlay reads as "pressed" in the operator's peripheral
       vision. Numbers picked so it's noticeable but not jarring. */
    transform: scale(0.965);
    filter: brightness(0.92);
}

/* Ripple-style feedback for the primary "action" buttons — makes destructive / big
   commit clicks feel especially responsive. Applied via a data-attribute so we don't
   need to touch every Razor component; buttons already opt-in via Tailwind classes
   like `bg-primary`. */
button.bg-primary:active,
button[class*="bg-emerald"]:active,
button[class*="bg-rose"]:active {
    box-shadow: 0 0 0 3px rgba(59, 130, 246, .25);
}

/* Global "pending" cursor — the App.razor watchdog flips <html>.classList to
   .cursor-busy the moment a click fires and back off when the server's reply lands.
   If the server answers within ~120 ms the operator never sees the cursor change.
   If it takes longer (Cloudflare hop, timer contention) they get a "wait" cursor so
   the click is visibly acknowledged instead of feeling ignored. */
html.cursor-busy,
html.cursor-busy * {
    cursor: progress !important;
}

/* ===========================================================================
   Client-side dropdowns — toggled by AddGen.toggleMenu() in App.razor.
   Zero SignalR round-trip: the panel is in the DOM at rest with display:none,
   flipping to display:block via a class the moment the button is clicked.
   =========================================================================== */
.addgen-menu-panel {
    display: none;
    /* Panel enter animation: subtle scale + fade so it doesn't just snap in. */
    opacity: 0;
    transform: translateY(-4px) scale(0.98);
    transition: opacity 100ms ease-out, transform 100ms ease-out;
    transform-origin: top right;
}
.addgen-menu.is-open > .addgen-menu-panel {
    display: block;
    opacity: 1;
    transform: translateY(0) scale(1);
}
.addgen-menu-trigger .chevron {
    transition: transform 150ms ease;
}
.addgen-menu.is-open .addgen-menu-trigger .chevron {
    transform: rotate(180deg);
}

/* ===========================================================================
   Modal appear / dismiss transitions — makes the modal FEEL smooth even when
   the SignalR round-trip that renders it takes 200-400 ms. On dismiss,
   AddGen.instantHideModal() adds .is-closing so the operator sees the modal
   melt away immediately while Blazor's "clear _selected" round-trip finishes
   in the background.
   =========================================================================== */
[data-addgen-modal] > .glass-panel,
[data-addgen-modal] > [data-modal-body] {
    animation: addgenModalIn 140ms cubic-bezier(.4, 0, .2, 1);
}
[data-addgen-modal].is-closing {
    /* opacity only — deliberately NO pointer-events:none. Setting pointer-events:none between
       mousedown and mouseup shifts the mouseup target to whatever's underneath the fading
       modal, which breaks the browser's mousedown+mouseup→click coupling: `click` never
       reaches the backdrop, Blazor's @onclick="OnClose" never fires, and once .is-closing's
       800 ms fallback timer strips the class the modal snaps back into view. Leaving
       pointer-events at default lets the click complete cleanly on the (transparent)
       backdrop — OnClose flushes Blazor state to null, the DOM is removed properly, and
       there's no snap-back. */
    opacity: 0;
    transition: opacity 120ms ease-out;
}
@keyframes addgenModalIn {
    from { opacity: 0; transform: translateY(-6px) scale(0.98); }
    to   { opacity: 1; transform: translateY(0)    scale(1); }
}

/* Private-key reveal-on-focus veil. The `.is-revealed` class is toggled by inline
   onfocus/onblur handlers in PrivateKeyField.razor — a JS shim is needed because
   the pure-CSS `:focus` pseudo doesn't apply consistently when the browser window
   isn't OS-focused (headless / automation / minimised). Resting state = blurred
   and non-selectable; revealed state = clear, selectable, subtle rose ring. */
.pk-blur {
    filter: blur(6px);
    user-select: none;
    cursor: pointer;
    transition: filter .15s ease, box-shadow .15s ease, border-color .15s ease;
    outline: none;
    -webkit-text-fill-color: inherit;
}
.pk-blur.is-revealed {
    filter: none;
    user-select: text;
    cursor: text;
    border-color: rgba(251, 113, 133, 0.6);
    box-shadow: 0 0 0 2px rgba(244, 63, 94, .25);
}

/* Blazor error UI (kept from template, restyled). */
#blazor-error-ui {
    color-scheme: light only;
    background: #b91c1c;
    color: white;
    bottom: 0;
    box-shadow: 0 -1px 2px rgba(0,0,0,0.2);
    display: none;
    left: 0;
    padding: 0.6rem 1.25rem 0.7rem 1.25rem;
    position: fixed;
    width: 100%;
    z-index: 1000;
}
#blazor-error-ui .dismiss {
    cursor: pointer;
    position: absolute;
    right: 0.75rem;
    top: 0.5rem;
}

/* Prevent the Chrome autofill from repainting inputs light-blue. Applies to every input in
   the app because Chrome's autofill selector fires on plain URL fields too when the browser
   has cached a value under a matching hostname / port. */
input:-webkit-autofill,
input:-webkit-autofill:hover,
input:-webkit-autofill:focus,
input:-webkit-autofill:active,
textarea:-webkit-autofill,
textarea:-webkit-autofill:hover,
textarea:-webkit-autofill:focus,
select:-webkit-autofill {
    -webkit-text-fill-color: #f1f5f9 !important;
    -webkit-box-shadow: 0 0 0 1000px rgba(0, 0, 0, .35) inset !important;
    caret-color: #f1f5f9 !important;
    transition: background-color 100000s ease-in-out 0s !important;
    background-clip: content-box !important;
}
.glass-input:-webkit-autofill,
.glass-input:-webkit-autofill:hover,
.glass-input:-webkit-autofill:focus,
.glass-input:-webkit-autofill:active {
    -webkit-box-shadow: 0 0 0 1000px rgba(0, 0, 0, .35) inset !important;
}

/* Material Symbols default weight/opsz so the icons don't render fat. */
.material-symbols-outlined {
    font-variation-settings: 'FILL' 0, 'wght' 400, 'GRAD' 0, 'opsz' 24;
    line-height: 1;
    vertical-align: middle;
}

/* ---------------------------------------------------------------------------
   Anchor styles for the top-right user pill + dropdown. Tailwind's Play CDN
   is loaded async, so between page navigations there's a small window where
   the pill would flash with the browser's default (light) button chrome
   before Tailwind's utilities apply. These plain-CSS rules cover exactly
   that gap: same colors as the Tailwind classes so they overlap cleanly.
   --------------------------------------------------------------------------- */
/* Top nav bar — plain CSS baseline covers the moment before Tailwind resolves the arbitrary
   `bg-[#0a0d17]/80` value. Same colour as the Tailwind class so no visual jump either way. */
body > header {
    background-color: rgba(10, 13, 23, 0.8);
    border-bottom: 1px solid rgba(255, 255, 255, 0.05);
    backdrop-filter: blur(20px);
    -webkit-backdrop-filter: blur(20px);
}

button.user-pill {
    background-color: rgba(255, 255, 255, 0.05);
    color: #e2e8f0;
    border: 1px solid rgba(255, 255, 255, 0.06);
    border-radius: 0.5rem;
    padding: 0.375rem 0.75rem;
    font-size: 0.875rem;
    display: inline-flex;
    align-items: center;
    gap: 0.5rem;
    transition: background-color .15s ease;
    cursor: pointer;
}
button.user-pill:hover,
button.user-pill.is-open,
.addgen-menu.is-open .user-pill {
    background-color: rgba(255, 255, 255, 0.1);
}
.user-menu {
    background-color: #0f1220;
    border: 1px solid rgba(255, 255, 255, 0.1);
    border-radius: 0.5rem;
    box-shadow: 0 25px 50px -12px rgba(0, 0, 0, .5);
    color: #f8fafc;
}
