/* css/cave-office.css — The Field Office
   A sea-cave workshop swum in first person: vertical scroll carries the
   diver forward, deeper into the cave, past seven works. The cave itself —
   walls, floor, light, furniture and finds — is a 3D world drawn by
   js/n64-cave.js on a canvas inside the tour's viewport; this page holds
   the controls, the captions and the words, laid out in station boxes the
   world furnishes and carries into place (without WebGL the strip of
   stations pans sideways instead).

   N64 rules apply: words in the HUD voice (a chunky display face with a
   hard, unblurred shadow; mono for instruments), panels flat and square
   with the double sand-gold frame, no vector icons. */

:root {
    --cave-mono: ui-monospace, 'SF Mono', Menlo, Consolas, monospace;
}

body.cave-office {
    /* `clip`, not `hidden`: an overflow-hidden body becomes a scroll
       container, and the tour's position:sticky viewport would stick to
       the body (which never scrolls) instead of the window — the whole
       cave would scroll straight off screen. */
    overflow-x: clip;
    background:
        linear-gradient(180deg, #05121f 0%, #04101c 55%, #020910 100%);
}

.cave-main {
    position: relative;
    z-index: 1;
}

/* ===== The tour: a tall page that pans a wide strip =====
   The unitless vars are consumed as vw by the strip and its stations, and
   scaled per breakpoint through --kx/--kw so one set of station coords
   serves every screen. */
.cave-tour {
    --strip-w: 562;
    --pace: 0.9;
    position: relative;
    height: calc(100vh + (var(--strip-w) - 100) * var(--pace) * 1vw);
}

.cave-viewport {
    position: sticky;
    top: 0;
    height: 100vh;
    overflow: hidden;
}

@supports (height: 100svh) {
    .cave-viewport {
        height: 100svh;
    }
}

/* the world, behind the strip */
.n64-cave {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    z-index: 0;
    pointer-events: none;
    image-rendering: pixelated;
    image-rendering: crisp-edges;
    /* hidden until it has drawn itself in the right place, then it fades in */
    opacity: 0;
    transition: opacity 0.5s ease;
}

.n64-cave.n64-cave--on {
    opacity: 1;
}

/* (under the arrival's mist until it starts to part: then it comes up beneath it) */
html.nav-arriving:not(.nav-reveal) .n64-cave {
    opacity: 0;
}

.cave-layer {
    position: absolute;
    top: 0;
    bottom: 0;
    left: 0;
    will-change: transform;
}

.cave-mid {
    --kx: 1;
    --kw: 1;
    width: calc(var(--strip-w) * 1vw);
    z-index: 2;
    /* the words arrive with the world: the swim lays every station over its
       furniture once the cave has drawn itself (html.cave-fp), or the strip
       pans as it always did without WebGL (html.no-cave) */
    opacity: 0;
    transition: opacity 0.5s ease;
}

html.cave-fp .cave-mid,
html.no-cave .cave-mid {
    opacity: 1;
}

/* ===== Stations: boxes the world furnishes ===== */
.cave-station {
    position: absolute;
    bottom: var(--sb, 7vh);
    /* --sx-m and --sw-m let a media query out-vote the inline seeds */
    left: calc(var(--sx-m, var(--sx)) * var(--kx, 1) * 1vw);
    width: calc(var(--sw-m, var(--sw)) * var(--kw, 1) * 1vw);
    aspect-ratio: var(--sar);
    /* swimming forward, the world sets each box's transform: the
       projective map of its station's plane, from the box's top-left */
    transform-origin: 0 0;
}

/* a station out of reach: its words are gone and its finds can't be hit */
.cave-station.st-away {
    pointer-events: none;
}

/* ===== The cave mouth: no words, only the way in =====
   The sign on the sandbar names the place; a gold arrow in the open water
   before the mouth nudges the swim on. */
.station-mouth .swim-hint {
    position: absolute;
    left: 36%;
    top: 40%;
    margin: 0;
    animation: mouthSettle 1.1s ease-out backwards;
}

@keyframes mouthSettle {
    from {
        opacity: 0;
        transform: translateY(14px);
    }

    to {
        opacity: 1;
        transform: translateY(0);
    }
}

/* the little gold arrows that point the way (props, drawn in 3D); each is
   a button that swims you on (js/cave-office.js) */
.hint-prop {
    --stage-w: 38px;
    --stage-h: 38px;
    display: inline-block;
}

.way-on {
    display: inline-block;
    padding: 0;
    margin: 0;
    line-height: 0;
    background: none;
    border: none;
    cursor: pointer;
    -webkit-tap-highlight-color: transparent;
}

.way-on:focus-visible {
    outline: 2px solid var(--hud-gold, #ffd36a);
    outline-offset: 4px;
}

/* the one riding the guide line at each stop: the world places it and
   fades it in while the swim rests there */
.cave-onward {
    position: absolute;
    left: 0;
    top: 0;
    z-index: 3;
    opacity: 0;
    pointer-events: none;
}

.cave-onward.on {
    pointer-events: auto;
}

.cave-onward .hint-prop {
    --stage-w: 84px;
    --stage-h: 84px;
}

/* (it points the way the passage carries on) */
.cave-onward .onward-l,
.cave-onward[data-side="left"] .onward-r {
    display: none;
}

.cave-onward[data-side="left"] .onward-l {
    display: inline-block;
}

@media (max-width: 700px), (max-height: 560px) {
    .cave-onward .hint-prop {
        --stage-w: 66px;
        --stage-h: 66px;
    }
}

html.no-cave .cave-onward {
    display: none;
}

.station-mouth .hint-prop {
    --stage-w: 64px;
    --stage-h: 64px;
}

.mouth-sign {
    position: absolute;
    right: 5%;
    bottom: 0;
    width: 24%;
    aspect-ratio: 300 / 480;
    pointer-events: none;
}

/* ===== Finds: the button is the control, the world draws the object ===== */
.cave-item {
    position: absolute;
    left: var(--ix);
    top: var(--iy);
    width: var(--iw);
    padding: 0;
    background: none;
    border: none;
    cursor: pointer;
    -webkit-tap-highlight-color: transparent;
    z-index: 2;
}

.cave-item:focus-visible,
.cave-ruby:focus-visible {
    outline: 2px solid var(--hud-gold, #ffd36a);
    outline-offset: 6px;
}

.item-art {
    display: block;
    width: 100%;
}

.cave-item.engaged {
    pointer-events: none;
}

/* ===== Captions: the HUD voice, as on the bio dive ===== */
.item-caption {
    position: absolute;
    /* --cap (a % of the button's height) drops the caption past whatever
       furniture the work sits on; default hangs just under the find */
    top: var(--cap, calc(100% + 0.55rem));
    left: 50%;
    transform: translateX(-50%);
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.22rem;
    font-family: var(--cave-mono);
    white-space: nowrap;
    pointer-events: none;
}

.item-no {
    font-size: 0.68rem;
    letter-spacing: 0.2em;
    color: rgba(220, 236, 255, 0.72);
    text-shadow: 1px 1px 0 rgba(6, 18, 32, 0.95);
}

.item-name {
    font-family: var(--hud-font, 'Lilita One', sans-serif);
    font-size: 1rem;
    font-weight: 400;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: var(--hud-ink, #fff4d8);
    text-shadow: 2px 2px 0 var(--hud-shadow, #061220), 0 0 10px rgba(3, 12, 22, 0.85);
    transition: color 0.25s ease, transform 0.25s ease;
}

.cave-item:hover .item-name,
.cave-item:focus-visible .item-name {
    color: var(--hud-gold, #ffd36a);
    transform: translateY(-2px);
}

/* the "Press A" line: shown for whichever find is in reach (js/cave-office.js),
   gone while its encounter plays */
.item-caption .press-prompt {
    margin-top: 0.3rem;
}

/* ...and while it shows, the words are part of the find: pressing them
   presses it */
.cave-station:not(.st-away) .cave-item.in-reach .item-caption,
.cave-station:not(.st-away) .cave-item.in-reach .press-prompt,
.cave-station:not(.st-away) .cave-ruby.in-reach .item-caption,
.cave-station:not(.st-away) .cave-ruby.in-reach .press-prompt {
    pointer-events: auto;
    cursor: pointer;
}

.cave-item.engaged .press-prompt {
    opacity: 0;
}

/* the chart hangs where a caption would, so its label rides above the roll */
.item-chart .item-caption {
    top: auto;
    bottom: calc(100% + 0.7rem);
}

/* the button is the roll, but the map it lets down is what a hand reaches
   for: the touch area runs down over the whole hanging sheet (156 of the
   roll's 200 units wide, ~5 roll-heights deep with its batten) */
.item-chart::before {
    content: '';
    position: absolute;
    left: 11%;
    right: 11%;
    top: 0;
    height: 510%;
}

/* ===== The field log: a slate on twine (3D), its words for readers =====
   The slate and the ruby keep to their own columns at every size: the
   slate in the beam on the left, the ruby at the horn's base on the right,
   never overlapping. */
.field-log {
    position: absolute;
    left: 4%;
    top: 13%;
    width: 60%;
}

.log-board {
    display: block;
    width: 100%;
    aspect-ratio: 360 / 430;
}

.log-list {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip: rect(0 0 0 0);
    white-space: nowrap;
    margin: 0;
    padding: 0;
}

.log-status {
    margin: 0.7rem 0 0;
    text-align: center;
    font-family: var(--cave-mono);
    font-size: 0.72rem;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: rgba(226, 244, 255, 0.85);
    text-shadow: 1px 1px 0 rgba(6, 18, 32, 0.95);
}

.field-log.complete .log-status {
    color: #8ff5dc;
}

/* ===== The ruby =====
   Hidden until every artifact is found, then it kindles in the beam.
   Taking it overexposes the cave to white and carries the diver home. */
.cave-ruby {
    position: absolute;
    left: 68%;
    bottom: 8%;
    width: 20%;
    padding: 0;
    background: none;
    border: none;
    cursor: pointer;
    -webkit-tap-highlight-color: transparent;
    z-index: 3;
}

.cave-ruby .item-caption {
    top: calc(100% + 0.3rem);
}

.cave-ruby .item-name {
    color: #ffe2e7;
    text-shadow: 2px 2px 0 var(--hud-shadow, #061220), 0 0 12px rgba(255, 70, 100, 0.6);
}

.cave-ruby:hover .item-name,
.cave-ruby:focus-visible .item-name {
    color: #ff9aa8;
}

.cave-ruby.taken .press-prompt {
    opacity: 0;
}

/* The collapse: the rock is the 3D world's (js/n64-cave.js); the page
   adds the rumble in the instruments and the torrent of bubbles that
   thickens until it closes over the view and carries the diver home */
body.cave-collapse .cave-mid {
    opacity: 0;
    transition: opacity 0.35s ease;
}

body.cave-collapse .cave-survey,
body.cave-collapse .cave-return {
    animation: caveRumble 0.11s linear infinite;
}

@keyframes caveRumble {
    0% { translate: 0 0; }
    25% { translate: 2px -1px; }
    50% { translate: -1px 2px; }
    75% { translate: -2px -1px; }
    100% { translate: 1px 1px; }
}

/* the bubbles close over the view: bright water from above, the light
   the diver is being carried up into */
.cave-flood {
    position: fixed;
    inset: 0;
    z-index: 470;
    pointer-events: none;
    opacity: 0;
    background: radial-gradient(ellipse 120% 90% at 50% 0%,
            rgba(214, 244, 246, 0.99) 0%,
            rgba(120, 196, 214, 0.98) 45%,
            rgba(26, 96, 130, 0.98) 100%);
    transition: opacity 0.6s ease-in;
}

.cave-flood.show {
    opacity: 1;
}

/* the way up: a gold arrow beside the beam, pointing out of the cave */
.ascend-hint {
    position: absolute;
    right: -34%;
    bottom: 36%;
    display: flex;
    justify-content: center;
    width: 10rem;
    margin: 0;
}

/* ===== The edges of the view: a soft vignette over the world =====
   It lies between the 3D world and the strip, so it darkens the cave's
   edges but never the captions printed over them. */
.cave-vignette {
    position: absolute;
    inset: 0;
    z-index: 1;
    pointer-events: none;
    background:
        radial-gradient(ellipse 130% 110% at 50% 44%,
            transparent 52%,
            rgba(2, 7, 14, 0.3) 80%,
            rgba(1, 4, 9, 0.6) 100%);
}

/* ===== Survey instrument: a HUD bar, gold-framed ===== */
.cave-survey {
    position: fixed;
    top: 0.9rem;
    left: 50%;
    transform: translateX(-50%);
    z-index: 60;
    display: flex;
    align-items: center;
    gap: 0.85rem;
    padding: 0.4rem 0.85rem 0.45rem;
    background: var(--panel-bg, rgba(3, 12, 24, 0.88));
    border: 2px solid var(--panel-line, #d8b56a);
    outline: 1px solid var(--panel-line-dim, rgba(216, 181, 106, 0.38));
    outline-offset: 3px;
    box-shadow: 4px 4px 0 rgba(2, 8, 16, 0.55);
    font-family: var(--cave-mono);
}

/* its two ends: the way in and the log at the end of it */
.survey-end {
    padding: 0.15rem 0;
    margin: 0;
    background: none;
    border: none;
    font-family: var(--hud-font, 'Lilita One', sans-serif);
    font-size: 0.8rem;
    line-height: 1;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    white-space: nowrap;
    color: var(--hud-gold, #ffd36a);
    text-shadow: 2px 2px 0 var(--hud-shadow, #061220);
    cursor: pointer;
    transition: color 0.2s ease;
    -webkit-tap-highlight-color: transparent;
}

.survey-end:hover,
.survey-end:focus-visible,
.survey-end.here {
    color: var(--hud-ink, #fff4d8);
}

.survey-end:focus-visible {
    outline: 1px solid var(--hud-gold, #ffd36a);
    outline-offset: 3px;
}

/* the log end remembers where the red light lives */
.survey-end.ruby {
    color: #ff8a98;
    text-shadow: 2px 2px 0 var(--hud-shadow, #061220), 0 0 9px rgba(255, 90, 110, 0.8);
}

.survey-track {
    position: relative;
    width: clamp(150px, 24vw, 300px);
    height: 16px;
}

.survey-track::before {
    content: '';
    position: absolute;
    left: 0;
    right: 0;
    top: 50%;
    height: 2px;
    margin-top: -1px;
    background: rgba(216, 181, 106, 0.5);
}

/* artifacts: square pips on the line */
.survey-tick {
    position: absolute;
    top: 50%;
    width: 9px;
    height: 9px;
    padding: 0;
    transform: translate(-50%, -50%);
    background: #12263a;
    border: 2px solid var(--panel-line, #d8b56a);
    border-radius: 0;
    cursor: pointer;
}

.survey-tick:hover,
.survey-tick:focus-visible {
    background: var(--hud-gold, #ffd36a);
}

.survey-tick:focus-visible {
    outline: 1px solid var(--hud-gold, #ffd36a);
    outline-offset: 3px;
}

.survey-tick.visited {
    background: #7df0d4;
    border-color: #bdf9ea;
}

/* the pips of the station you're at stand up a little */
.survey-tick.here {
    transform: translate(-50%, -50%) scale(1.35);
    border-color: #fff0c2;
}

/* (a fingertip's worth to press, round each little pip) */
.survey-tick::before {
    content: '';
    position: absolute;
    inset: -9px -5px;
}

.survey-tick::after {
    content: attr(data-label);
    position: absolute;
    top: calc(100% + 9px);
    left: 50%;
    transform: translateX(-50%);
    white-space: nowrap;
    font-size: 0.66rem;
    letter-spacing: 0.16em;
    text-transform: uppercase;
    color: var(--hud-ink, #fff4d8);
    background: var(--panel-bg, rgba(3, 12, 24, 0.88));
    border: 1px solid var(--panel-line, #d8b56a);
    padding: 3px 7px;
    opacity: 0;
    pointer-events: none;
    transition: opacity 0.25s ease;
}

.survey-tick:hover::after,
.survey-tick:focus-visible::after {
    opacity: 1;
}

/* the diver: a gold diamond riding the line */
.survey-dot {
    position: absolute;
    top: 50%;
    left: 0%;
    width: 11px;
    height: 11px;
    transform: translate(-50%, -50%) rotate(45deg);
    background: var(--hud-gold, #ffd36a);
    border: 2px solid #2a1c08;
    box-shadow: 0 0 8px rgba(255, 211, 106, 0.65);
    pointer-events: none;
    z-index: 1;
}

/* ===== Return props (site nav, top right): three small finds ===== */
.cave-return {
    position: fixed;
    top: 0.6rem;
    right: 1rem;
    z-index: 60;
    display: flex;
    gap: 0.3rem;
}

.return-bubble {
    position: relative;
    width: 58px;
    text-decoration: none;
}

.return-bubble .prop-stage {
    --stage-w: 58px;
    --stage-h: 58px;
}

.return-bubble:focus-visible {
    outline: 2px solid var(--hud-gold, #ffd36a);
    outline-offset: 3px;
}

.return-word {
    position: absolute;
    top: calc(100% + 2px);
    left: 50%;
    transform: translateX(-50%);
    font-family: var(--hud-font, 'Lilita One', sans-serif);
    font-size: 0.7rem;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: var(--hud-ink, #fff4d8);
    text-shadow: 2px 2px 0 var(--hud-shadow, #061220);
    opacity: 0;
    transition: opacity 0.25s ease;
    pointer-events: none;
}

.return-bubble:hover .return-word,
.return-bubble:focus-visible .return-word {
    opacity: 1;
}

/* Out through the skylight the swim's instruments have done their job: the
   survey and the hung finds give the screen to the way on (body.cave-left
   is set by js/cave-office.js once the swim is over) */
.cave-survey,
.cave-return {
    transition: opacity 0.35s ease;
}

body.cave-left .cave-survey,
body.cave-left .cave-return {
    opacity: 0;
    pointer-events: none;
}

/* ===== Skip link: a HUD key ===== */
.skip-main {
    position: fixed;
    top: -4rem;
    left: 1rem;
    z-index: 200;
    padding: 0.55rem 1rem;
    font-family: var(--hud-font, 'Lilita One', sans-serif);
    font-size: 0.9rem;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: #1a1206;
    background: var(--panel-line, #d8b56a);
    border: 2px solid #2a1c08;
    box-shadow: 3px 3px 0 var(--hud-shadow, #061220);
    transition: top 0.25s ease;
}

.skip-main:focus {
    top: 1rem;
}

/* ===== Surfacing: the exit section =====
   The cave's last view stays clear; once the swim is over and the page
   scrolls on, the bottom of the cave darkens (--leave, set by the swim)
   into the same dark water this section opens with, so there's no edge. */
.cave-viewport::after {
    content: '';
    position: absolute;
    inset: 0;
    z-index: 3;
    pointer-events: none;
    background: linear-gradient(180deg, rgba(3, 10, 18, 0) 50%, rgba(3, 10, 18, 0.92) 100%);
    opacity: var(--leave, 0);
}

.cave-exit {
    position: relative;
    z-index: 1;
    min-height: 74vh;
    display: flex;
    flex-direction: column;
    justify-content: center;
    padding-top: 5rem;
    background: linear-gradient(180deg,
            rgba(3, 10, 18, 0.92) 0,
            rgba(4, 14, 26, 0.75) 45%,
            rgba(2, 8, 16, 0.88) 100%);
}

.cave-exit .ocean-footer {
    text-align: center;
    padding: 3.5rem 0 1.8rem;
    color: rgba(255, 255, 255, 0.35);
    font-size: 0.85rem;
}

/* ===== Without WebGL: the finds become plain framed keys ===== */
html.no-cave .cave-item .item-art,
html.no-cave .log-board {
    background: var(--panel-bg, rgba(3, 12, 24, 0.88));
    border: 2px solid var(--panel-line, #d8b56a);
}

html.no-cave .log-list {
    position: static;
    width: auto;
    height: auto;
    clip: auto;
    padding: 0.8rem 1rem;
    list-style: none;
    font-family: var(--cave-mono);
    font-size: 0.7rem;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: rgba(226, 244, 255, 0.8);
}

html.no-cave .log-tick.on::after {
    content: ' ✓';
    color: #8ff5dc;
}

/* ===== Responsive scales ===== */
@media (min-width: 701px) and (max-width: 1100px) {
    .cave-tour {
        --strip-w: 700;
    }

    .cave-mid {
        --kx: 1.245;
        --kw: 1.26;
    }

    /* the swim comes to rest with the whole skylight in view, slate and all */
    .cave-station[data-station="skylight"] {
        --sx-m: 485;
    }
}

@media (max-width: 700px) {
    .cave-tour {
        --strip-w: 1010;
        --pace: 0.85;
    }

    .cave-mid {
        --kx: 1.8;
        --kw: 1.85;
    }

    /* the mouth station is wider than a phone screen: the arrow keeps to
       the middle of the first view */
    .station-mouth .swim-hint {
        left: 19%;
        top: -10%;
    }

    /* the cave hugs its furniture closer on a phone */
    .cave-station {
        bottom: var(--sb, 12vh);
    }

    /* the skylight packs into the last screen of the swim: slate, horn
       and ruby all in view where the swim comes to rest (its twine runs
       up to the ceiling whatever the station's size) */
    .cave-station[data-station="skylight"] {
        --sw-m: 50;
        --sx-m: 507.5;
        /* stand on the same floor as every other station (its inline --sb
           is the desktop value, which would sink the ruby into the silt) */
        bottom: 12vh;
    }

    /* the way through tucks into the top-left corner, clear of the nav
       props: the line on top, its two ends named under its two ends */
    .cave-survey {
        left: 0.6rem;
        top: 0.6rem;
        transform: none;
        display: grid;
        grid-template-columns: auto auto;
        grid-template-areas: "track track" "in log";
        justify-content: space-between;
        gap: 0.3rem 0.6rem;
        padding: 0.35rem 0.6rem 0.4rem;
    }

    .survey-track {
        grid-area: track;
        width: 40vw;
    }

    .survey-end {
        font-size: 0.7rem;
    }

    .survey-end[data-end="entrance"] {
        grid-area: in;
        justify-self: start;
    }

    .survey-end[data-end="log"] {
        grid-area: log;
        justify-self: end;
    }

    .cave-return {
        top: 0.5rem;
        right: 0.5rem;
        gap: 0.1rem;
    }

    .return-bubble {
        width: 44px;
    }

    .return-bubble .prop-stage {
        --stage-w: 44px;
        --stage-h: 44px;
    }

    .item-name {
        font-size: 0.88rem;
    }

    /* the way up rides above the station, under the ceiling */
    .ascend-hint {
        top: -12%;
        bottom: auto;
        right: 2%;
    }

    /* on a phone the slate hangs wide (its chalk has to read at a glance)
       with its foot just clear of the floor; the ruby takes the corner at
       the horn's base, right of the slate and below its lowest edge */
    .field-log {
        left: 2%;
        top: 22%;
        width: 66%;
    }

    .cave-ruby {
        left: 70%;
        bottom: 0;
        width: 26%;
    }
}

/* Short landscape phones: rein the furniture in so it fits under the ceiling */
@media (max-height: 560px) {
    .cave-mid {
        --kw: 0.82;
        --kx: 0.92;
    }

    .cave-tour {
        --strip-w: 520;
    }

    .station-mouth .swim-hint {
        left: 36%;
        top: 34%;
    }

    /* the stations shrink with the short screen; the words tighten with
       them so neighbouring captions (the desk's two) keep apart */
    .item-name {
        font-size: 0.8rem;
        letter-spacing: 0.05em;
    }

    .item-no {
        letter-spacing: 0.08em;
    }

    /* a phone on its side keeps the skylight at its desktop size; the
       screen is short, so the slate steps out into the open water left of
       the station and hangs larger, the ruby keeps the horn's base, and the
       way up moves out to the right */
    .cave-station[data-station="skylight"] {
        --sw-m: 34;
        --sx-m: 478;
    }

    .field-log {
        left: -44%;
        top: 4%;
        width: 92%;
    }

    .cave-ruby {
        left: 64%;
        bottom: 2%;
        width: 26%;
    }

    .ascend-hint {
        top: auto;
        bottom: 40%;
        right: -62%;
    }
}

/* ===== Reduced motion: the cave holds still ===== */
@media (prefers-reduced-motion: reduce) {

    .swim-hint,
    body.cave-collapse .cave-survey,
    body.cave-collapse .cave-return {
        animation: none;
    }

    .item-name,
    .n64-cave,
    .cave-mid {
        transition: none;
    }
}
