/* ========== ROOT VARIABLES ========== */
:root {
    /* Background — deep plum, warm candy night */
    --color-bg: #120a14;
    /* Primary — candy pink (interactive chrome, CTAs, active states) */
    --color-primary: #EBADFF;
    --color-primary-light: #F8DEFF;
    --color-primary-dark: #2A0031;
    --color-primary-darker: #1a001f;
    /* Accent */
    --color-accent: #EBADFF;
    --color-accent-dark: #2A0031;
    /* Win */
    --color-win-gold: #FFDAFE;
    --color-win-gold-light: #FFF0FC;
    /* Text */
    --color-text: #ffffff;
    --color-text-muted: #e0c8d8;
    --color-text-dim: #b09aae;
    /* Overlay */
    --color-overlay-dark: rgba(0, 0, 0, 0.5);
    --color-overlay-light: rgba(0, 0, 0, 0.3);
    /* Glass — warm pink-tinted borders */
    --color-glass-border: rgba(255, 120, 180, 0.12);
    --color-glass-border-hover: rgba(255, 120, 180, 0.25);
    --color-glass-highlight: rgba(255, 200, 230, 0.2);
    --color-gold-subtle: rgba(235, 173, 255, 0.05);
    --color-gold-glow: rgba(235, 173, 255, 0.3);
    /* Gold glow */
    --color-gold-glow-strong: rgba(235, 173, 255, 0.35);
}

/* ========== BODY ========== */
body {
    margin: 0;
    padding: 0;
    overflow: hidden;
    background-color: #120a14;
    font-family: var(--sui-font);
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
    -webkit-tap-highlight-color: transparent;
    -webkit-touch-callout: none;
    -webkit-user-select: none;
    user-select: none;
    touch-action: manipulation;
}

/* ========== GAME HEADER ========== */
#game-header {
    position: fixed;
    top: 0.4vw;
    left: var(--safe-left, 0px);
    z-index: 1000;
    pointer-events: none;
    display: none !important; /* hide top-left game name + (already-removed) clock area, per request */
    flex-direction: row;
    align-items: center;
    gap: 0;
    background: transparent;
    border-radius: 6px;
    padding: 0.2vw 0.6vw;
    border: none;
}

/* Portrait: pin header to the viewport's true top-left (left: 0)
   instead of going through --safe-left. On tablets like iPad
   (985×1173) safe-left can compute to ~160px which pushes the
   brand text well off the corner — producer wanted it visibly at
   the screen corner. */
@media (orientation: portrait) {
    #game-header {
        left: 0 !important;
        transform: none !important;
    }
}

/* Ultrawide: hide the brand text when viewport has L/R letterbox
   bars (resizer toggles `.viewport-has-letterbox` on <html> when
   viewportAspect > bg's native aspect). Producer spec: "如果是超宽
   屏幕 左右有黑边, 那 game name 就不显示" — cleaner than trying to
   pixel-perfect-anchor the text to the bg edge. */
html.viewport-has-letterbox #game-header {
    display: none !important;
}

#game-title {
    font-family: var(--sui-font);
    /* 60% of the previous size (was clamp(7px, 0.8vw, 11px)) per
       producer feedback — clock removed, brand text now lives here. */
    font-size: clamp(4px, 0.48vw, 7px);
    font-weight: 700;
    color: rgba(255, 255, 255, 0.85);
    text-shadow: 0 1px 4px rgba(0, 0, 0, 0.6);
    letter-spacing: 0.1em;
    text-transform: uppercase;
    white-space: nowrap;
    padding-right: 0.5vw;
}


#app-container {
    -webkit-transform: translateZ(0);
    transform: translateZ(0);
    -webkit-backface-visibility: hidden;
    backface-visibility: hidden;
}

/* ========== CANDY MODAL (Paytable) ========== */
.candy-modal-overlay {
    position: fixed;
    inset: 0;
    background: rgba(80, 30, 60, 0.4);
    z-index: 10000;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 20px;
    animation: fadeIn 0.3s ease-out;
}

.candy-modal {
    background: linear-gradient(160deg, #8a4570 0%, #7a3d65 50%, #6a3558 100%);
    border-radius: 16px;
    border: 1.5px solid rgba(255, 105, 180, 0.35);
    box-shadow:
        0 0 0 1px rgba(235, 173, 255, 0.08),
        0 8px 32px rgba(0, 0, 0, 0.45),
        inset 0 1px 0 rgba(235, 173, 255, 0.12);
    position: relative;
    overflow: hidden;
}

.candy-modal-header {
    padding: 18px 24px;
    border-bottom: 1px solid rgba(255, 105, 180, 0.2);
    background: linear-gradient(180deg, rgba(255, 105, 180, 0.12) 0%, rgba(255, 105, 180, 0.03) 100%);
}

.candy-modal-header h2 {
    margin: 0;
    font-size: clamp(18px, 3vw, 26px);
    font-weight: 700;
    color: #FFDAFE;
    letter-spacing: 0.12em;
    text-shadow: 0 1px 8px rgba(235, 173, 255, 0.4);
    text-align: center;
    text-transform: uppercase;
}

.candy-close-btn {
    background: rgba(255, 105, 180, 0.15);
    border: 1.5px solid rgba(255, 105, 180, 0.45);
    color: rgba(255, 255, 255, 0.85);
    width: 36px;
    height: 36px;
    border-radius: 50%;
    cursor: pointer;
    display: flex;
    align-items: center;
    justify-content: center;
    transition: background 0.2s ease, transform 0.15s ease;
}

.candy-close-btn:hover {
    background: rgba(255, 105, 180, 0.3);
    transform: scale(1.1);
}

#paytable-content {
    padding: 20px 24px;
    overflow-y: auto;
    flex: 1;
    -webkit-overflow-scrolling: touch;
    color: rgba(255, 220, 240, 0.85);
}

#paytable-content::-webkit-scrollbar {
    width: 6px;
}

#paytable-content::-webkit-scrollbar-track {
    background: rgba(255, 255, 255, 0.04);
    border-radius: 10px;
}

#paytable-content::-webkit-scrollbar-thumb {
    background: linear-gradient(180deg, #FFDAFE 0%, #ff69b4 100%);
    border-radius: 10px;
}

/* ========== MODAL ANIMATIONS ========== */
@keyframes fadeIn {
    from { opacity: 0; }
    to { opacity: 1; }
}

@keyframes popupIn {
    0%   { transform: scale(0.85); opacity: 0; }
    60%  { transform: scale(1.03); opacity: 1; }
    100% { transform: scale(1); opacity: 1; }
}

.modal-popup {
    animation: popupIn 0.35s cubic-bezier(0.34, 1.56, 0.64, 1) forwards;
}

.modal-fade {
    animation: fadeIn 0.2s ease-out forwards;
}

@keyframes fadeOut {
    from { opacity: 1; }
    to { opacity: 0; }
}

@keyframes popupOut {
    from {
        transform: scale(1) translateY(0);
        opacity: 1;
    }
    to {
        transform: scale(0.95) translateY(10px);
        opacity: 0;
    }
}

.modal-fade-out {
    animation: fadeOut 0.2s ease-in forwards;
}

.modal-popup-out {
    animation: popupOut 0.2s ease-in forwards;
}

/* ========== FOCUS INDICATORS (keyboard accessibility) ========== */
button:focus-visible,
[role="button"]:focus-visible {
    outline: 2px solid var(--color-primary);
    outline-offset: 2px;
}

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

/* ========== SERVER LOADING SPINNER ========== */
#server-loading {
    position: fixed;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    z-index: 15000;
    display: flex;
    align-items: center;
    justify-content: center;
    pointer-events: none;
    animation: fadeIn 0.2s ease-out;
}

.server-loading-spinner {
    width: 48px;
    height: 48px;
    border: 4px solid rgba(255, 255, 255, 0.15);
    border-top-color: rgba(255, 255, 255, 0.8);
    border-radius: 50%;
    animation: spin 0.7s linear infinite;
}

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

/* ========== SPLASH OVERLAY ========== */
.splash-start-btn {
    font-family: var(--sui-font);
    font-weight: 700;
    font-size: clamp(22px, 3vw, 32px);
    color: #ffffff;
    background: radial-gradient(circle at 35% 30%, #e8508a 0%, #c0286a 45%, #8a1050 100%);
    border: 3px solid rgba(255, 180, 210, 0.7);
    border-radius: 9999px;
    padding: clamp(14px, 2vh, 20px) clamp(48px, 6vw, 80px);
    min-height: 48px;
    min-width: clamp(160px, 30vw, 240px);
    text-shadow: 0 2px 4px rgba(0, 0, 0, 0.4);
    cursor: pointer;
    text-transform: uppercase;
    letter-spacing: 2px;
    text-shadow: 0 1px 2px rgba(0, 0, 0, 0.25);
    box-shadow: 0 0 24px rgba(235, 173, 255,0.6), 0 4px 12px rgba(0,0,0,0.5);
    transition: all 0.2s;
    position: relative;
    overflow: hidden;
    animation: splash-btn-pulse 2s ease-in-out infinite;
}

@keyframes splash-btn-pulse {
    0%, 100% { box-shadow: 0 0 24px rgba(200, 40, 100, 0.55), 0 4px 16px rgba(0,0,0,0.4), inset 0 3px 8px rgba(255, 220, 240, 0.25); }
    50% { box-shadow: 0 0 44px rgba(200, 40, 100, 0.8), 0 4px 20px rgba(0,0,0,0.5), inset 0 3px 8px rgba(255, 220, 240, 0.35); }
}

.splash-start-btn::before {
    content: '';
    position: absolute;
    top: 0; left: -75%;
    width: 50%; height: 100%;
    background: linear-gradient(120deg, rgba(255,255,255,0) 0%, rgba(255,255,255,0.35) 50%, rgba(255,255,255,0) 100%);
    animation: splash-btn-shimmer 3s ease-in-out infinite;
}

@keyframes splash-btn-shimmer {
    0% { left: -75%; }
    40%, 100% { left: 125%; }
}

.splash-start-btn:hover {
    transform: scale(1.06);
    background: radial-gradient(circle at 35% 30%, #ff6aaa 0%, #d4306e 45%, #a01858 100%);
    box-shadow: 0 0 56px rgba(200, 40, 100, 0.9), 0 6px 20px rgba(0,0,0,0.5), inset 0 3px 8px rgba(255, 220, 240, 0.3);
}

.splash-start-btn:active {
    transform: scale(0.96);
}

.splash-dont-show {
    display: flex;
    align-items: center;
    gap: 8px;
    cursor: pointer;
    font-family: var(--sui-font);
    font-size: clamp(12px, 1.5vw, 15px);
    font-weight: 800;
    white-space: nowrap;
    color: rgba(255,255,255,0.85);
    user-select: none;
    letter-spacing: 0.5px;
    min-height: 32px;
}

.splash-checkbox {
    -webkit-appearance: none;
    appearance: none;
    width: 20px;
    height: 20px;
    border: 2px solid rgba(255, 105, 180, 0.6);
    border-radius: 5px;
    background: rgba(0, 0, 0, 0.2);
    cursor: pointer;
    margin: 0;
    vertical-align: middle;
    position: relative;
}

.splash-checkbox:checked {
    background: #ff69b4;
    border-color: #ff69b4;
}

.splash-checkbox:checked::after {
    content: '';
    position: absolute;
    left: 5px;
    top: 1px;
    width: 6px;
    height: 11px;
    border: solid #ffffff;
    border-width: 0 2.5px 2.5px 0;
    transform: rotate(45deg);
}


/* ========== PAYTABLE STYLES ========== */
.paytable-container {
    width: 100%;
    padding: 0 20px;
}

.paytable-section {
    margin-bottom: 40px;
}

.paytable-section-title {
    font-weight: 700;
    color: #ffffff;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    margin: 0 0 12px 0;
    width: 100%;
    text-align: center;
    text-shadow: 0 1px 4px rgba(0, 0, 0, 0.3);
}

.paytable-grid {
    display: grid;
    justify-items: center;
}

.paytable-card {
    background: rgba(255, 255, 255, 0.04);
    border: 1px solid rgba(255, 255, 255, 0.08);
    border-radius: 12px;
    padding: 12px;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 8px;
    transition: border-color 0.3s ease, box-shadow 0.3s ease;
    max-width: 200px;
    width: 100%;
}

.paytable-card:hover {
    border-color: rgba(255, 255, 255, 0.18);
    box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
}

.paytable-symbol-img {
    width: 100%;
    max-width: 180px;
    height: auto;
    aspect-ratio: 1;
    object-fit: contain;
}

/* Skeleton shimmer placeholder for ALL images inside paytable / popup
   modals — covers the brief window between modal open and PNG load
   (cascade illustrations, buy-bonus card, payout-symbol icons) so the
   user never sees a blank area waiting for bytes. The shimmer keeps
   running underneath the loaded image but is naturally hidden once
   the opaque PNG covers the element. Producer: 'paytable 里很多图片
   显示载入 需要有占位符号 否则载入时间长咋办'. */
@keyframes paytable-img-shimmer {
    0%   { background-position: -150% 0; }
    100% { background-position:  150% 0; }
}
#paytable-content img,
#game-rules-content img,
.candy-modal-content img {
    background-color: rgba(235, 173, 255, 0.06);
    background-image: linear-gradient(
        110deg,
        rgba(235, 173, 255, 0.04) 30%,
        rgba(235, 173, 255, 0.18) 50%,
        rgba(235, 173, 255, 0.04) 70%
    );
    background-size: 200% 100%;
    background-repeat: no-repeat;
    animation: paytable-img-shimmer 1.5s ease-in-out infinite;
    border-radius: 6px;
    /* min-height ensures the placeholder is visible even before the img
       has its natural dimensions (since width/height attrs aren't on
       the img tags). 40px is the minimum readable shimmer area. */
    min-height: 40px;
}
/* Once the image bytes arrive, an inline <script> in index.html flips
   `data-loaded="1"` on the img element. Strip the placeholder so the
   shimmer animation stops eating CPU and the background isn't visible
   through any transparent corners of the PNG. */
#paytable-content img[data-loaded="1"],
#game-rules-content img[data-loaded="1"],
.candy-modal-content img[data-loaded="1"] {
    background: none;
    animation: none;
    min-height: 0;
}

.paytable-payouts {
    width: 100%;
    display: flex;
    flex-direction: column;
    gap: 8px;
}

.paytable-payout-row {
    display: flex;
    justify-content: space-between;
    align-items: center;
    font-size: 16px;
}

.paytable-range {
    color: var(--color-text-dim);
    font-weight: 400;
}

.paytable-value {
    color: var(--color-text);
    font-weight: 400;
}

.paytable-page-divider {
    width: 100%;
    height: 2px;
    background: linear-gradient(to right, transparent, rgba(255, 255, 255, 0.5), rgba(235, 173, 255, 0.6), rgba(255, 255, 255, 0.5), transparent);
    margin: 32px 0;
}

.paytable-page-title {
    font-weight: bold;
    text-align: center;
    margin-bottom: 16px;
    text-transform: uppercase;
}

/* Area header — sticky at the top of the main-content column.
   Stays visible while the user scrolls the long paytable document.
   - margin: 0 (default h1 has 0.67em top margin which leaves a gap
     where scrolled content bleeds through above the sticky element)
   - background: fully opaque solid color (no alpha gradient)
   - z-index: 50 — sits above side-nav and inline content. Close-btn
     is bumped to 60+ separately so it stays visible above this. */
.paytable-area-title {
    position: sticky;
    top: 0;
    z-index: 50;
    font-family: var(--sui-font, sans-serif);
    font-size: clamp(44px, 9vw, 64px);
    font-weight: 900;
    color: #ffffff;            /* m10: paytable text → white */
    text-transform: uppercase;
    letter-spacing: 0.12em;
    margin: 0 0 16px 0;
    /* Symmetric horizontal padding so the centred title reads as
       balanced against the floating close-X at top:12 right:12 (button
       width 36 = 48px right edge clearance). 60px padding on BOTH sides
       keeps geometric centre = modal centre AND avoids overlap.
       Producer-flagged: title was leaning off-centre because the close
       button's visual weight was pulling the eye right while title
       padding was a narrow 20px symmetric. */
    padding: 14px 60px 12px;
    text-align: center;
    text-shadow: 0 1px 8px rgba(255, 255, 255, 0.35), 0 0 20px rgba(255, 255, 255, 0.18);
    background: #2a0031;
    border-bottom: 1px solid rgba(255, 255, 255, 0.18);
    box-shadow: 0 4px 12px rgba(0, 0, 0, 0.4);
}

/* Game-rules modal mirrors paytable structure — its area-title is the
   same h1.paytable-area-title element rendered inside #game-rules-content.
   Cover its sticky parent path here. */
#game-rules-content > h1.paytable-area-title {
    margin-top: 0 !important;
}

/* Pull the modal close buttons above the sticky stack so they stay
   clickable even when the area title is pinned at the top. Applies to
   both paytable and game-rules modals (same area-title pattern). */
#paytable-modal #close-paytable-btn,
#game-rules-modal #close-rules-btn {
    z-index: 60 !important;
}

/* The h1 used for the area title inherits a `margin: 0.67em 0` from
   user-agent stylesheet. With sticky elements that margin-top creates
   a transparent gap at the top through which the scrolling page
   content (HIGH PAY SYMBOLS, etc.) bleeds. Force it to zero. */
.paytable-main-content > h1.paytable-area-title {
    margin-top: 0 !important;
}

/* Portrait: drop the sticky behaviour (producer "portrait paytable
   可以根整个页面一起 scroll"), shrink the heading so it fits within
   the narrower modal, and reserve right padding so the floating
   close-X (top:12 right:12) doesn't overlap the title text.
   Producer also said "paytable 字体不要提大" — keep the title
   compact, well under the desktop 44-64px scale.

   Selector note: uses `body.pixi-portrait-ui-active` (set by
   layer-manager based on game canvas aspect) instead of a viewport
   `@media (max-width: 768px) and (orientation: portrait)` gate.
   Reason: iPad portrait widths (810/820/834) don't match the
   max-width:768 clause, so those iPads kept the desktop sticky +
   solid-bg styling — but on tablet the sticky+glow combo can paint
   incomplete (iPad-Safari quirk), making the title appear see-through.
   Tying the override to the GAME's logical orientation matches the
   HTML structure already chosen by paytable-menu.js (which also
   reads stateManager.getOrientation()) so both signals stay aligned. */
body.pixi-portrait-ui-active .paytable-area-title {
    position: static !important;
    font-size: clamp(22px, 5vw, 30px) !important;
    /* Symmetric horizontal padding so the centred text actually
       lands at visual centre — close-X clearance on the right is
       mirrored on the left. Aligns with SYMBOL TABLE / FREE GAMES
       sub-titles below. */
    padding: 8px 60px !important;
    margin: 6px 0 10px 0 !important;
    text-align: center !important;
    background: transparent !important;
    border-bottom: none !important;
    box-shadow: none !important;
}

/* Side-nav header — sits above the page-list buttons in landscape so
   the column doesn't read as just a floating list. Mirrors the
   styling weight of the area title but at a smaller, "tab strip"
   scale. */
.paytable-side-nav-title {
    font-family: var(--sui-font, sans-serif);
    font-size: 14px;
    font-weight: 800;
    color: #ffffff;            /* m10: paytable text → white */
    text-transform: uppercase;
    letter-spacing: 0.16em;
    text-align: center;
    padding: 6px 4px 10px;
    margin-bottom: 6px;
    border-bottom: 1px solid rgba(255, 255, 255, 0.18);
    text-shadow: 0 1px 6px rgba(255, 255, 255, 0.3);
}

/* Page section wrapper (landscape long-page layout). scroll-margin-top
   gives the smooth-scroll target a small breathing gap above the title
   instead of pinning it flush against the scroll container top. */
.paytable-page-section {
    scroll-margin-top: 12px;
}

.paytable-section-divider {
    width: 100%;
    height: 1px;
    background: linear-gradient(to right, transparent, rgba(255, 255, 255, 0.4), transparent);
    margin: 16px 0 12px 0;
}

/* Landscape layout */
.paytable-landscape-layout {
    display: flex;
    gap: 0;
}

.paytable-side-nav {
    min-width: 160px;
    max-width: 180px;
    flex-shrink: 0;
    position: sticky;
    top: 0;
    align-self: flex-start;
    background: rgba(0, 0, 0, 0.2);
    border-radius: 14px;
    padding: 6px;
    border: 1px solid rgba(255, 255, 255, 0.08);
    backdrop-filter: blur(4px);
}

.paytable-nav-list {
    display: flex;
    flex-direction: column;
    gap: 6px;
}

.paytable-nav-btn {
    padding: 11px 14px;
    text-align: left;
    font-size: 11px;
    font-weight: 800;
    cursor: pointer;
    transition: all 0.2s ease;
    border-radius: 999px;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    background: linear-gradient(180deg, rgba(60,25,45,0.55) 0%, rgba(40,15,30,0.4) 100%);
    color: rgba(255, 255, 255, 0.78);   /* m10: white text */
    border: 1px solid rgba(255, 105, 180, 0.18);
    box-shadow: 0 1px 3px rgba(0,0,0,0.25), inset 0 1px 0 rgba(255,218,254,0.06);
    position: relative;
    overflow: hidden;
}

.paytable-nav-btn:hover {
    background: linear-gradient(180deg, rgba(90,35,65,0.6) 0%, rgba(60,20,45,0.45) 100%);
    color: #ffffff;             /* m10: white text */
    border-color: rgba(255, 105, 180, 0.45);
    box-shadow: 0 2px 8px rgba(255,105,180,0.18), inset 0 1px 0 rgba(255,218,254,0.15);
    transform: translateX(2px);
}

.paytable-nav-btn.active {
    background: linear-gradient(180deg, rgba(232, 80, 138, 0.45) 0%, rgba(160, 24, 88, 0.55) 100%);
    color: #ffffff;
    border-color: rgba(255, 105, 180, 0.65);
    box-shadow: 0 2px 12px rgba(255, 105, 180, 0.4), inset 0 1px 0 rgba(255,255,255,0.22);
    text-shadow: 0 1px 4px rgba(0, 0, 0, 0.35);
}

/* Active pill has a soft left glow bar to telegraph selection */
.paytable-nav-btn.active::before {
    content: '';
    position: absolute;
    left: 0;
    top: 20%;
    bottom: 20%;
    width: 3px;
    background: linear-gradient(to bottom, transparent, #FFDAFE 50%, transparent);
    border-radius: 0 2px 2px 0;
    box-shadow: 0 0 8px rgba(255, 218, 254, 0.8);
}

.paytable-nav-divider {
    width: 1px;
    background: rgba(255, 105, 180, 0.2);
    flex-shrink: 0;
    margin: 0 15px;
}

/* Pager (arrows + dots) sitting under the side-nav list */
.paytable-pager {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 8px;
    margin-top: 12px;
    padding: 8px 6px;
    border-top: 1px solid rgba(255, 105, 180, 0.18);
}

.paytable-pager-arrow {
    width: 26px;
    height: 26px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 999px;
    background: linear-gradient(180deg, rgba(60,25,45,0.55) 0%, rgba(40,15,30,0.4) 100%);
    border: 1px solid rgba(255, 105, 180, 0.25);
    color: #FFDAFE;
    font-size: 16px;
    font-weight: 700;
    line-height: 1;
    cursor: pointer;
    transition: background 0.15s ease, border-color 0.15s ease, transform 0.1s ease;
    padding: 0;
    box-shadow: 0 1px 3px rgba(0,0,0,0.25), inset 0 1px 0 rgba(255,218,254,0.06);
}

.paytable-pager-arrow:hover:not(:disabled) {
    background: linear-gradient(180deg, rgba(90,35,65,0.6) 0%, rgba(60,20,45,0.45) 100%);
    border-color: rgba(255, 105, 180, 0.55);
    transform: scale(1.08);
}

.paytable-pager-arrow:disabled {
    opacity: 0.3;
    cursor: not-allowed;
}

.paytable-pager-dots {
    display: flex;
    align-items: center;
    gap: 6px;
}

.paytable-pager-dot {
    width: 8px;
    height: 8px;
    padding: 0;
    border-radius: 50%;
    border: 1px solid rgba(255, 105, 180, 0.3);
    background: rgba(255, 218, 254, 0.18);
    cursor: pointer;
    transition: background 0.15s ease, border-color 0.15s ease, transform 0.1s ease, box-shadow 0.15s ease;
}

.paytable-pager-dot:hover {
    background: rgba(255, 218, 254, 0.45);
    border-color: rgba(255, 105, 180, 0.6);
    transform: scale(1.2);
}

.paytable-pager-dot.active {
    background: #FFDAFE;
    border-color: #FFDAFE;
    box-shadow: 0 0 8px rgba(255, 218, 254, 0.7);
}

.paytable-main-content {
    flex: 1;
    min-width: 0;
    /* `overflow-x: clip` clips horizontal overflow without creating a
       scroll container — unlike `hidden`, it does NOT trap a sticky
       child here. The PAYTABLE area header (position: sticky; top: 0)
       therefore binds to the real scroll container (#paytable-content)
       and pins to the top of the viewport during scroll. */
    overflow-x: clip;
}

/* ========== RESPONSIVE: PORTRAIT ========== */
@media (max-width: 768px) and (orientation: portrait) {
    #game-header {
        top: 1vh;
        left: 50%;
        transform: translateX(-50%);
        gap: 1.5vw;
        flex-direction: row;
        align-items: center;
    }

    #game-header {
        top: 0.8vh;
        left: 50%;
        transform: translateX(-50%);
        padding: 0.4vh 1vh;
        border-radius: 6px;
    }

    #game-title {
        font-size: clamp(4px, 1.2vw, 6px);
        letter-spacing: 0.05em;
        padding-right: 1vw;
    }

    /* Make modals larger in portrait mode */
    #paytable-modal > div,
    #game-rules-modal > div,
    #game-history-modal > div,
    #bet-menu-modal > div,
    #autoplay-menu-modal > div,
    #settings-info-modal > div,
    #cheat-menu-modal > div {
        max-width: 95vw !important;
        width: 95vw !important;
        max-height: 85vh !important;
    }

    /* m7: anchor modals to the TOP of the viewport (was vertically
       centred) so they always cover the reels area in portrait — the
       reels live in the upper half of the screen, so a top-anchored
       modal naturally sits over them. Producer "move up auto play /
       settings and other menus so they always cover the reels area". */
    #paytable-modal,
    #game-rules-modal,
    #game-history-modal,
    #bet-menu-modal,
    #autoplay-menu-modal,
    #settings-info-modal,
    #cheat-menu-modal {
        align-items: flex-start !important;
        padding-top: 2vh !important;
    }

    /* B6: pack ALL bet values in without scroll. The bet list can run
       40+ tiers; with the previous 5-col grid + py-3 padding the rows
       overflowed below 85vh. Force 6 columns + compact pill paddings
       (vertical 4 / horizontal 6) and a tight gap so the grid fits the
       allowed height without a scrollbar. Modal max-height bumped to
       95vh below to give the content the extra few rows of room. */
    #bet-menu-content .bet-button,
    #bet-menu-content .line-button {
        padding: 4px 6px !important;
        font-size: 12px !important;
        min-height: 0 !important;
    }

    /* Override the Tailwind `grid-cols-3 sm:cols-4 md:cols-5` chain
       baked into the markup — Tailwind doesn't ship a portrait media
       query, so we lock 6 cols for any portrait viewport. */
    #bet-menu-content .grid {
        grid-template-columns: repeat(6, minmax(0, 1fr)) !important;
        gap: 4px !important;
    }

    #bet-menu-content h3 {
        font-size: 14px !important;
    }
    /* Compact the section spacing too — `space-y-8` → ~32px between
       sections. Tighten to 12px so PLAY VALUE + LINES rows fit. */
    #bet-menu-content .space-y-8 > * + * {
        margin-top: 12px !important;
    }
    #bet-menu-content .space-y-4 > * + * {
        margin-top: 8px !important;
    }

    /* Allow the bet-menu modal to grow taller than the shared 85vh
       cap so the full bet ladder fits. Other modals stay at 85vh. */
    #bet-menu-modal > div {
        max-height: 95vh !important;
    }
    /* Prefer auto-fit content height — when the bet list is short the
       modal naturally collapses; when long it caps at 95vh and only
       the inner #bet-menu-content scrolls (still avoids a scrollbar
       in the typical case where content fits). */
    #bet-menu-content {
        overflow-y: visible !important;
    }

    /* Compact autoplay menu for portrait */
    #autoplay-menu-content {
        font-size: 14px;
    }

    #autoplay-menu-content h3 {
        font-size: 18px !important;
        margin-bottom: 8px !important;
    }

    #autoplay-menu-content button {
        padding: 10px 14px !important;
        font-size: 14px !important;
    }
}

/* ========== RESPONSIVE: LANDSCAPE SMALL SCREENS ========== */
@media (max-height: 600px) and (orientation: landscape) {
    #game-header {
        top: 1vh;
        left: calc(var(--safe-left, 0px) + 1vh);
        gap: 1vw;
        flex-direction: row;
        align-items: center;
    }

    #game-title {
        font-size: clamp(5px, 1.2vh, 7px);
        letter-spacing: 0.05em;
    }

    /* Paytable scaling for landscape small screens */
    .paytable-symbol-img {
        max-width: 100px !important;
    }

    .paytable-card {
        padding: 8px !important;
        gap: 6px !important;
    }

    .paytable-payout-row {
        font-size: 12px !important;
    }

    .paytable-section-title {
        font-size: 18px !important;
    }

    .paytable-grid {
        gap: 12px !important;
    }
}

/* ========== RESPONSIVE: VERY SMALL SCREENS ========== */
@media (max-width: 480px) {
    #game-header {
        top: 0.5vh;
        gap: 0.3vh;
    }

    #game-title {
        font-size: clamp(4px, 1.2vw, 6px);
        letter-spacing: 0.03em;
    }
}

/* ========== RESPONSIVE: PAYTABLE MOBILE ========== */
@media (max-width: 768px) {
    .paytable-card {
        padding: 12px;
        gap: 10px;
    }

    .paytable-symbol-img {
        max-width: 100px;
    }

    .paytable-payout-row {
        font-size: 13px;
    }

    .paytable-section-title {
        font-size: 18px;
        margin-bottom: 12px;
    }

    .paytable-container {
        padding: 0 10px;
    }

    .paytable-section {
        margin-bottom: 25px;
    }
}

@media (max-width: 480px) {
    .paytable-card {
        padding: 10px;
        gap: 8px;
        max-width: 180px;
    }

    .paytable-symbol-img {
        max-width: 80px;
    }

    .paytable-payout-row {
        font-size: 11px;
    }

    .paytable-section-title {
        font-size: 16px;
    }

    .paytable-container {
        padding: 0 8px;
    }
}

/* ========== SAFE AREA INSETS (iPhone notch/dynamic island) ========== */
@supports (padding: env(safe-area-inset-top)) {
    #game-header {
        top: max(0.5vw, env(safe-area-inset-top));
    }

    .fixed.inset-0 {
        padding-top: env(safe-area-inset-top);
        padding-bottom: env(safe-area-inset-bottom);
    }
}

/* Promo bet: lock bet controls */
body.promo-bet-active .sui-bet-minus,
body.promo-bet-active .sui-bet-plus,
body.promo-bet-active .sui-bet-box {
    pointer-events: none !important;
    opacity: 0.4 !important;
    cursor: not-allowed !important;
}

/* Hide HTML UI when connector popup is active (Tartarus uses PIXI UI so doesn't need this) */
body.connector-popup-active .sui-root,
body.connector-popup-active #splash-buttons,
body.connector-popup-active #game-header {
    visibility: hidden !important;
    pointer-events: none !important;
}

/* Hide all game UI when orientation is locked (mobile landscape) */
body.orientation-locked .sui-root,
body.orientation-locked #game-header,
body.orientation-locked #app-container,
body.orientation-locked #splash-buttons,
body.orientation-locked canvas {
    visibility: hidden !important;
    pointer-events: none !important;
}

/* Connector UI — styled via theme config in reskin-map.json */
