:root {
    color-scheme: light;
    --paper: #f3eddf;
    --paper-light: #fffaf0;
    --blue: #9bcce3;
    --blue-soft: #d9ebf1;
    --ink: #15334b;
    --ink-soft: #536879;
    --orange: #e6443b;
    --grid: rgba(21, 51, 75, 0.2);
    --rule: rgba(21, 51, 75, 0.18);
}

@media (prefers-color-scheme: dark) {
    :root {
        color-scheme: dark;
        --paper: #211f1c;
        --paper-light: #2d2925;
        --blue: #315f73;
        --blue-soft: #1d3947;
        --ink: #f3eddf;
        --ink-soft: #aebdc3;
        --grid: rgba(243, 237, 223, 0.16);
        --rule: rgba(243, 237, 223, 0.18);
    }
}

* {
    box-sizing: border-box;
    margin: 0;
    padding: 0;
}

body {
    display: flex;
    min-height: 100vh;
    min-height: 100dvh;
    flex-direction: column;
    overflow-x: hidden;
    background: var(--paper);
    color: var(--ink);
    font-family: Inter, Arial, sans-serif;
}

html[lang="ja"] body {
    font-family: "Noto Sans JP", Inter, sans-serif;
}

a {
    color: inherit;
}

a:focus-visible {
    outline: 2px solid currentColor;
    outline-offset: 4px;
}

.site-header {
    --header-inner-width: min(100% - 48px, 1120px);
    --brand-mark-size: 48px;
    --brand-center-x: calc((100% - var(--header-inner-width)) / 2 + var(--brand-mark-size) / 2);
    --brand-center-y: 50px;

    display: flex;
    height: 100px;
    align-items: center;
    background-color: var(--blue);
    background-image:
        linear-gradient(var(--grid) 1px, transparent 1px),
        linear-gradient(90deg, var(--grid) 1px, transparent 1px);
    background-position: var(--brand-center-x) var(--brand-center-y);
    background-size: 32px 32px;
}

.site-header-inner {
    display: flex;
    width: var(--header-inner-width);
    height: 100px;
    margin: 0 auto;
    gap: 2rem;
}

.site-brand {
    display: flex;
    width: fit-content;
    align-items: center;
    gap: 0.9rem;
    font-size: 1.12rem;
    font-weight: 600;
    letter-spacing: -0.025em;
    text-decoration: none;
}

.site-brand-mark {
    display: grid;
    width: var(--brand-mark-size);
    height: var(--brand-mark-size);
    place-items: center;
    border-radius: 50%;
    background: var(--orange);
    color: var(--paper-light);
}

.site-brand-mark svg {
    width: 27px;
    height: 27px;
}

.site-nav {
    --tab-height: 42px;
    /* The active tab overhangs into this padding so its own box reaches the
       header's bottom edge. padding-top + --tab-height + --tab-overhang must
       equal the header's height, or the tab stops short of the fold. */
    --tab-overhang: 10px;

    display: flex;
    gap: 0.6rem;
    padding-top: 48px;
    padding-bottom: var(--tab-overhang);
}

.site-nav a {
    display: flex;
    height: var(--tab-height);
    align-items: center;
    padding: 0.7rem 1rem;
    background: var(--ink);
    color: var(--paper-light);
    font-size: 0.84rem;
    font-weight: 600;
    line-height: 1.1;
    text-align: center;
    text-decoration: none;
}

.site-nav a > span {
    display: inline-block;
}

.site-nav a:hover,
.site-nav a:focus-visible {
    background: var(--orange);
    color: var(--paper-light);
    outline: none;
}

.site-nav a:active > span {
    transform: translateY(2px);
}

.site-nav a[aria-current="page"] {
    /* Genuinely taller rather than faking the overhang with a solid
       box-shadow, so the element's own box reaches the header's bottom edge —
       which means it hit-tests over its full height and its box-shadow is free
       to be an actual shadow. The negative margin keeps it out of the flex
       line's cross sizing so the other tabs don't move, and the extra bottom
       padding cancels the centring shift so every label stays on one baseline. */
    height: calc(var(--tab-height) + var(--tab-overhang));
    margin-bottom: calc(var(--tab-overhang) * -1);
    padding-bottom: calc(0.7rem + var(--tab-overhang));
    background: var(--paper);
    color: var(--ink);
}

.page-shell {
    display: flex;
    width: min(100% - 48px, 1120px);
    flex: 1;
    flex-direction: column;
    align-items: flex-start;
    gap: 2.25rem;
    margin: 0 auto;
    padding: clamp(4.5rem, 8vw, 7rem) 0;
}

h1 {
    max-width: 12ch;
    font-size: clamp(3.7rem, 7vw, 6.8rem);
    font-weight: 600;
    letter-spacing: -0.07em;
    line-height: 0.86;
}

h2 {
    font-size: 1.55rem;
    font-weight: 600;
    letter-spacing: -0.035em;
    line-height: 1.15;
}

time {
    color: var(--orange);
    font-family: "DM Mono", monospace;
    font-size: 0.8rem;
    letter-spacing: 0.09em;
    text-transform: uppercase;
}

cite {
    font-style: italic;
}

.intro,
.info-card p,
.timeline-item p,
.profile-list dd {
    color: var(--ink-soft);
    font-size: 1.05rem;
    line-height: 1.65;
}

.intro {
    max-width: 45rem;
}

.text-link,
.email-link {
    color: var(--ink);
    font-weight: 600;
    text-decoration-color: var(--orange);
    text-decoration-thickness: 2px;
    text-underline-offset: 0.25em;
}

.text-link:hover,
.text-link:focus-visible,
.email-link:hover,
.email-link:focus-visible {
    color: var(--orange);
}

.service-grid {
    display: grid;
    width: 100%;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    gap: 1.1rem;
}

.info-card {
    display: flex;
    min-height: 100%;
    flex-direction: column;
    gap: 1rem;
    padding: 2rem;
    border-top: 6px solid var(--blue);
    background: var(--paper-light);
    box-shadow: 0 18px 45px rgba(21, 51, 75, 0.07);
}

.info-card:nth-child(2) {
    border-top-color: var(--orange);
}

.regulatory-notice {
    width: min(100%, 850px);
    padding: 1.75rem 2rem;
    background: var(--blue-soft);
}

.regulatory-notice h2 {
    margin-bottom: 0.75rem;
    font-family: "DM Mono", monospace;
    font-size: 0.7rem;
    letter-spacing: 0.09em;
    text-transform: uppercase;
}

.regulatory-notice p {
    color: var(--ink-soft);
    font-size: 0.92rem;
    line-height: 1.65;
}

.contact-cta {
    display: grid;
    width: 100%;
    justify-items: center;
    gap: 0.9rem;
    text-align: center;
}

.contact-cta p {
    font-size: 1.15rem;
    font-weight: 600;
}

.contact-button {
    display: inline-flex;
    min-height: 48px;
    align-items: center;
    justify-content: center;
    padding: 0.8rem 1.1rem;
    background: var(--ink);
    color: var(--paper-light);
    font-size: 0.9rem;
    font-weight: 600;
    text-decoration: none;
}

.contact-button > span {
    display: inline-block;
}

.contact-button:hover,
.contact-button:focus-visible {
    background: var(--orange);
    color: var(--paper-light);
    outline: none;
}

.contact-button:active > span {
    transform: translateY(2px);
}

.timeline {
    --timeline-gutter: 5rem;
    --timeline-line-left: 1.5rem;

    position: relative;
    display: grid;
    width: 100%;
    gap: 1.4rem;
    padding-left: var(--timeline-gutter);
}

.timeline::before {
    position: absolute;
    top: 2.25rem;
    bottom: 2.25rem;
    left: var(--timeline-line-left);
    border-left: 3px dotted rgba(21, 51, 75, 0.55);
    content: "";
}

.timeline-item {
    position: relative;
    display: grid;
    grid-template-columns: minmax(18rem, 0.85fr) minmax(0, 1.15fr);
    align-items: start;
    background: var(--paper-light);
    box-shadow: 0 18px 45px rgba(21, 51, 75, 0.07);
}

.timeline-item::before {
    position: absolute;
    z-index: 2;
    top: 2rem;
    left: calc(var(--timeline-line-left) + 1.5px - var(--timeline-gutter));
    width: 20px;
    height: 20px;
    border: 3px solid var(--ink);
    border-radius: 50%;
    background: var(--paper-light);
    box-shadow: 0 0 0 10px rgba(255, 250, 240, 0.42);
    content: "";
    transform: translateX(-50%);
}

.game-image {
    display: block;
    width: calc(100% - clamp(2rem, 4vw, 3.5rem));
    height: auto;
    margin: clamp(1rem, 2vw, 1.75rem);
    min-height: 0;
    object-fit: contain;
}

.timeline-content {
    display: flex;
    align-self: stretch;
    flex-direction: column;
    align-items: flex-start;
    justify-content: center;
    gap: 0.8rem;
    padding: clamp(1rem, 2vw, 1.75rem);
}

.timeline-content h2 {
    font-size: clamp(1.9rem, 3vw, 3rem);
}

.profile-list {
    display: grid;
    width: min(100%, 900px);
    overflow: hidden;
    background: var(--paper-light);
    box-shadow: 0 18px 45px rgba(21, 51, 75, 0.07);
}

.profile-list div {
    display: grid;
    grid-template-columns: minmax(13rem, 0.4fr) 1fr;
    gap: 2rem;
    padding: 1.25rem 1.6rem;
    border-bottom: 1px solid var(--rule);
}

.profile-list div:last-child {
    border-bottom: 0;
}

.profile-list dt {
    font-family: "DM Mono", monospace;
    font-size: 0.7rem;
    font-weight: 500;
    letter-spacing: 0.07em;
    line-height: 1.6;
    text-transform: uppercase;
}

.email-link {
    font-size: clamp(1.35rem, 3.2vw, 2.8rem);
    overflow-wrap: anywhere;
}

.site-footer {
    width: min(100% - 48px, 1120px);
    margin: 0 auto;
    padding: 1.5rem 0 2rem;
    border-top: 1px solid var(--rule);
}

.site-footer-inner {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 1.5rem;
}

.footer-nav {
    display: flex;
    flex-wrap: wrap;
    justify-content: flex-start;
    gap: 1.5rem;
}

.footer-nav a {
    font-family: "DM Mono", monospace;
    font-size: 0.67rem;
    letter-spacing: 0.08em;
    text-decoration: none;
    text-transform: uppercase;
}

.footer-nav a:hover,
.footer-nav a:focus-visible,
.footer-nav a[aria-current="page"] {
    color: var(--orange);
}

.language-nav {
    display: flex;
    align-items: baseline;
    gap: 0.8rem;
    font-family: "DM Mono", monospace;
    font-size: 0.67rem;
    letter-spacing: 0.08em;
    text-transform: uppercase;
}

.language-nav-icon {
    display: inline-flex;
    color: var(--ink-soft);
}

.language-nav-icon svg {
    width: 1rem;
    height: 1rem;
}

.language-nav a {
    text-decoration: none;
}

.language-nav a:hover,
.language-nav a:focus-visible,
.language-nav a[aria-current="page"] {
    color: var(--orange);
}

@media (prefers-color-scheme: dark) {
    .site-brand-mark {
        color: #fffaf0;
    }

    .site-nav a {
        background: #15334b;
        color: var(--ink);
    }

    .contact-button {
        background: var(--blue);
        color: var(--ink);
    }

    .site-nav a:hover,
    .site-nav a:focus-visible,
    .contact-button:hover,
    .contact-button:focus-visible {
        color: #fffaf0;
    }

    .site-nav a[aria-current="page"] {
        background: var(--paper);
        color: var(--ink);
    }

    .info-card,
    .timeline-item,
    .profile-list {
        box-shadow: 0 18px 45px rgba(0, 0, 0, 0.24);
    }

    .timeline::before {
        border-left-color: rgba(243, 237, 223, 0.45);
    }

    .timeline-item::before {
        box-shadow: 0 0 0 10px rgba(243, 237, 223, 0.22);
    }
}

@media (max-width: 900px) {
    .service-grid {
        grid-template-columns: 1fr;
    }

    .timeline-item {
        grid-template-columns: 1fr;
    }

    .game-image {
        aspect-ratio: auto;
    }
}

@media (max-width: 680px) {
    .site-header {
        --header-inner-width: calc(100% - 28px);
        --brand-mark-size: 42px;
        --brand-center-y: calc(1rem + var(--brand-mark-size) / 2);

        height: auto;
        padding-top: 1rem;
    }

    .site-header-inner {
        display: flex;
        width: var(--header-inner-width);
        height: auto;
        flex-wrap: wrap;
        gap: 0.85rem;
    }

    .site-nav {
        /* Once the tabs wrap, the active one is no longer guaranteed to be on
           the row flush with the header's bottom edge, so an overhang would
           just collide with the row beneath it rather than meeting the page.
           Zeroed here, which also zeroes the derived padding-bottom — so that
           is restored explicitly to keep the header's spacing. */
        --tab-overhang: 0px;

        display: flex;
        width: 100%;
        align-self: auto;
        height: auto;
        align-items: center;
        flex-wrap: wrap;
        padding-top: 0;
        padding-bottom: 10px;
    }

    .page-shell,
    .site-footer {
        width: calc(100% - 32px);
    }

    .page-shell {
        gap: 1.75rem;
        padding: 3.75rem 0;
    }

    .site-footer-inner {
        align-items: flex-start;
        flex-direction: column;
    }

    h1 {
        font-size: clamp(3.25rem, 17vw, 5rem);
    }

    .info-card,
    .regulatory-notice {
        padding: 1.4rem;
    }

    .timeline {
        --timeline-gutter: 3.4rem;
        --timeline-line-left: 1.1rem;
    }

    .profile-list div {
        grid-template-columns: 1fr;
        gap: 0.45rem;
        padding: 1rem 1.15rem;
    }

    .intro,
    .info-card p,
    .timeline-item p,
    .profile-list dd {
        font-size: 0.98rem;
    }
}

@media (max-width: 450px) {
    .site-nav a {
        padding-right: 0.4rem;
        padding-left: 0.4rem;
    }
}

/* ==========================================================================
 * TEXTURE PASS (site-wide) — self-contained. Delete to end of file to revert.
 *
 * The chart-specific half of this lives at the end of landing-page.css, which
 * only index.astro imports; anything that should reach every page has to be
 * here instead. Same rule as the other block: overrides only, no new elements,
 * so deleting it restores the flat original exactly.
 * ========================================================================== */

:root {
    /* Light-mode navy is *lighter* than dark mode's --paper (#211f1c), so
       reusing it there would render shadows as glows. Hence a themed value. */
    --object-shadow: rgba(21, 51, 75, 0.45);
    --edge-shadow: rgba(21, 51, 75, 0.22);
    --paper-grain: 0.26;
}

@media (prefers-color-scheme: dark) {
    :root {
        --object-shadow: rgba(0, 0, 0, 0.55);
        --edge-shadow: rgba(0, 0, 0, 0.38);
        --paper-grain: 0.18;
    }
}

/* Paper grain. One page-wide layer rather than per-element: section
   backgrounds paint solid over anything sitting on <body>, and per-layer
   grain would need phase-matching against the tilted chart backdrop. A single
   fixed overlay also matches the physical story — one sheet of stock, with
   everything printed on it. 'overlay' is luminance-relative, so the same
   artwork serves both schemes; only its strength is themed. */
body::after {
    content: "";
    position: fixed;
    z-index: 9999;
    inset: 0;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='128' height='128'%3E%3Cfilter id='paperGrain'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.7' numOctaves='4' stitchTiles='stitch'/%3E%3CfeColorMatrix type='saturate' values='0'/%3E%3C/filter%3E%3Crect width='128' height='128' filter='url(%23paperGrain)'/%3E%3C/svg%3E");
    background-size: 128px 128px;
    opacity: var(--paper-grain);
    mix-blend-mode: overlay;
    pointer-events: none;
}

/* Buttons lifted off the page. --shadow-dx/--shadow-dy are written to :root by
   index.astro so that, on the landing page, every shadow on the page swings
   away from the same moving light as the chart's. Other pages ship no script,
   so they fall back to the resting offsets and simply sit still.

   .site-nav a[aria-current="page"] out-specifies this rule and takes its own
   shadow below instead, because it needs a differently-shaped one. */
.site-nav a,
.contact-button,
.strip-button {
    box-shadow:
        calc(var(--shadow-dx, 0px) * 0.45) calc(var(--shadow-dy, 15px) * 0.4) 14px -6px var(--object-shadow);
}

/* The active tab is the page itself poking up above the fold, so its shadow
   belongs on the chart behind it and must not show below its own bottom edge,
   where there is no chart left to catch it — only the page it is continuous
   with.

   That cannot be done by tuning the shadow, which is worth knowing before
   trying. Blurring approximates a Gaussian whose standard deviation is *half*
   the blur radius, and a Gaussian has no endpoint: one deviation past the
   shadow's hard edge it is still at ~16% of its alpha, two at ~2%. So no
   combination of offset, spread and blur makes it stop on a line — offset only
   slides that hard edge and spread only resizes it, while the falloff carries
   on past wherever they put it. The strip below covers it instead.

   The offsets here are therefore only about where the shadow sits, not how far
   it reaches: a slight lift, so more of it gathers above the tab where the
   chart is. */
.site-nav a[aria-current="page"] {
    box-shadow: calc(var(--shadow-dx, 0px) * 0.3) -4px 16px -4px var(--object-shadow);
}

/* Covers the part of that shadow which falls past the header, sitting above
   .site-header-inner so it hides the shadow while the tab itself still paints
   over the top of it. Masking rather than clipping: it needs nothing newer
   than absolute positioning, and leaves the focus ring — which outline-offset
   puts outside the border box — completely alone, where a clip would have
   sliced its bottom edge off.

   16px is comfortably enough: the shadow's hard edge sits 8px above the tab's
   bottom (offset -4 plus spread -4) and is ~2% of its alpha two deviations
   past that, i.e. by 8px below the fold. It does mean this paints over the top
   16px of the content area — free today, since .page-shell opens with 72px+ of
   padding, but the reason not to put anything flush to the top there. */
.site-header::before {
    content: "";
    position: absolute;
    z-index: 2;
    right: 0;
    bottom: -16px;
    left: 0;
    height: 16px;
    background: var(--paper);
    pointer-events: none;
}

/* Header edge shadow — same story as the hero's bottom edge: the page below
   overlaps the header rather than butting against it. Layered beneath
   .site-header-inner so it shades the open chart area without darkening the
   active tab, which is the thing casting it. .site-header needs its own
   stacking context, or the negative-order painting of this pseudo-element
   depends on ancestors it should not care about. */
.site-header {
    position: relative;
    isolation: isolate;
}

.site-header::after {
    content: "";
    position: absolute;
    z-index: 0;
    right: 0;
    bottom: 0;
    left: 0;
    height: 16px;
    background: linear-gradient(to top, var(--edge-shadow), transparent);
    pointer-events: none;
}
.site-header-inner {
    position: relative;
    z-index: 1;
}
