/* ---- themes: light, dark, bumblebee, ember and pride (ember is the default for a device that has never picked one). Components
        read these variables; loader.js and genogram-theme.js set data-theme on <html>, and :root holds light's values
        for anything drawn before they run. The blocks match any element with data-theme, not only <html>, so the
        Color Theme dialog's preview cards can each wear a theme of their own. ---- */

:root,
[data-theme="light"] {
    --gno-surface: #ffffff;
    --gno-surface-2: #f8fafc;
    --gno-surface-3: #f1f5f9;
    --gno-bar: #f8fafc;
    /* The accent and the soft tints round it, as the Data Tips tree first used them: a solid blue for what is on, a
       wash of it for hover and for "partly", a faint grey for a row under the pointer, a hairline for guides. */
    --gno-accent: #2563eb;
    --gno-accent-strong: #1d4ed8;
    --gno-accent-soft: rgba(37, 99, 235, 0.14);
    --gno-accent-glow: rgba(37, 99, 235, 0.35);
    --gno-row-hover: rgba(15, 23, 42, 0.055);
    --gno-guide: rgba(15, 23, 42, 0.13);
    --gno-pop-shadow: 0 10px 30px rgba(15, 23, 42, 0.18), 0 1px 3px rgba(15, 23, 42, 0.08);
    --gno-modal-shadow: 0 24px 60px rgba(15, 23, 42, 0.32), 0 2px 6px rgba(15, 23, 42, 0.1);
    --gno-scrim: rgba(15, 23, 42, 0.38);
    --gno-border: #cbd5e1;
    --gno-border-strong: #94a3b8;
    --gno-edge: rgba(15, 23, 42, 0.25);
    --gno-text: #0f172a;
    --gno-text-strong: #020617;
    --gno-text-2: #1e293b;
    --gno-muted: #475569;
    --gno-muted-2: #64748b;
    --gno-title-hover: #e0e7ff;
    --gno-hover: rgba(15, 23, 42, 0.1);
    --gno-active-tint: #eef2ff;
    --gno-active-border: #a5b4fc;
    --gno-accent-text: #1e40af;
    --gno-accent-hover-text: #1e3a8a;
    --gno-accent-fill: #eff6ff;
    --gno-drop-active: #dbeafe;
    --gno-desktop: #e2e8f0;
    --gno-glow: rgba(255, 255, 255, 0.7);
    --gno-tint-glow: rgba(191, 219, 254, 0.55);
    --gno-dots: rgba(15, 23, 42, 0.1);
    --gno-dock-bg: rgba(255, 255, 255, 0.72);
    --gno-dock-edge: rgba(255, 255, 255, 0.9);
    /* The same frosted glass, nearly opaque, for menus that drop over busy drawings; a soft lift for the bars that
       float over the desktop for good; and the windows' hairline edge and shadows, deeper on the active one. */
    --gno-glass: rgba(255, 255, 255, 0.9);
    --gno-glass-edge: rgba(15, 23, 42, 0.1);
    --gno-float-shadow: 0 4px 16px rgba(15, 23, 42, 0.08), 0 1px 2px rgba(15, 23, 42, 0.06);
    --gno-window-edge: rgba(15, 23, 42, 0.12);
    --gno-window-shadow: 0 6px 20px rgba(15, 23, 42, 0.1), 0 1px 3px rgba(15, 23, 42, 0.06);
    --gno-window-shadow-active: 0 0 0 1px var(--gno-accent-soft), 0 18px 44px rgba(15, 23, 42, 0.22), 0 2px 6px rgba(15, 23, 42, 0.08);
    --gno-grid: #e2e8f0;
    --gno-line: #111827;
    --gno-error-bg: #fef2f2;
    --gno-error-edge: #fecaca;
    --gno-error-text: #991b1b;
    --gno-modified-from: #fffbeb;
    --gno-modified-to: #fde68a;
    --gno-modified-edge: #f59e0b;
    --gno-modified-text: #78350f;
    /* Read-only: a cool teal, kept apart from the accent (what is on) and from amber (what needs care). The lock
       chips, the locked window's title bar and the strip over its drawing all draw on these. */
    --gno-locked: #0f766e;
    --gno-locked-text: #115e59;
    --gno-locked-soft: rgba(15, 118, 110, 0.12);
    --gno-locked-from: #f0fdfa;
    --gno-locked-to: #ccfbf1;
    --gno-locked-edge: #5eead4;
    --gno-on-locked: #ffffff;
    /* The accent as drawn on white paper (the print preview's frame): the same blue here, a deeper gold in bumblebee
       and ember. And the ink on the accent itself (a primary button's text): white on blue, near-black on yellow or gold. */
    --gno-paper-accent: #2563eb;
    --gno-on-accent: #ffffff;
    /* The pulse: the hairline that runs while the bug tracker is polled, and the stripe on its toasts. Each theme has a
       three-stop gradient of its own with a glow and a glint; light's is electric, blue through violet to cyan. */
    --gno-pulse-track: rgba(15, 23, 42, 0.09);
    --gno-pulse-a: #2563eb;
    --gno-pulse-b: #7c3aed;
    --gno-pulse-c: #06b6d4;
    --gno-pulse-glow: rgba(99, 102, 241, 0.5);
    --gno-pulse-glint: rgba(255, 255, 255, 0.95);
    color-scheme: light;
}

[data-theme="dark"] {
    --gno-surface: #1f2430;
    --gno-surface-2: #242a37;
    --gno-surface-3: #2a3142;
    --gno-bar: #242a37;
    --gno-accent: #3b82f6;
    --gno-accent-strong: #2563eb;
    --gno-accent-soft: rgba(96, 165, 250, 0.2);
    --gno-accent-glow: rgba(59, 130, 246, 0.45);
    --gno-row-hover: rgba(255, 255, 255, 0.06);
    --gno-guide: rgba(255, 255, 255, 0.12);
    --gno-pop-shadow: 0 10px 30px rgba(0, 0, 0, 0.45), 0 1px 3px rgba(0, 0, 0, 0.3);
    --gno-modal-shadow: 0 24px 60px rgba(0, 0, 0, 0.55), 0 2px 6px rgba(0, 0, 0, 0.3);
    --gno-scrim: rgba(0, 0, 0, 0.5);
    --gno-border: #4a5568;
    --gno-border-strong: #6b7690;
    --gno-edge: rgba(255, 255, 255, 0.22);
    --gno-text: #f3f4f6;
    --gno-text-strong: #ffffff;
    --gno-text-2: #e5e7eb;
    --gno-muted: #b8c1d0;
    --gno-muted-2: #8f9aad;
    --gno-title-hover: #2e3748;
    --gno-hover: rgba(255, 255, 255, 0.12);
    --gno-active-tint: #262e41;
    --gno-active-border: #5a6c94;
    --gno-accent-text: #a5d0ff;
    --gno-accent-hover-text: #bfdbfe;
    --gno-accent-fill: #1e3a5f;
    --gno-drop-active: #1e2d4a;
    --gno-desktop: #12151c;
    --gno-glow: rgba(255, 255, 255, 0.03);
    --gno-tint-glow: rgba(59, 130, 246, 0.12);
    --gno-dots: rgba(255, 255, 255, 0.06);
    --gno-dock-bg: rgba(31, 36, 48, 0.78);
    --gno-dock-edge: rgba(255, 255, 255, 0.08);
    --gno-glass: rgba(31, 36, 48, 0.92);
    --gno-glass-edge: rgba(255, 255, 255, 0.1);
    --gno-float-shadow: 0 4px 16px rgba(0, 0, 0, 0.3), 0 1px 2px rgba(0, 0, 0, 0.25);
    --gno-window-edge: rgba(255, 255, 255, 0.1);
    --gno-window-shadow: 0 6px 20px rgba(0, 0, 0, 0.35), 0 1px 3px rgba(0, 0, 0, 0.25);
    --gno-window-shadow-active: 0 0 0 1px var(--gno-accent-soft), 0 18px 44px rgba(0, 0, 0, 0.55), 0 2px 6px rgba(0, 0, 0, 0.3);
    --gno-grid: #2c3443;
    --gno-line: #e5e7eb;
    --gno-error-bg: #3a1d20;
    --gno-error-edge: #6b2a30;
    --gno-error-text: #fca5a5;
    --gno-modified-from: #3b2f12;
    --gno-modified-to: #5a4414;
    --gno-modified-edge: #b45309;
    --gno-modified-text: #fde68a;
    --gno-locked: #2dd4bf;
    --gno-locked-text: #99f6e4;
    --gno-locked-soft: rgba(45, 212, 191, 0.16);
    --gno-locked-from: #14302d;
    --gno-locked-to: #1a3f3a;
    --gno-locked-edge: #0f766e;
    --gno-on-locked: #042f2e;
    --gno-paper-accent: #2563eb;
    --gno-on-accent: #ffffff;
    /* Aurora: cyan through indigo to pink, neon on the slate. */
    --gno-pulse-track: rgba(255, 255, 255, 0.09);
    --gno-pulse-a: #22d3ee;
    --gno-pulse-b: #818cf8;
    --gno-pulse-c: #f472b6;
    --gno-pulse-glow: rgba(129, 140, 248, 0.65);
    --gno-pulse-glint: rgba(255, 255, 255, 0.95);
    color-scheme: dark;
}

/* Bumblebee: black and white, with yellow kept for the accent alone (what is on, selected or focused) and red for what
   needs care (unsaved changes, errors, Live). The chrome is near-black on a true-black desktop with a faint yellow
   glow; the drawing itself stays on white paper (see below). */
[data-theme="bumblebee"] {
    --gno-surface: #161616;
    --gno-surface-2: #1c1c1c;
    --gno-surface-3: #262626;
    --gno-bar: #111111;
    --gno-accent: #facc15;
    --gno-accent-strong: #eab308;
    --gno-accent-soft: rgba(250, 204, 21, 0.13);
    --gno-accent-glow: rgba(250, 204, 21, 0.4);
    --gno-row-hover: rgba(255, 255, 255, 0.07);
    --gno-guide: rgba(255, 255, 255, 0.11);
    --gno-pop-shadow: 0 10px 30px rgba(0, 0, 0, 0.6), 0 1px 3px rgba(0, 0, 0, 0.4);
    --gno-modal-shadow: 0 24px 60px rgba(0, 0, 0, 0.7), 0 2px 6px rgba(0, 0, 0, 0.4);
    --gno-scrim: rgba(0, 0, 0, 0.6);
    --gno-border: #3a3a3a;
    --gno-border-strong: #5e5e5e;
    --gno-edge: rgba(255, 255, 255, 0.22);
    --gno-text: #f5f5f5;
    --gno-text-strong: #ffffff;
    --gno-text-2: #e4e4e4;
    --gno-muted: #b3b3b3;
    --gno-muted-2: #878787;
    --gno-title-hover: #262626;
    --gno-hover: rgba(255, 255, 255, 0.12);
    --gno-active-tint: #262211;
    --gno-active-border: #a16207;
    --gno-accent-text: #fde047;
    --gno-accent-hover-text: #fef08a;
    --gno-accent-fill: #2a2510;
    --gno-drop-active: #332c0e;
    --gno-desktop: #000000;
    --gno-glow: rgba(255, 255, 255, 0.04);
    --gno-tint-glow: rgba(250, 204, 21, 0.1);
    --gno-dots: rgba(255, 255, 255, 0.07);
    --gno-dock-bg: rgba(14, 14, 14, 0.8);
    --gno-dock-edge: rgba(255, 255, 255, 0.1);
    --gno-glass: rgba(16, 16, 16, 0.93);
    --gno-glass-edge: rgba(255, 255, 255, 0.12);
    --gno-float-shadow: 0 4px 16px rgba(0, 0, 0, 0.45), 0 1px 2px rgba(0, 0, 0, 0.35);
    --gno-window-edge: rgba(255, 255, 255, 0.12);
    --gno-window-shadow: 0 6px 20px rgba(0, 0, 0, 0.5), 0 1px 3px rgba(0, 0, 0, 0.35);
    --gno-window-shadow-active: 0 0 0 1px var(--gno-accent-soft), 0 18px 44px rgba(0, 0, 0, 0.7), 0 2px 6px rgba(0, 0, 0, 0.4);
    --gno-grid: #262626;
    --gno-line: #f5f5f5;
    --gno-error-bg: #2a0e11;
    --gno-error-edge: #7f1d1d;
    --gno-error-text: #fca5a5;
    --gno-modified-from: #2a0e11;
    --gno-modified-to: #4a1218;
    --gno-modified-edge: #dc2626;
    --gno-modified-text: #fecaca;
    /* Read-only is silver here: yellow stays the accent and red stays for care. */
    --gno-locked: #d4d4d4;
    --gno-locked-text: #e8e8e8;
    --gno-locked-soft: rgba(212, 212, 212, 0.14);
    --gno-locked-from: #202020;
    --gno-locked-to: #2d2d2d;
    --gno-locked-edge: #737373;
    --gno-on-locked: #111111;
    --gno-paper-accent: #ca8a04;
    --gno-on-accent: #111111;
    /* High voltage: amber through yellow to a white-hot tip, on black. */
    --gno-pulse-track: rgba(255, 255, 255, 0.09);
    --gno-pulse-a: #f59e0b;
    --gno-pulse-b: #facc15;
    --gno-pulse-c: #fef08a;
    --gno-pulse-glow: rgba(250, 204, 21, 0.7);
    --gno-pulse-glint: rgba(255, 255, 255, 1);
    color-scheme: dark;
}

/* Ember: black, gold and a little fire. The chrome is a warm near-black, gold is the accent (what is on, selected or
   focused), yellow is kept for the one brightest moment (gold text under the pointer), and red for what needs care
   (unsaved changes, errors, Live) and for a single deep glow in the desktop's corner. The drawing stays on white
   paper (see below). */
[data-theme="ember"] {
    --gno-surface: #1b1416;
    --gno-surface-2: #221a1c;
    --gno-surface-3: #2c2225;
    --gno-bar: #140f10;
    --gno-accent: #efb72e;
    --gno-accent-strong: #d59a16;
    --gno-accent-soft: rgba(239, 183, 46, 0.14);
    --gno-accent-glow: rgba(239, 183, 46, 0.42);
    --gno-row-hover: rgba(255, 220, 190, 0.07);
    --gno-guide: rgba(255, 235, 220, 0.11);
    --gno-pop-shadow: 0 10px 30px rgba(0, 0, 0, 0.62), 0 1px 3px rgba(0, 0, 0, 0.4);
    --gno-modal-shadow: 0 24px 60px rgba(0, 0, 0, 0.72), 0 2px 6px rgba(0, 0, 0, 0.4);
    --gno-scrim: rgba(0, 0, 0, 0.62);
    --gno-border: #3b2e31;
    --gno-border-strong: #665055;
    --gno-edge: rgba(255, 235, 220, 0.22);
    --gno-text: #f6efe8;
    --gno-text-strong: #fffaf3;
    --gno-text-2: #e8dfd6;
    --gno-muted: #c4b5ab;
    --gno-muted-2: #958279;
    --gno-title-hover: #2b1a1d;
    --gno-hover: rgba(255, 230, 200, 0.12);
    --gno-active-tint: #2a2012;
    --gno-active-border: #8c6a14;
    --gno-accent-text: #f5c042;
    --gno-accent-hover-text: #ffd76a;
    --gno-accent-fill: #2e2410;
    --gno-drop-active: #3a2b0f;
    --gno-desktop: #0a0708;
    --gno-glow: rgba(239, 183, 46, 0.08);
    --gno-tint-glow: rgba(185, 28, 28, 0.2);
    --gno-dots: rgba(255, 230, 200, 0.07);
    --gno-dock-bg: rgba(20, 15, 16, 0.82);
    --gno-dock-edge: rgba(255, 235, 220, 0.1);
    --gno-glass: rgba(22, 16, 18, 0.93);
    --gno-glass-edge: rgba(255, 235, 220, 0.12);
    --gno-float-shadow: 0 4px 16px rgba(0, 0, 0, 0.48), 0 1px 2px rgba(0, 0, 0, 0.35);
    --gno-window-edge: rgba(255, 235, 220, 0.12);
    --gno-window-shadow: 0 6px 20px rgba(0, 0, 0, 0.52), 0 1px 3px rgba(0, 0, 0, 0.35);
    --gno-window-shadow-active: 0 0 0 1px var(--gno-accent-soft), 0 18px 44px rgba(0, 0, 0, 0.72), 0 2px 6px rgba(0, 0, 0, 0.4);
    --gno-grid: #2c2225;
    --gno-line: #f6efe8;
    --gno-error-bg: #2b0d10;
    --gno-error-edge: #8b1a1a;
    --gno-error-text: #fda4a4;
    --gno-modified-from: #2a1012;
    --gno-modified-to: #4b1418;
    --gno-modified-edge: #e11d2e;
    --gno-modified-text: #fecaca;
    /* Read-only is a warm pewter here: gold stays the accent and red stays for care. */
    --gno-locked: #b8aaa0;
    --gno-locked-text: #e6dbd2;
    --gno-locked-soft: rgba(184, 170, 160, 0.14);
    --gno-locked-from: #241c1e;
    --gno-locked-to: #322729;
    --gno-locked-edge: #6e5f58;
    --gno-on-locked: #1b1416;
    --gno-paper-accent: #ca8a04;
    --gno-on-accent: #1a1208;
    /* Fire: deep red through orange to bright gold, the glow orange. */
    --gno-pulse-track: rgba(255, 220, 190, 0.09);
    --gno-pulse-a: #b91c1c;
    --gno-pulse-b: #f97316;
    --gno-pulse-c: #ffd76a;
    --gno-pulse-glow: rgba(249, 115, 22, 0.65);
    --gno-pulse-glint: rgba(255, 241, 199, 1);
    color-scheme: dark;
}

/* Pride: couture after dark. The chrome is a plum black, the trans flag's pink is the accent (what is on, selected or
   focused) and its blue the second voice: the desktop glows blue in one corner and pink in the other, read-only is a
   soft blue, and the activity pulse runs blue, pink and white. The rainbow is kept for one fine ribbon under the menu
   bar (below), led by the Progress flag's trans stripes. A true red stays for what needs care. The drawing stays on
   white paper (see below). */
[data-theme="pride"] {
    --gno-surface: #19131b;
    --gno-surface-2: #201922;
    --gno-surface-3: #2a212d;
    --gno-bar: #120d14;
    --gno-accent: #f5a9b8;
    --gno-accent-strong: #ee8ea2;
    --gno-accent-soft: rgba(245, 169, 184, 0.14);
    --gno-accent-glow: rgba(245, 169, 184, 0.4);
    --gno-row-hover: rgba(255, 228, 236, 0.065);
    --gno-guide: rgba(255, 228, 236, 0.1);
    --gno-pop-shadow: 0 10px 30px rgba(0, 0, 0, 0.6), 0 1px 3px rgba(0, 0, 0, 0.4);
    --gno-modal-shadow: 0 24px 60px rgba(0, 0, 0, 0.7), 0 2px 6px rgba(0, 0, 0, 0.4);
    --gno-scrim: rgba(6, 3, 8, 0.62);
    --gno-border: #362a38;
    --gno-border-strong: #5c4a5e;
    --gno-edge: rgba(255, 228, 236, 0.2);
    --gno-text: #f7f0f4;
    --gno-text-strong: #ffffff;
    --gno-text-2: #e8dde4;
    --gno-muted: #bfb0ba;
    --gno-muted-2: #8f7f8b;
    --gno-title-hover: #2a1d26;
    --gno-hover: rgba(255, 228, 236, 0.11);
    --gno-active-tint: #2b1a22;
    --gno-active-border: #a8667a;
    --gno-accent-text: #f7b6c4;
    --gno-accent-hover-text: #fcd6df;
    --gno-accent-fill: #2f1b24;
    --gno-drop-active: #3c2230;
    --gno-desktop: #0b080d;
    --gno-glow: rgba(91, 206, 250, 0.1);
    --gno-tint-glow: rgba(245, 169, 184, 0.17);
    --gno-dots: rgba(255, 228, 236, 0.065);
    --gno-dock-bg: rgba(18, 13, 20, 0.84);
    --gno-dock-edge: rgba(255, 228, 236, 0.1);
    --gno-glass: rgba(21, 16, 23, 0.94);
    --gno-glass-edge: rgba(255, 228, 236, 0.12);
    --gno-float-shadow: 0 4px 16px rgba(0, 0, 0, 0.46), 0 1px 2px rgba(0, 0, 0, 0.35);
    --gno-window-edge: rgba(255, 228, 236, 0.11);
    --gno-window-shadow: 0 6px 20px rgba(0, 0, 0, 0.5), 0 1px 3px rgba(0, 0, 0, 0.35);
    --gno-window-shadow-active: 0 0 0 1px var(--gno-accent-soft), 0 18px 44px rgba(0, 0, 0, 0.7), 0 0 60px -20px rgba(91, 206, 250, 0.22);
    --gno-grid: #2a212d;
    --gno-line: #f7f0f4;
    --gno-error-bg: #2b0c10;
    --gno-error-edge: #8f1d22;
    --gno-error-text: #fca5a5;
    --gno-modified-from: #2a0f12;
    --gno-modified-to: #4a1419;
    --gno-modified-edge: #ef4444;
    --gno-modified-text: #fecaca;
    /* Read-only is the flag's blue, softened: pink stays the accent and red stays for care. */
    --gno-locked: #8fcbe6;
    --gno-locked-text: #d4ecf7;
    --gno-locked-soft: rgba(143, 203, 230, 0.14);
    --gno-locked-from: #17202a;
    --gno-locked-to: #1d2c38;
    --gno-locked-edge: #4c7a8f;
    --gno-on-locked: #0e1820;
    --gno-paper-accent: #c2185b;
    --gno-on-accent: #2a0f18;
    /* The trans flag: blue, pink and a white glint. */
    --gno-pulse-track: rgba(255, 228, 236, 0.08);
    --gno-pulse-a: #5bcefa;
    --gno-pulse-b: #f5a9b8;
    --gno-pulse-c: #ffffff;
    --gno-pulse-glow: rgba(245, 169, 184, 0.6);
    --gno-pulse-glint: rgba(255, 255, 255, 1);
    /* The ribbon: the Progress flag's chevron as clean trans stripes, then the rainbow in jewel tones, blended. */
    --gno-pride-ribbon: linear-gradient(90deg,
        #5bcefa 0 3%, #f5a9b8 3% 6%, #ffffff 6% 9%, #f5a9b8 9% 12%, #5bcefa 12% 15%,
        #e0405a 22%, #f08a3c 36%, #f2c84b 50%, #3fae74 64%, #3d7fd1 78%, #8e5bd0 92%);
    color-scheme: dark;
}

/* Pride's signature: a hairline of the ribbon under the menu bar (and the theme card's little one), and selected text
   in a wash of pink. */
html[data-theme="pride"] .menu-bar,
.theme-card__preview[data-theme="pride"] .theme-card__menubar {
    border-bottom: 2px solid transparent;
    border-image: var(--gno-pride-ribbon) 1;
}

[data-theme="pride"] ::selection {
    background: rgba(245, 169, 184, 0.32);
    color: #ffffff;
}

/* Pride's desktop is woven silk (pride-silk.webp, rendered by tools/pride-silk/pride_silk.py): pink silk for trans
   women, blue for trans men and a ribbon in the non-binary flag's stripes, each passing over one and under another so
   none is on top, bound together by a thread dyed in the trans flag, with the rainbow soft behind. A veil of the plum,
   deepest in the middle where the desktop's own words sit, keeps them readable and lets the silk frame the edges. */
html[data-theme="pride"] .app-zoom,
html[data-theme="pride"] .tablet,
html[data-theme="pride"] .phone,
.theme-cards .theme-card__preview[data-theme="pride"] {
    background-image:
        radial-gradient(ellipse 60% 55% at 50% 52%, rgba(11, 8, 13, 0.78), rgba(11, 8, 13, 0.5) 45%, rgba(11, 8, 13, 0.12) 100%),
        url("pride-silk.webp");
    background-size: cover;
    background-position: center;
}

/* Bumblebee's, ember's and pride's GenoMap is white paper inside the dark window: the drawing's colours are a light
   theme's, and its accent a gold deep enough to read on white (pride's a raspberry, below). Only the svg is inside this scope; the context menus and the
   delete confirmation beside it keep the black chrome. The Color Theme dialog's preview paper shares the look. */
[data-theme="bumblebee"] .genogram-canvas,
[data-theme="bumblebee"] .gno-paper-preview,
[data-theme="ember"] .genogram-canvas,
[data-theme="ember"] .gno-paper-preview,
[data-theme="pride"] .genogram-canvas,
[data-theme="pride"] .gno-paper-preview {
    --gno-surface: #ffffff;
    --gno-surface-2: #f5f5f4;
    --gno-surface-3: #ebebea;
    --gno-line: #111111;
    --gno-text: #111111;
    --gno-text-strong: #000000;
    --gno-text-2: #262626;
    --gno-muted: #525252;
    --gno-muted-2: #737373;
    --gno-grid: #e7e5e4;
    --gno-accent: #ca8a04;
    --gno-accent-strong: #a16207;
    --gno-accent-text: #854d0e;
    --gno-accent-soft: rgba(202, 138, 4, 0.16);
    --gno-accent-glow: rgba(202, 138, 4, 0.35);
    --gno-accent-fill: #fef9c3;
    --gno-scrim: rgba(0, 0, 0, 0.38);
}

[data-theme="pride"] .genogram-canvas,
[data-theme="pride"] .gno-paper-preview {
    --gno-accent: #c2185b;
    --gno-accent-strong: #a3134c;
    --gno-accent-text: #880e40;
    --gno-accent-soft: rgba(194, 24, 91, 0.12);
    --gno-accent-glow: rgba(194, 24, 91, 0.3);
    --gno-accent-fill: #fdeef4;
    --gno-scrim: rgba(0, 0, 0, 0.38);
}

/* ---- read-only: the lock chip, wherever it shows (menu bar, title bar, window footer, dock). A quiet capsule in the
        theme's locked colour with a small padlock; as a button it unlocks the window, and says so under the pointer. ---- */

.lock-chip {
    display: inline-flex;
    align-items: center;
    gap: 0.32rem;
    padding: 0.14rem 0.55rem 0.14rem 0.45rem;
    border: 1px solid color-mix(in srgb, var(--gno-locked) 38%, transparent);
    border-radius: 999px;
    background: var(--gno-locked-soft);
    color: var(--gno-locked-text);
    font-size: 0.68rem;
    font-weight: 650;
    letter-spacing: 0.05em;
    line-height: 1.25;
    text-transform: uppercase;
    white-space: nowrap;
    user-select: none;
    transition: background-color 140ms ease, color 140ms ease, border-color 140ms ease;
}

.lock-chip svg {
    flex: none;
}

.lock-chip__label {
    display: inline-block;
}

/* As a button: hovering it turns it solid and offers to unlock; the shackle on its padlock swings open. */
.lock-chip--button {
    cursor: pointer;
    font: inherit;
    font-size: 0.68rem;
    font-weight: 650;
    letter-spacing: 0.05em;
    text-transform: uppercase;
}

.lock-chip--button .lock-chip__hover {
    display: none;
}

.lock-chip--button:hover,
.lock-chip--button:focus-visible {
    background: var(--gno-locked);
    border-color: var(--gno-locked);
    color: var(--gno-on-locked);
    outline: none;
    box-shadow: 0 0 0 3px var(--gno-locked-soft);
}

.lock-chip--button:hover .lock-chip__label,
.lock-chip--button:focus-visible .lock-chip__label {
    display: none;
}

.lock-chip--button:hover .lock-chip__hover,
.lock-chip--button:focus-visible .lock-chip__hover {
    display: inline-block;
}

.lock-chip--button .lock-glyph__shackle {
    transform-origin: 5.5px 7px;
    transition: transform 160ms ease;
}

.lock-chip--button:hover .lock-glyph__shackle,
.lock-chip--button:focus-visible .lock-glyph__shackle {
    transform: rotate(-28deg) translateX(-0.6px);
}

/* The padlock shaken when an edit is refused: the strip over the drawing replays this each time. */
@keyframes lock-shake {
    0%, 100% { transform: none; }
    20% { transform: translateX(-2px) rotate(-8deg); }
    40% { transform: translateX(2px) rotate(8deg); }
    60% { transform: translateX(-1.5px) rotate(-4deg); }
    80% { transform: translateX(1px) rotate(3deg); }
}

html, body {
    font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;
    --maui-status-bar-safe-area-background: rgb(3, 23, 62);
    height: 100%;
    margin: 0;
    overflow: hidden;
}

/* Root element of the MAUI BlazorWebView host (index.html). */
#app {
    height: 100%;
}

* {
    scrollbar-width: thin;
    scrollbar-color: var(--gno-border-strong) transparent;
}

a, .btn-link {
    color: var(--gno-accent-text);
}

/* ---- controls: every button, field, box, switch and slider in the Data Tips look. Bootstrap supplies the shapes;
        these give them the app's colours (in both themes), rounder corners and the soft accent ring on focus. ---- */

.btn {
    --bs-btn-padding-x: 0.85rem;
    --bs-btn-padding-y: 0.36rem;
    --bs-btn-font-size: 0.85rem;
    --bs-btn-font-weight: 600;
    --bs-btn-border-radius: 8px;
    --bs-btn-focus-box-shadow: 0 0 0 3px var(--gno-accent-soft);
    --bs-btn-disabled-opacity: 0.5;
    transition: background-color 120ms ease, border-color 120ms ease, color 120ms ease, box-shadow 120ms ease, transform 80ms ease;
}

    .btn:active {
        transform: translateY(0.5px);
    }

.btn-sm {
    --bs-btn-padding-x: 0.65rem;
    --bs-btn-padding-y: 0.22rem;
    --bs-btn-font-size: 0.78rem;
    --bs-btn-border-radius: 7px;
}

.btn-primary {
    --bs-btn-color: var(--gno-on-accent);
    --bs-btn-bg: var(--gno-accent);
    --bs-btn-border-color: var(--gno-accent);
    --bs-btn-hover-color: var(--gno-on-accent);
    --bs-btn-hover-bg: var(--gno-accent-strong);
    --bs-btn-hover-border-color: var(--gno-accent-strong);
    --bs-btn-active-color: var(--gno-on-accent);
    --bs-btn-active-bg: var(--gno-accent-strong);
    --bs-btn-active-border-color: var(--gno-accent-strong);
    --bs-btn-disabled-color: var(--gno-on-accent);
    --bs-btn-disabled-bg: var(--gno-accent);
    --bs-btn-disabled-border-color: var(--gno-accent);
    box-shadow: 0 1px 2px var(--gno-accent-glow);
}

/* The quiet button (Defaults, Cancel): a hairline that takes the accent under the pointer. */
.btn-outline-secondary,
.btn-secondary {
    --bs-btn-color: var(--gno-text-2);
    --bs-btn-bg: var(--gno-surface);
    --bs-btn-border-color: var(--gno-border);
    --bs-btn-hover-color: var(--gno-accent-text);
    --bs-btn-hover-bg: var(--gno-accent-fill);
    --bs-btn-hover-border-color: var(--gno-accent);
    --bs-btn-active-color: var(--gno-accent-text);
    --bs-btn-active-bg: var(--gno-accent-soft);
    --bs-btn-active-border-color: var(--gno-accent);
    --bs-btn-disabled-color: var(--gno-muted-2);
    --bs-btn-disabled-bg: transparent;
    --bs-btn-disabled-border-color: var(--gno-border);
}

.btn-secondary {
    --bs-btn-bg: var(--gno-surface-3);
}

.btn-link {
    --bs-btn-color: var(--gno-accent-text);
    --bs-btn-hover-color: var(--gno-accent-hover-text);
    --bs-btn-active-color: var(--gno-accent-hover-text);
    --bs-btn-font-weight: 600;
    text-decoration: none;
}

    .btn-link:hover {
        text-decoration: underline;
        text-underline-offset: 0.15em;
    }

.form-control,
.form-select {
    border-color: var(--gno-border);
    border-radius: 8px;
    background-color: var(--gno-surface);
    color: var(--gno-text);
    transition: border-color 120ms ease, box-shadow 120ms ease;
}

    .form-control::placeholder {
        color: var(--gno-muted-2);
    }

    .form-control:hover:not(:disabled):not(:focus),
    .form-select:hover:not(:disabled):not(:focus) {
        border-color: var(--gno-border-strong);
    }

    .form-control:focus,
    .form-select:focus {
        border-color: var(--gno-accent);
        background-color: var(--gno-surface);
        color: var(--gno-text);
        box-shadow: 0 0 0 3px var(--gno-accent-soft);
    }

    .form-control:disabled,
    .form-select:disabled {
        background-color: var(--gno-surface-3);
        color: var(--gno-muted-2);
    }

.form-control-sm,
.form-select-sm {
    border-radius: 7px;
}

[data-theme="dark"] .form-select,
[data-theme="bumblebee"] .form-select,
[data-theme="ember"] .form-select,
[data-theme="pride"] .form-select {
    --bs-form-select-bg-img: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cpath fill='none' stroke='%23b8c1d0' stroke-linecap='round' stroke-linejoin='round' stroke-width='2' d='m2 5 6 6 6-6'/%3e%3c/svg%3e");
}

/* Tick boxes and radio buttons: the tree's drawn box. A soft ring on hover, a solid fill and a white tick when on, a
   wash and a dash when only partly on. */
input[type="checkbox"]:not([role="switch"]),
input[type="radio"] {
    appearance: none;
    flex: none;
    width: 15px;
    height: 15px;
    margin: 0;
    vertical-align: -0.17em;
    box-sizing: border-box;
    border: 1.5px solid var(--gno-border-strong);
    border-radius: 4px;
    background: var(--gno-surface) center / 11px 11px no-repeat;
    box-shadow: none;
    cursor: pointer;
    transition: background-color 120ms ease, border-color 120ms ease, box-shadow 120ms ease;
}

input[type="radio"] {
    border-radius: 50%;
}

    input[type="checkbox"]:not([role="switch"]):hover:not(:disabled):not(:checked),
    input[type="radio"]:hover:not(:disabled):not(:checked),
    label:hover > input[type="checkbox"]:not([role="switch"]):not(:disabled):not(:checked),
    label:hover > input[type="radio"]:not(:disabled):not(:checked) {
        border-color: var(--gno-accent);
        box-shadow: 0 0 0 3px var(--gno-accent-soft);
    }

    input[type="checkbox"]:not([role="switch"]):checked {
        border-color: var(--gno-accent);
        background-color: var(--gno-accent);
        background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12' fill='none' stroke='%23fff' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M2.6 6.3 4.9 8.6 9.5 3.7'/%3E%3C/svg%3E");
        box-shadow: 0 1px 2px var(--gno-accent-glow);
    }

    input[type="checkbox"]:not([role="switch"]):indeterminate {
        border-color: var(--gno-accent);
        background: var(--gno-accent-soft) linear-gradient(var(--gno-accent), var(--gno-accent)) center / 7px 2px no-repeat;
    }

    input[type="radio"]:checked {
        border-color: var(--gno-accent);
        background: radial-gradient(circle, #fff 0 2.5px, transparent 3px) var(--gno-accent);
        box-shadow: 0 1px 2px var(--gno-accent-glow);
    }

    input[type="checkbox"]:focus-visible,
    input[type="radio"]:focus-visible {
        outline: 2px solid var(--gno-accent);
        outline-offset: 2px;
    }

    input[type="checkbox"]:disabled,
    input[type="radio"]:disabled {
        opacity: 0.5;
        cursor: default;
    }

/* An on/off setting: a slide switch (mark the box role="switch"). */
input[type="checkbox"][role="switch"] {
    appearance: none;
    position: relative;
    flex: none;
    width: 26px;
    height: 15px;
    margin: 0;
    vertical-align: -0.2em;
    border: 0;
    border-radius: 999px;
    background: var(--gno-border-strong);
    cursor: pointer;
    transition: background-color 150ms ease;
}

    input[type="checkbox"][role="switch"]::after {
        content: "";
        position: absolute;
        left: 2px;
        top: 2px;
        width: 11px;
        height: 11px;
        border-radius: 50%;
        background: #fff;
        box-shadow: 0 1px 2px rgba(15, 23, 42, 0.3);
        transition: transform 150ms ease;
    }

    input[type="checkbox"][role="switch"]:checked {
        background: var(--gno-accent);
    }

        input[type="checkbox"][role="switch"]:checked::after {
            transform: translateX(11px);
        }

/* Sliders: a thin rounded track, filled up to a white knob ringed in the accent. Set --fill (0%-100%) on the input to
   colour the track behind the knob in WebKit; Firefox fills it on its own. */
input[type="range"] {
    --fill: 0%;
    appearance: none;
    height: 16px;
    background: transparent;
    cursor: pointer;
}

    input[type="range"]::-webkit-slider-runnable-track {
        height: 4px;
        border-radius: 999px;
        background: linear-gradient(var(--gno-accent), var(--gno-accent)) 0 0 / var(--fill) 100% no-repeat, var(--gno-border);
    }

    input[type="range"]::-webkit-slider-thumb {
        appearance: none;
        width: 14px;
        height: 14px;
        margin-top: -5px;
        box-sizing: border-box;
        border: 2px solid var(--gno-accent);
        border-radius: 50%;
        background: #fff;
        box-shadow: 0 1px 3px rgba(15, 23, 42, 0.25);
        transition: box-shadow 120ms ease;
    }

    input[type="range"]::-moz-range-track {
        height: 4px;
        border-radius: 999px;
        background: var(--gno-border);
    }

    input[type="range"]::-moz-range-progress {
        height: 4px;
        border-radius: 999px;
        background: var(--gno-accent);
    }

    input[type="range"]::-moz-range-thumb {
        width: 14px;
        height: 14px;
        box-sizing: border-box;
        border: 2px solid var(--gno-accent);
        border-radius: 50%;
        background: #fff;
        box-shadow: 0 1px 3px rgba(15, 23, 42, 0.25);
        transition: box-shadow 120ms ease;
    }

    input[type="range"]:hover::-webkit-slider-thumb,
    input[type="range"]:focus-visible::-webkit-slider-thumb {
        box-shadow: 0 0 0 4px var(--gno-accent-soft), 0 1px 3px rgba(15, 23, 42, 0.25);
    }

    input[type="range"]:hover::-moz-range-thumb,
    input[type="range"]:focus-visible::-moz-range-thumb {
        box-shadow: 0 0 0 4px var(--gno-accent-soft), 0 1px 3px rgba(15, 23, 42, 0.25);
    }

    /* The knob's ring shows keyboard focus. */
    input[type="range"]:focus-visible {
        outline: none;
    }

/* Dialogs rise into place over a dimmed, softly blurred desktop; menus drop open. Used by the components' own CSS. */
@keyframes gno-dialog-in {
    from {
        opacity: 0;
        transform: translateY(6px) scale(0.985);
    }
}

@keyframes gno-menu-in {
    from {
        opacity: 0;
        transform: translateY(-3px);
    }
}

.content {
    padding-top: 1.1rem;
}

h1:focus {
    outline: none;
}

.valid.modified:not([type=checkbox]) {
    outline: 1px solid #26b050;
}

.invalid {
    outline: 1px solid #e50000;
}

.validation-message {
    color: #e50000;
}

.blazor-error-boundary {
    background: url(data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iNTYiIGhlaWdodD0iNDkiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiIG92ZXJmbG93PSJoaWRkZW4iPjxkZWZzPjxjbGlwUGF0aCBpZD0iY2xpcDAiPjxyZWN0IHg9IjIzNSIgeT0iNTEiIHdpZHRoPSI1NiIgaGVpZ2h0PSI0OSIvPjwvY2xpcFBhdGg+PC9kZWZzPjxnIGNsaXAtcGF0aD0idXJsKCNjbGlwMCkiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0yMzUgLTUxKSI+PHBhdGggZD0iTTI2My41MDYgNTFDMjY0LjcxNyA1MSAyNjUuODEzIDUxLjQ4MzcgMjY2LjYwNiA1Mi4yNjU4TDI2Ny4wNTIgNTIuNzk4NyAyNjcuNTM5IDUzLjYyODMgMjkwLjE4NSA5Mi4xODMxIDI5MC41NDUgOTIuNzk1IDI5MC42NTYgOTIuOTk2QzI5MC44NzcgOTMuNTEzIDI5MSA5NC4wODE1IDI5MSA5NC42NzgyIDI5MSA5Ny4wNjUxIDI4OS4wMzggOTkgMjg2LjYxNyA5OUwyNDAuMzgzIDk5QzIzNy45NjMgOTkgMjM2IDk3LjA2NTEgMjM2IDk0LjY3ODIgMjM2IDk0LjM3OTkgMjM2LjAzMSA5NC4wODg2IDIzNi4wODkgOTMuODA3MkwyMzYuMzM4IDkzLjAxNjIgMjM2Ljg1OCA5Mi4xMzE0IDI1OS40NzMgNTMuNjI5NCAyNTkuOTYxIDUyLjc5ODUgMjYwLjQwNyA1Mi4yNjU4QzI2MS4yIDUxLjQ4MzcgMjYyLjI5NiA1MSAyNjMuNTA2IDUxWk0yNjMuNTg2IDY2LjAxODNDMjYwLjczNyA2Ni4wMTgzIDI1OS4zMTMgNjcuMTI0NSAyNTkuMzEzIDY5LjMzNyAyNTkuMzEzIDY5LjYxMDIgMjU5LjMzMiA2OS44NjA4IDI1OS4zNzEgNzAuMDg4N0wyNjEuNzk1IDg0LjAxNjEgMjY1LjM4IDg0LjAxNjEgMjY3LjgyMSA2OS43NDc1QzI2Ny44NiA2OS43MzA5IDI2Ny44NzkgNjkuNTg3NyAyNjcuODc5IDY5LjMxNzkgMjY3Ljg3OSA2Ny4xMTgyIDI2Ni40NDggNjYuMDE4MyAyNjMuNTg2IDY2LjAxODNaTTI2My41NzYgODYuMDU0N0MyNjEuMDQ5IDg2LjA1NDcgMjU5Ljc4NiA4Ny4zMDA1IDI1OS43ODYgODkuNzkyMSAyNTkuNzg2IDkyLjI4MzcgMjYxLjA0OSA5My41Mjk1IDI2My41NzYgOTMuNTI5NSAyNjYuMTE2IDkzLjUyOTUgMjY3LjM4NyA5Mi4yODM3IDI2Ny4zODcgODkuNzkyMSAyNjcuMzg3IDg3LjMwMDUgMjY2LjExNiA4Ni4wNTQ3IDI2My41NzYgODYuMDU0N1oiIGZpbGw9IiNGRkU1MDAiIGZpbGwtcnVsZT0iZXZlbm9kZCIvPjwvZz48L3N2Zz4=) no-repeat 1rem/1.8rem, #b32121;
    padding: 1rem 1rem 1rem 3.7rem;
    color: white;
}

    .blazor-error-boundary::after {
        content: "An error has occurred."
    }

/* ---- printed pages (print.js): a sheet of paper with the drawing inside its margin. Always the light colours, and
        the drawing still and complete: no fade-in, no line drawing itself, no hover. ---- */

.gno-paper {
    --gno-surface: #ffffff;
    --gno-surface-2: #f8fafc;
    --gno-text: #0f172a;
    --gno-text-2: #1e293b;
    --gno-line: #111827;
    --gno-accent-fill: #eff6ff;
    position: relative;
    display: flex;
    box-sizing: border-box;
    max-width: 100%;
    background: #ffffff;
    color-scheme: light;
    print-color-adjust: exact;
    -webkit-print-color-adjust: exact;
}

/* The printable area, inside the margin. The clip cuts the drawing off at the margin; the frame (preview only) is not
   cut off, so a drawing dragged partly off the page can still be grabbed. */
.gno-paper__stage {
    position: relative;
    flex: 1 1 auto;
    min-width: 0;
    min-height: 0;
}

.gno-paper__clip {
    position: absolute;
    inset: 0;
    overflow: hidden;
}

.gno-paper .gno-paper__drawing {
    position: absolute;
    display: block;
    flex: none;
    min-height: 0;
    background: transparent;
    pointer-events: none;
}

.gno-paper__frame {
    position: absolute;
    box-sizing: border-box;
    border: 1.5px dashed var(--gno-paper-accent);
    cursor: move;
    touch-action: none;
}

.gno-paper__frame--outside {
    border: 2px solid #dc2626;
    background: rgba(220, 38, 38, 0.06);
}

.gno-paper__handle {
    position: absolute;
    width: 10px;
    height: 10px;
    margin: -5px;
    box-sizing: border-box;
    background: #ffffff;
    border: 1.5px solid var(--gno-paper-accent);
}

.gno-paper__frame--outside .gno-paper__handle {
    border-color: #dc2626;
}

.gno-paper__handle--nw { left: 0; top: 0; cursor: nwse-resize; }
.gno-paper__handle--ne { right: 0; top: 0; cursor: nesw-resize; }
.gno-paper__handle--sw { left: 0; bottom: 0; cursor: nesw-resize; }
.gno-paper__handle--se { right: 0; bottom: 0; cursor: nwse-resize; }

.gno-paper .genogram-canvas__fade,
.gno-paper .genogram-canvas__draw,
.gno-paper .genogram-canvas__relation-line,
.gno-paper .genogram-canvas__label,
.gno-paper .genogram-canvas__label-box {
    opacity: 1 !important;
    animation: none !important;
}

.gno-paper .genogram-canvas__draw {
    stroke-dasharray: none !important;
}

.gno-paper__number {
    position: absolute;
    right: 3mm;
    bottom: 2mm;
    font: 9px/1 'Helvetica Neue', Helvetica, Arial, sans-serif;
    color: #64748b;
}

.gno-print-root {
    display: none;
}

/* ---- menu and toolbar tooltips (tooltips.js): one div on the body, placed by script, faded in. Here rather than in a
   component's scoped CSS because the element is made by script, outside any component's markup. Above the menu
   dropdowns (300000). ---- */
.gno-tooltip {
    position: fixed;
    left: 0;
    top: 0;
    z-index: 400000;
    pointer-events: none;
    opacity: 0;
    transition: opacity 120ms ease-out;
    padding: 5px 9px;
    border-radius: 8px;
    font: 12px/1.3 'Helvetica Neue', Helvetica, Arial, sans-serif;
    /* Short tips stay on one line; a long one (the Live panel's Experimental badge) wraps instead of leaving the window. */
    max-width: min(320px, calc(100vw - 8px));
    width: max-content;
    background: var(--gno-text-strong);
    color: var(--gno-surface);
    box-shadow: var(--gno-pop-shadow);
    will-change: transform, opacity;
}

.gno-tooltip--visible {
    opacity: 1;
}

/* ---- the genogram's tooltips (genogramCanvas.js): one div on the body, moved by script. A plain tip is the menus'
   dark pill; the data tip of a person, family or emotional line is a card in the style of the tray and the Data Tips
   panel, frosted, rounded, softly shadowed. It shows the moment the pointer is on the item: the card fades and lifts
   into place, and fades out a little faster than it came. ---- */
.gno-canvas-tip {
    position: fixed;
    left: 0;
    top: 0;
    z-index: 400000;
    pointer-events: none;
    opacity: 0;
    transition: opacity 90ms ease-in;
    font: 12px/1.4 'Helvetica Neue', Helvetica, Arial, sans-serif;
    /* Each of the two buffers on a compositor layer of its own: moving one repaints nothing else. Not opacity as well:
       that would make it a backdrop root, and the card's frosted backdrop-filter would see nothing behind it. */
    will-change: transform;
}

.gno-canvas-tip--shown {
    opacity: 1;
    transition: none;
}

.gno-canvas-tip--plain {
    padding: 4px 8px;
    border-radius: 6px;
    white-space: nowrap;
    background: var(--gno-text-strong);
    color: var(--gno-surface);
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
}

    .gno-canvas-tip--plain.gno-canvas-tip--shown {
        animation: gno-tip-fade 120ms ease-out;
    }

@keyframes gno-tip-fade {
    from { opacity: 0; }
}

@keyframes gno-datatip-in {
    from {
        opacity: 0;
        transform: translateY(4px) scale(0.985);
    }
}

.gno-datatip__card {
    width: max-content;
    min-width: 196px;
    max-width: min(280px, calc(100vw - 16px));
    padding: 11px 13px 12px;
    background: color-mix(in srgb, var(--gno-surface) 88%, transparent);
    backdrop-filter: blur(18px) saturate(1.6);
    -webkit-backdrop-filter: blur(18px) saturate(1.6);
    border: 1px solid var(--gno-dock-edge);
    border-radius: 14px;
    box-shadow: var(--gno-pop-shadow), 0 0 0 0.5px var(--gno-guide);
    color: var(--gno-text);
    transform-origin: top left;
    animation: gno-datatip-in 150ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

@media (prefers-reduced-motion: reduce) {
    .gno-datatip__card {
        animation-name: gno-tip-fade;
    }
}

/* Symbol, then title, the line under it and the chips. */
.gno-datatip__head {
    display: flex;
    align-items: flex-start;
    gap: 10px;
}

.gno-datatip__glyph {
    flex: none;
    display: grid;
    place-items: center;
    width: 30px;
    height: 30px;
    border-radius: 9px;
    background: var(--gno-accent-soft);
    color: var(--gno-accent-text);
}

    .gno-datatip__glyph svg {
        width: 20px;
        height: 20px;
        fill: none;
        stroke: currentColor;
        stroke-width: 1.8;
        stroke-linecap: round;
        stroke-linejoin: round;
    }

    .gno-datatip__glyph .gno-datatip__cross {
        stroke-width: 1.6;
        opacity: 0.85;
    }

/* The person's picture: a set size, so the card is measured right before the image has loaded. */
.gno-datatip__photo {
    flex: none;
    width: 64px;
    height: 80px;
    overflow: hidden;
    border-radius: 8px;
    background: var(--gno-accent-soft);
    box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--gno-accent) 14%, transparent);
}

    .gno-datatip__photo img {
        display: block;
        width: 100%;
        height: 100%;
        object-fit: cover;
        object-position: 50% 25%;
    }

.gno-details .gno-datatip__photo {
    width: 128px;
    height: 160px;
    border-radius: 16px;
    box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--gno-accent) 14%, transparent), 0 6px 18px rgba(15, 23, 42, 0.14);
}

/* A picture hosted online that would not download: the frame says the link is broken, in place of the picture. */
.gno-datatip__photo--broken {
    position: relative;
    background: repeating-linear-gradient(135deg, rgba(154, 52, 18, 0.06) 0 8px, transparent 8px 16px), var(--gno-accent-soft);
    box-shadow: inset 0 0 0 1.5px rgba(154, 52, 18, 0.45);
}

.gno-datatip__photo--broken::after {
    content: "Broken link";
    position: absolute;
    inset: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 6px;
    text-align: center;
    font-size: 11px;
    font-weight: 600;
    line-height: 1.25;
    color: #9a3412;
}

/* A picture on its way: the frame shimmers while the app or the browser fetches it. */
.gno-datatip__photo--loading {
    background: linear-gradient(100deg, var(--gno-accent-soft) 35%, color-mix(in srgb, var(--gno-surface) 75%, var(--gno-accent-soft)) 50%, var(--gno-accent-soft) 65%);
    background-size: 250% 100%;
    animation: gno-photo-shimmer 1.4s linear infinite;
}

@keyframes gno-photo-shimmer {
    from {
        background-position: 100% 0;
    }

    to {
        background-position: -100% 0;
    }
}

@media (prefers-reduced-motion: reduce) {
    .gno-datatip__photo--loading {
        animation: none;
    }
}

.gno-datatip__heading {
    flex: 1;
    min-width: 0;
    padding-top: 1px;
}

.gno-datatip__title {
    color: var(--gno-text-strong);
    font-size: 13.5px;
    font-weight: 650;
    line-height: 1.25;
    letter-spacing: -0.005em;
    overflow-wrap: anywhere;
}

.gno-datatip__title--to {
    display: flex;
    gap: 0.35em;
    margin-top: 1px;
}

.gno-datatip__arrow {
    flex: none;
    color: var(--gno-muted-2);
    font-weight: 500;
}

.gno-datatip__sub {
    margin-top: 2px;
    color: var(--gno-muted);
    font-size: 11.5px;
    line-height: 1.35;
    font-variant-numeric: tabular-nums;
}

/* With nothing above them, the chips sit level with the middle of the symbol. */
.gno-datatip__chips {
    display: flex;
    flex-wrap: wrap;
    gap: 4px;
    margin-top: 6px;
}

    .gno-datatip__heading > .gno-datatip__chips:first-child {
        margin-top: 4px;
    }

/* The search term in a data tip, during a search on the canvas (the beta review). */
.gno-datatip__hit {
    padding: 0 1px;
    border-radius: 2px;
    background: #ffe066;
    color: #111;
}

.gno-datatip__chip {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    padding: 1px 8px;
    border-radius: 999px;
    background: var(--gno-accent-soft);
    color: var(--gno-accent-text);
    font-size: 10.5px;
    font-weight: 600;
    line-height: 16px;
    white-space: nowrap;
}

/* An emotional line's chip is neutral, so its red, green or blue sample reads true. */
.gno-datatip--emotional .gno-datatip__chip {
    background: var(--gno-surface-3);
    box-shadow: inset 0 0 0 1px var(--gno-guide);
    color: var(--gno-text-2);
}

.gno-datatip__swatch svg {
    display: block;
    width: 38px;
    height: 7px;
    overflow: visible;
}

/* The other fields: those of the item itself first, then a small heading per group. */
.gno-datatip__body {
    display: flex;
    flex-direction: column;
    gap: 9px;
    margin-top: 10px;
    padding-top: 9px;
    border-top: 1px solid var(--gno-guide);
}

.gno-datatip__section-title {
    display: flex;
    align-items: center;
    gap: 5px;
    margin-bottom: 3px;
    color: var(--gno-muted-2);
    font-size: 10px;
    font-weight: 700;
    letter-spacing: 0.07em;
    text-transform: uppercase;
}

.gno-datatip__index {
    padding: 0 5px;
    border-radius: 999px;
    background: var(--gno-surface-3);
    color: var(--gno-muted);
    font-size: 9.5px;
    letter-spacing: 0;
    line-height: 14px;
}

.gno-datatip__subhead {
    margin: 5px 0 2px calc(var(--depth, 0) * 8px);
    color: var(--gno-text-2);
    font-size: 11px;
    font-weight: 650;
}

.gno-datatip__grid {
    display: grid;
    grid-template-columns: minmax(58px, max-content) minmax(0, 1fr);
    column-gap: 12px;
    row-gap: 3px;
    align-items: baseline;
    margin-left: calc(var(--depth, 0) * 8px);
}

.gno-datatip__label {
    color: var(--gno-muted);
    font-size: 11.5px;
    white-space: nowrap;
}

.gno-datatip__value {
    color: var(--gno-text-strong);
    font-size: 12px;
    font-weight: 500;
    /* A list (parents, children, sources) is one item per line. */
    white-space: pre-line;
    overflow-wrap: anywhere;
    font-variant-numeric: tabular-nums;
}

/* Running text: its label above it, across the card, four lines at most. */
.gno-datatip__label--prose,
.gno-datatip__value--prose {
    grid-column: 1 / -1;
}

.gno-datatip__label--prose {
    margin-top: 2px;
}

.gno-datatip__value--prose {
    display: -webkit-box;
    -webkit-box-orient: vertical;
    -webkit-line-clamp: 4;
    overflow: hidden;
    color: var(--gno-text-2);
    font-weight: 400;
    line-height: 1.45;
}

/* A card lingers a moment after the pointer leaves its item, and takes the pointer then, so its links can be clicked. */
.gno-canvas-tip--shown.gno-canvas-tip--live {
    pointer-events: auto;
}

/* A person, family or line named in a card: opens it in the details window. */
.gno-datatip__ref {
    color: inherit;
    text-decoration: underline;
    text-decoration-color: color-mix(in srgb, currentColor 28%, transparent);
    text-decoration-thickness: 1px;
    text-underline-offset: 2.5px;
    cursor: pointer;
    transition: color 120ms, text-decoration-color 120ms;
}

    .gno-datatip__ref:hover {
        color: var(--gno-accent-text);
        text-decoration-color: currentColor;
    }

/* A web or email address: opens it in a new tab. */
.gno-datatip__url {
    color: var(--gno-accent-text);
    text-decoration: none;
    background-image: linear-gradient(currentColor, currentColor);
    background-size: 100% 1px;
    background-position: 0 100%;
    background-repeat: no-repeat;
    opacity: 0.92;
    transition: opacity 120ms;
}

    .gno-datatip__url:hover {
        opacity: 1;
        background-size: 100% 1.5px;
    }

.gno-datatip__amp {
    color: var(--gno-muted-2);
    font-weight: 500;
}

/* ---- the details window (genogramCanvas.js): double-clicking a person, family or emotional line. The data tip's card
   grown into a window in the middle of the map, on the tray's frosted glass: a slim bar with the trail's back and
   forward and the close button, a header with the item's symbol, name and picture, then every field it has in soft
   panels that flow in two columns, the people it names as pills to click through. The stage is the map's frame laid on
   the page; the window sits in its centre, so it stays centred as its page changes height. The scrim only catches
   clicks outside; the canvas dims itself round its spotlight. ---- */
.gno-details-scrim {
    position: fixed;
    inset: 0;
    z-index: 349000;
}

.gno-details-stage {
    position: fixed;
    left: 0;
    top: 0;
    z-index: 350000;
    display: grid;
    place-items: center;
    pointer-events: none;
}

.gno-details {
    position: relative;
    display: flex;
    flex-direction: column;
    width: min(820px, calc(100% - 48px));
    max-height: calc(100% - 48px);
    overflow: hidden;
    pointer-events: auto;
    background: color-mix(in srgb, var(--gno-surface) 92%, transparent);
    backdrop-filter: blur(28px) saturate(1.7);
    -webkit-backdrop-filter: blur(28px) saturate(1.7);
    border: 1px solid var(--gno-dock-edge);
    border-radius: 20px;
    box-shadow: var(--gno-modal-shadow), 0 0 0 0.5px var(--gno-guide);
    color: var(--gno-text);
    font: 13px/1.45 'Helvetica Neue', Helvetica, Arial, sans-serif;
    outline: none;
    transform-origin: center;
    animation: gno-details-in 280ms cubic-bezier(0.2, 0.9, 0.25, 1);
}

    /* A wash of the accent behind the header, fading out down the panel. */
    .gno-details::before {
        content: '';
        position: absolute;
        inset: 0 0 auto 0;
        height: 220px;
        background: radial-gradient(75% 100% at 12% 0%, var(--gno-accent-soft), transparent 70%);
        pointer-events: none;
    }

/* A narrow screen: a sheet along the bottom of it. */
.gno-details-stage--sheet {
    place-items: end center;
}

.gno-details--sheet {
    width: calc(100% - 16px);
    max-height: 72vh;
    margin-bottom: 8px;
    transform-origin: bottom center;
}

.gno-details--closing {
    animation: gno-details-out 160ms ease-in forwards;
    pointer-events: none;
}

@keyframes gno-details-in {
    from {
        opacity: 0;
        transform: translateY(10px) scale(0.96);
    }
}

@keyframes gno-details-out {
    to {
        opacity: 0;
        transform: translateY(4px) scale(0.98);
    }
}

/* The bar: the trail's buttons, what kind of item the page is, and the close button at the far end. */
.gno-details__bar {
    position: relative;
    flex: none;
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 12px 12px 0 12px;
}

.gno-details__nav {
    display: flex;
    gap: 2px;
    padding: 2px;
    border-radius: 11px;
    background: color-mix(in srgb, var(--gno-surface-3) 70%, transparent);
    box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--gno-guide) 60%, transparent);
}

.gno-details__button {
    display: grid;
    place-items: center;
    width: 30px;
    height: 30px;
    padding: 0;
    border: 0;
    border-radius: 9px;
    background: transparent;
    color: var(--gno-muted);
    cursor: pointer;
    transition: background-color 120ms, color 120ms, opacity 120ms, transform 80ms;
}

    .gno-details__button svg {
        width: 16px;
        height: 16px;
        fill: none;
        stroke: currentColor;
        stroke-width: 1.7;
        stroke-linecap: round;
        stroke-linejoin: round;
    }

    .gno-details__button:hover:not(:disabled) {
        background: var(--gno-surface);
        color: var(--gno-text-strong);
        box-shadow: 0 1px 2px rgba(15, 23, 42, 0.08);
    }

    .gno-details__button:active:not(:disabled) {
        transform: translateY(0.5px);
    }

    .gno-details__button:focus-visible {
        outline: 2px solid var(--gno-accent);
        outline-offset: 1px;
    }

    .gno-details__button:disabled {
        opacity: 0.3;
        cursor: default;
    }

.gno-details__button--close {
    margin-left: auto;
    width: 32px;
    height: 32px;
    border-radius: 999px;
}

    .gno-details__button--close:hover:not(:disabled) {
        background: var(--gno-row-hover);
        box-shadow: none;
    }

.gno-details__kind {
    margin-left: 4px;
    color: var(--gno-muted-2);
    font-size: 11px;
    font-weight: 700;
    letter-spacing: 0.09em;
    text-transform: uppercase;
}

.gno-details__where {
    padding: 2px 9px;
    border-radius: 999px;
    background: var(--gno-surface-3);
    box-shadow: inset 0 0 0 1px var(--gno-guide);
    color: var(--gno-muted);
    font-size: 10.5px;
    font-weight: 600;
    line-height: 16px;
}

    .gno-details__where[hidden] {
        display: none;
    }

.gno-details__body {
    position: relative;
    flex: 1 1 auto;
    min-height: 0;
    overflow: hidden auto;
    overscroll-behavior: contain;
    padding: 0 24px 24px;
    scrollbar-width: thin;
    scrollbar-gutter: stable;
    transition: height 280ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

.gno-details__page {
    padding-top: 12px;
}

.gno-details__page--from-right {
    animation: gno-page-from-right 280ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

.gno-details__page--from-left {
    animation: gno-page-from-left 280ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

.gno-details__page--out {
    position: absolute;
    left: 24px;
    right: 24px;
    pointer-events: none;
}

.gno-details__page--to-left {
    animation: gno-page-to-left 200ms ease-in forwards;
}

.gno-details__page--to-right {
    animation: gno-page-to-right 200ms ease-in forwards;
}

@keyframes gno-page-from-right {
    from {
        opacity: 0;
        transform: translateX(24px);
    }
}

@keyframes gno-page-from-left {
    from {
        opacity: 0;
        transform: translateX(-24px);
    }
}

@keyframes gno-page-to-left {
    to {
        opacity: 0;
        transform: translateX(-24px);
    }
}

@keyframes gno-page-to-right {
    to {
        opacity: 0;
        transform: translateX(24px);
    }
}

@media (prefers-reduced-motion: reduce) {
    .gno-details,
    .gno-details__page--from-right,
    .gno-details__page--from-left {
        animation: gno-tip-fade 160ms ease-out;
    }

    .gno-details__body {
        transition: none;
    }
}

/* The card inside the window: no frame of its own, and everything a size up. */
.gno-details .gno-datatip__card {
    width: auto;
    min-width: 0;
    max-width: none;
    padding: 0;
    background: none;
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
    border: 0;
    border-radius: 0;
    box-shadow: none;
    animation: none;
}

/* The header: the symbol, the name with its dates and chips, and the picture at the far side. */
.gno-details .gno-datatip__head {
    align-items: center;
    gap: 20px;
    padding: 6px 4px 0;
}

.gno-details .gno-datatip__glyph {
    width: 60px;
    height: 60px;
    border-radius: 18px;
    background: linear-gradient(160deg, color-mix(in srgb, var(--gno-accent) 22%, transparent), var(--gno-accent-soft));
    box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--gno-accent) 20%, transparent), 0 4px 12px var(--gno-accent-soft);
}

    .gno-details .gno-datatip__glyph svg {
        width: 34px;
        height: 34px;
        stroke-width: 1.5;
    }

.gno-details .gno-datatip__heading {
    padding-top: 0;
}

.gno-details .gno-datatip__title {
    font-size: 26px;
    font-weight: 700;
    line-height: 1.12;
    letter-spacing: -0.018em;
}

.gno-details .gno-datatip__title--to {
    margin-top: 3px;
}

.gno-details .gno-datatip__title .gno-datatip__ref {
    text-decoration-color: color-mix(in srgb, currentColor 22%, transparent);
    text-decoration-thickness: 1.5px;
    text-underline-offset: 5px;
}

    .gno-details .gno-datatip__title .gno-datatip__ref:hover {
        text-decoration-color: currentColor;
    }

.gno-details .gno-datatip__sub {
    margin-top: 5px;
    font-size: 14px;
    line-height: 1.4;
}

.gno-details .gno-datatip__chips {
    gap: 6px;
    margin-top: 10px;
}

.gno-details .gno-datatip__chip {
    padding: 3px 11px;
    font-size: 11.5px;
    line-height: 18px;
}

.gno-details .gno-datatip__swatch svg {
    width: 52px;
    height: 9px;
}

/* The fields: each group (and the item's own fields before them) on a soft panel of its own. The panels flow in two
   columns where the window is wide enough; the item's own fields run across both, two to a row. */
.gno-details .gno-datatip__body {
    display: block;
    columns: 300px 2;
    column-gap: 14px;
    margin-top: 22px;
    padding-top: 0;
    border-top: 0;
}

    .gno-details .gno-datatip__section,
    .gno-details .gno-datatip__body > .gno-datatip__grid {
        break-inside: avoid;
        margin-bottom: 14px;
        padding: 13px 16px 14px;
        border-radius: 14px;
        background: color-mix(in srgb, var(--gno-surface-3) 60%, transparent);
        box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--gno-guide) 60%, transparent);
    }

    .gno-details .gno-datatip__body > :last-child {
        margin-bottom: 0;
    }

    .gno-details .gno-datatip__body > .gno-datatip__grid {
        column-span: all;
        grid-template-columns: repeat(2, minmax(96px, max-content) minmax(0, 1fr));
        column-gap: 18px;
    }

.gno-details .gno-datatip__section-title {
    gap: 6px;
    margin-bottom: 9px;
    font-size: 10.5px;
    letter-spacing: 0.09em;
}

.gno-details .gno-datatip__index {
    font-size: 10px;
    line-height: 15px;
}

.gno-details .gno-datatip__subhead {
    margin: 10px 0 4px calc(var(--depth, 0) * 12px);
    font-size: 12.5px;
}

.gno-details .gno-datatip__grid {
    grid-template-columns: minmax(96px, max-content) minmax(0, 1fr);
    column-gap: 16px;
    row-gap: 7px;
    margin-left: calc(var(--depth, 0) * 12px);
}

.gno-details .gno-datatip__label {
    font-size: 12.5px;
}

.gno-details .gno-datatip__value {
    font-size: 13.5px;
}

/* The person's other pictures: a strip across the window, each with its name under it. */
.gno-details .gno-datatip__gallery {
    column-span: all;
}

.gno-datatip__shots {
    display: flex;
    flex-wrap: wrap;
    gap: 14px;
}

.gno-datatip__shot {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
    width: 112px;
    margin: 0;
}

.gno-details .gno-datatip__shot .gno-datatip__photo {
    width: 112px;
    height: 140px;
    border-radius: 12px;
}

.gno-datatip__shot-caption {
    max-width: 100%;
    overflow: hidden;
    color: var(--gno-muted);
    font-size: 12px;
    line-height: 1.3;
    text-align: center;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* Running text in full, not cut short as in a tip. */
.gno-details .gno-datatip__value--prose {
    display: block;
    overflow: visible;
    font-size: 13.5px;
    line-height: 1.55;
}

/* A field of people: its label in the first column and the pills across the rest of the row. */
.gno-details .gno-datatip__label--wide {
    grid-column: 1;
}

.gno-details .gno-datatip__value--wide {
    grid-column: 2 / -1;
}

/* The people a field names: pills that wrap, each with the person's symbol. */
.gno-datatip__value--refs {
    display: flex;
    flex-wrap: wrap;
    gap: 6px;
    white-space: normal;
}

.gno-datatip__ref--pill {
    display: inline-flex;
    align-items: center;
    gap: 7px;
    max-width: 100%;
    padding: 3px 10px 3px 3px;
    border-radius: 999px;
    background: var(--gno-surface);
    box-shadow: inset 0 0 0 1px var(--gno-guide), 0 1px 2px rgba(15, 23, 42, 0.06);
    color: var(--gno-text-strong);
    font-size: 13px;
    font-weight: 550;
    line-height: 20px;
    text-decoration: none;
    transition: background-color 140ms, box-shadow 140ms, color 140ms, transform 140ms;
}

    .gno-datatip__ref--pill > span:last-child {
        overflow: hidden;
        text-overflow: ellipsis;
        white-space: nowrap;
    }

    .gno-datatip__ref--pill:not(:has(> .gno-datatip__ref-glyph)) {
        padding-left: 10px;
    }

    .gno-datatip__ref--pill::after {
        content: '';
        flex: none;
        width: 5px;
        height: 5px;
        margin-left: 1px;
        border-top: 1.5px solid currentColor;
        border-right: 1.5px solid currentColor;
        transform: rotate(45deg);
        opacity: 0.35;
        transition: opacity 140ms, transform 140ms;
    }

    .gno-datatip__ref--pill:hover {
        background: var(--gno-accent-fill);
        box-shadow: inset 0 0 0 1px var(--gno-active-border), 0 2px 6px var(--gno-accent-soft);
        color: var(--gno-accent-hover-text);
        transform: translateY(-1px);
    }

        .gno-datatip__ref--pill:hover::after {
            opacity: 0.8;
            transform: translateX(1.5px) rotate(45deg);
        }

    .gno-datatip__ref--pill:focus-visible {
        outline: 2px solid var(--gno-accent);
        outline-offset: 1px;
    }

.gno-datatip__ref-glyph {
    flex: none;
    display: grid;
    place-items: center;
    width: 20px;
    height: 20px;
    border-radius: 999px;
    background: var(--gno-accent-soft);
    color: var(--gno-accent-text);
}

    .gno-datatip__ref-glyph svg {
        width: 13px;
        height: 13px;
        fill: none;
        stroke: currentColor;
        stroke-width: 2.2;
        stroke-linecap: round;
        stroke-linejoin: round;
    }

/* ---- the spotlight on the canvas while the details window is open (genogramCanvas.js): the drawing dims round the
   item, which sits in a soft-edged hole with a ring that breathes. It glides when a link is followed. ---- */
.genogram-canvas__spot {
    opacity: 0;
    transition: opacity 240ms ease-out;
}

    .genogram-canvas__spot[data-on] {
        opacity: 1;
    }

.genogram-canvas__spot-veil {
    fill: var(--gno-scrim);
    opacity: 0.5;
}

.genogram-canvas__spot-ring,
.genogram-canvas__spot-halo {
    fill: none;
    vector-effect: non-scaling-stroke;
    transform-box: fill-box;
    transform-origin: center;
}

.genogram-canvas__spot-ring {
    stroke: var(--gno-accent);
    stroke-width: 2.25px;
}

.genogram-canvas__spot-halo {
    stroke: var(--gno-accent-glow);
    stroke-width: 9px;
    animation: gno-spot-breathe 2.6s ease-in-out infinite;
}

.genogram-canvas__spot[data-on] .genogram-canvas__spot-ring {
    animation: gno-spot-in 460ms cubic-bezier(0.2, 0.9, 0.25, 1.15);
}

@keyframes gno-spot-breathe {
    50% {
        stroke-opacity: 0.4;
        stroke-width: 15px;
    }
}

@keyframes gno-spot-in {
    from {
        opacity: 0;
        transform: scale(1.7);
    }
}

@media (prefers-reduced-motion: reduce) {
    .genogram-canvas__spot-halo,
    .genogram-canvas__spot[data-on] .genogram-canvas__spot-ring {
        animation: none;
    }
}

@media print {
    html.gno-printing,
    html.gno-printing body {
        height: auto;
        overflow: visible;
        background: #ffffff;
    }

    html.gno-printing body > :not(.gno-print-root) {
        display: none !important;
    }

    html.gno-printing .gno-print-root {
        display: block;
    }

    .gno-print-root .gno-paper {
        max-width: none;
        break-after: page;
        overflow: hidden;
    }

    .gno-print-root .gno-paper:last-child {
        break-after: auto;
    }
}

.form-floating > .form-control-plaintext::placeholder, .form-floating > .form-control::placeholder {
    color: var(--bs-secondary-color);
    text-align: end;
}

.form-floating > .form-control-plaintext:focus::placeholder, .form-floating > .form-control:focus::placeholder {
    text-align: start;
}

/* ---- dragging a tab along its row: a file tab on the bottom tray, or a GenoMap tab along the foot of a window
   (tabDrag.js, Home.razor.css). The script makes the floating copy of the tab and the drop bar, so their look lives
   here rather than in Home's scoped styles. ---- */

/* Cursors for the tabs: a grip with arrows either way says "drag me sideways"; it fills with the accent while a tab
   is held, and greys out with a "no" badge where letting go would put the tab back. Hotspot in the middle. */
:root {
    --gno-cursor-grab: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='white' stroke-width='4'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%230f172a' stroke-width='1.75'/></g><rect x='8' y='10.5' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.2'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='white' stroke='%230f172a' stroke-width='1.5'/><g fill='%231e40af'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grab;
    --gno-cursor-grabbing: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='white' stroke-width='4.5'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%232563eb' stroke-width='2'/></g><rect x='8' y='11' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.25'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%232563eb' stroke='white' stroke-width='1.5'/><g fill='white'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grabbing;
    --gno-cursor-nodrop: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><rect x='8' y='10.5' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.2'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%23f1f5f9' stroke='%2364748b' stroke-width='1.5'/><g fill='%2394a3b8'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g><circle cx='23.5' cy='23.5' r='6' fill='white' stroke='%23dc2626' stroke-width='2'/><path d='M19.5 19.5 27.5 27.5' stroke='%23dc2626' stroke-width='2' stroke-linecap='round'/></svg>") 16 16, no-drop;
}

/* Bumblebee's grip is black with yellow dots, and fills yellow with black dots while held. */
[data-theme="bumblebee"] {
    --gno-cursor-grab: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='white' stroke-width='4'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%23111111' stroke-width='1.75'/></g><rect x='8' y='10.5' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.3'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%23111111' stroke='white' stroke-width='1.5'/><g fill='%23facc15'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grab;
    --gno-cursor-grabbing: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%23111111' stroke-width='4.5'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%23facc15' stroke-width='2'/></g><rect x='8' y='11' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.35'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%23facc15' stroke='%23111111' stroke-width='1.5'/><g fill='%23111111'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grabbing;
}

/* Ember's is the same grip in its gold. */
[data-theme="ember"] {
    --gno-cursor-grab: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='white' stroke-width='4'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%231a1208' stroke-width='1.75'/></g><rect x='8' y='10.5' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.3'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%231a1208' stroke='white' stroke-width='1.5'/><g fill='%23efb72e'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grab;
    --gno-cursor-grabbing: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%231a1208' stroke-width='4.5'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%23efb72e' stroke-width='2'/></g><rect x='8' y='11' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.35'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%23efb72e' stroke='%231a1208' stroke-width='1.5'/><g fill='%231a1208'><circle cx='13.5' cy='13' r='1.35'/><circle cx='18.5' cy='13' r='1.35'/><circle cx='13.5' cy='16' r='1.35'/><circle cx='18.5' cy='16' r='1.35'/><circle cx='13.5' cy='19' r='1.35'/><circle cx='18.5' cy='19' r='1.35'/></g></svg>") 16 16, grabbing;
}

/* Pride's grip is plum black with its dots in the trans flag's stripes, and fills pink with blue arrows while held. */
[data-theme="pride"] {
    --gno-cursor-grab: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='white' stroke-width='4'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%232a0f18' stroke-width='1.75'/></g><rect x='8' y='10.5' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.3'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%232a0f18' stroke='white' stroke-width='1.5'/><circle cx='13.5' cy='13' r='1.35' fill='%235bcefa'/><circle cx='18.5' cy='13' r='1.35' fill='%235bcefa'/><circle cx='13.5' cy='16' r='1.35' fill='%23ffffff'/><circle cx='18.5' cy='16' r='1.35' fill='%23ffffff'/><circle cx='13.5' cy='19' r='1.35' fill='%23f5a9b8'/><circle cx='18.5' cy='19' r='1.35' fill='%23f5a9b8'/></svg>") 16 16, grab;
    --gno-cursor-grabbing: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='32' height='32' viewBox='0 0 32 32'><g fill='none' stroke-linecap='round' stroke-linejoin='round'><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%232a0f18' stroke-width='4.5'/><path d='M5 12.5 1.75 16 5 19.5M27 12.5 30.25 16 27 19.5' stroke='%235bcefa' stroke-width='2'/></g><rect x='8' y='11' width='16' height='13' rx='4.5' fill='%23000' fill-opacity='.35'/><rect x='8' y='9.5' width='16' height='13' rx='4.5' fill='%23f5a9b8' stroke='%232a0f18' stroke-width='1.5'/><circle cx='13.5' cy='13' r='1.35' fill='%232a0f18'/><circle cx='18.5' cy='13' r='1.35' fill='%232a0f18'/><circle cx='13.5' cy='16' r='1.35' fill='%232a0f18'/><circle cx='18.5' cy='16' r='1.35' fill='%232a0f18'/><circle cx='13.5' cy='19' r='1.35' fill='%232a0f18'/><circle cx='18.5' cy='19' r='1.35' fill='%232a0f18'/></svg>") 16 16, grabbing;
}

/* While a tab is held the cursor stays the held one wherever it goes, and nothing selects or shows its tooltip. */
html.tab-drag-active .gno-tooltip {
    opacity: 0 !important;
}

html.tab-drag-active,
html.tab-drag-active * {
    cursor: var(--gno-cursor-grabbing) !important;
    user-select: none !important;
}

html.tab-drag-active.tab-drag-nodrop,
html.tab-drag-active.tab-drag-nodrop * {
    cursor: var(--gno-cursor-nodrop) !important;
}

/* The other tabs of the row ignore the pointer while one is held: no hover lift as the copy passes over them. */
.tab-row--dragging > [data-key]:not(.tab-row__item--lifted) {
    pointer-events: none;
}

/* The tab under the pointer: a lifted copy of it, tilted a touch as if picked up. The outer box follows the pointer;
   the inner one fades and scales in and out. It holds the tab's own content, in the tab's shape (the script copies the
   padding, radius and type size), with the lifted look from here. */
.tab-ghost {
    position: fixed;
    left: 0;
    top: 0;
    z-index: 2147483000;
    pointer-events: none;
    will-change: transform;
}

.tab-ghost__tab {
    display: inline-flex;
    align-items: center;
    box-sizing: border-box;
    background: var(--gno-surface);
    color: var(--gno-accent-text);
    font-weight: 600;
    white-space: nowrap;
    box-shadow: 0 0 0 1px var(--gno-accent-soft), 0 14px 30px rgba(15, 23, 42, 0.24), 0 3px 8px rgba(15, 23, 42, 0.12);
    opacity: 0;
    transform: scale(0.94) rotate(0deg);
    transition: opacity 130ms ease, transform 160ms cubic-bezier(0.2, 0.8, 0.2, 1), filter 130ms ease, box-shadow 130ms ease;
}

.tab-ghost--shown .tab-ghost__tab {
    opacity: 0.95;
    transform: scale(1.04) rotate(-2deg);
}

/* Dragged away from the row: letting go would put the tab back, so the copy fades and loses its colour. */
.tab-ghost--nodrop .tab-ghost__tab {
    opacity: 0.6;
    filter: grayscale(1);
    transform: scale(0.98) rotate(0deg);
    box-shadow: 0 8px 20px rgba(15, 23, 42, 0.16);
}

/* Where the tab will go: an upright accent bar in the gap between two tabs, capped with a dot at each end, sliding
   from gap to gap as the pointer moves. Hidden over the tab's own place, where a drop would change nothing. */
/* Fixed on the page (placed by the script from the tabs' boxes), so it never sits among Blazor's own elements; above the
   lifted tab, which would otherwise hide it when the pointer is right on the gap. */
.tab-drop-bar {
    position: fixed;
    top: 0;
    left: 0;
    z-index: 2147483001;
    width: 3px;
    height: 24px;
    margin-left: -1.5px;
    border-radius: 2px;
    background: var(--gno-accent);
    box-shadow: 0 0 0 3px var(--gno-accent-soft), 0 0 12px var(--gno-accent-glow);
    pointer-events: none;
    opacity: 0;
    transform: scaleY(0.4);
    transition: opacity 120ms ease, transform 160ms cubic-bezier(0.2, 0.8, 0.2, 1), left 120ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

.tab-drop-bar::before,
.tab-drop-bar::after {
    content: "";
    position: absolute;
    left: 50%;
    width: 7px;
    height: 7px;
    margin-left: -3.5px;
    border-radius: 50%;
    background: var(--gno-accent);
    box-shadow: 0 0 0 2px var(--gno-surface);
}

.tab-drop-bar::before {
    top: -3px;
}

.tab-drop-bar::after {
    bottom: -3px;
}

.tab-drop-bar--shown {
    opacity: 1;
    transform: scaleY(1);
}

/* The bar's first placement jumps straight to its gap; only later moves slide. */
.tab-drop-bar--placing {
    transition: opacity 120ms ease, transform 160ms cubic-bezier(0.2, 0.8, 0.2, 1);
}

@media (prefers-reduced-motion: reduce) {
    .tab-ghost__tab,
    .tab-drop-bar {
        transition-duration: 1ms;
    }
}
/* ---- text that keeps one size in every language (L.Stable): each language's version sits in the same grid cell and
   only the one in force shows, so the box is as wide and as tall as the longest. Switching the language then moves
   no button, menu or dialog. */
.l10n {
    display: inline-grid;
    max-width: 100%;
}

/* No min-width: 0 here: a label must keep its longest version's width when a menu measures its smallest size,
   or the menu shrinks to its minimum and the longer items are cut off. */
.l10n > * {
    grid-area: 1 / 1;
}

.l10n > [aria-hidden] {
    visibility: hidden;
    pointer-events: none;
}

/* The genogram drawing keeps its own direction whatever the interface's: right to left (Arabic, Urdu) mirrors the
   menus and panels, but a name's text anchors and the drawing's labels stay as GenoPro drew them. SVG ignores the
   dir attribute; direction is the property it honours. The print preview's copy has the same class. */
svg.genogram-canvas {
    direction: ltr;
}
