/**
 * Circuit board 3D study â€” page styles.
 *
 * Only ever loaded by template-circuit-3d.php, which enqueues it
 * directly. The study writes its own <head> rather than going through
 * get_header(), so nothing else on the site pulls this in.
 *
 * Three groups live here, and they are not the same kind of thing:
 *
 *   .study-stage  the canvas and its reveal
 *   .study-hud    working chrome, shown only in tune mode (M)
 *   .study-tune   working chrome, shown only in tune mode (M)
 *   .study-nav    the page's own UI, always up
 *
 * The two tune-mode blocks are temporary and go when the numbers are
 * settled; the nav stays.
 *
 * @package WordPress
 * @subpackage annualReport2026
 * @since Annual Report 2026 1.0
 */
html, body { height: 100%; }
body { margin: 0; overflow: hidden; background: #2a0308; }
.study-stage {
    position: fixed;
    inset: 0;
}
.study-stage canvas { display: block; }
/* Hidden until the ready gate opens, so the first thing shown is
   the opening frame rather than a half-built scene. */
.study-stage canvas { opacity: 0; transition: opacity 0.2s; }
.study-stage.is-ready canvas { opacity: 1; }
/* CSS3DRenderer appends its own container; keep it under the HUD. */
.study-stage > div { z-index: 1; }

/* --------------------------------------------------------------
   Section panel.

   The left-hand slab that arrives once the camera has landed on a
   section: the section's name and its stories. Sits above the CSS3D
   screens so it stays readable over them, below the nav so the bar
   still reads on top of it, and it only takes pointer events where
   there is actually something to click.

   Held back until the camera stops for the same reason the nav is:
   text sliding in over a board still in motion reads as two things
   happening at once.
   -------------------------------------------------------------- */

.study-panel {
    position: fixed;
    top: 0;
    bottom: 3rem;
    left: 0;
    z-index: 3;
    width: var(--panel-w);
    height: 100vh;
    display: flex;
    padding: 2rem var(--panel-gut-out) 2rem var(--panel-gut-in);
    box-sizing: border-box;
    pointer-events: none;
    color: #fff;
    font: 400 1rem/1.5 "Work Sans", system-ui, sans-serif;

    /* How far in the scrim and blur hold at full strength, and how hard
       the blur is. Both fade over the same distance. */
    --panel-fade: 55%;
    --panel-blur: 12px;

    /*
     * Width, and the two gutters — "in" is the screen edge the panel
     * is anchored to, "out" is the edge facing the board. Reading a
     * story opens all three out; see .is-article below.
     */
    --panel-w: min(47%, 46rem);
    --panel-gut-in: 2rem;
    --panel-gut-out: 2.5rem;
    --panel-measure: 34rem;
    visibility: hidden;
    transition: visibility 0s linear 0.6s;
}

.study-panel.is-open {
    visibility: visible;
    transition-delay: 0s;
}

/*
 * The scrim and the blur, as a layer of their own.
 *
 * backdrop-filter applies one radius across whatever element carries it
 * and cannot be graduated. What CAN be graduated is a mask, which fades
 * the filtered layer out over the sharp board beneath it — but a mask on
 * .study-panel would take the text with it. So the filter lives on a
 * pseudo-element, and the content sits above it as a separate layer:
 * unmasked, and sharp all the way across.
 *
 * Absolutely positioned, so it does not become a flex item of the panel.
 *
 * Strictly this is a cross-fade between blurred and sharp rather than a
 * falling blur radius. At 6px the two are indistinguishable.
 */
/*
 * Blur only — there is no scrim.
 *
 * This used to carry a dark gradient as well, on the usual reasoning
 * that type over live trace work needs something to sit on. In practice
 * the blur alone does it: the traces lose their edges, the type keeps
 * its own, and the board stays the colour it was rendered rather than
 * going muddy behind half the screen.
 */
.study-panel::before {
    content: "";
    position: absolute;
    inset: 0;
    -webkit-backdrop-filter: blur(var(--panel-blur));
    backdrop-filter: blur(var(--panel-blur));
    -webkit-mask-image: linear-gradient(to right, #000 var(--panel-fade), transparent);
    mask-image: linear-gradient(to right, #000 var(--panel-fade), transparent);

    /*
     * The fade-in lives here rather than on .study-panel deliberately: an
     * ancestor at less than full opacity becomes the backdrop root, and
     * the blur would then sample the panel's own empty background
     * instead of the board behind it.
     */
    opacity: 0;
    transition: opacity 0.45s ease;
}

.study-panel.is-open::before { opacity: 1; }

/*
 * Mirrored. Everything with a direction in it has to flip: which edge
 * the slab is pinned to, which way the scrim and the mask give way, and
 * which way the rows travel as they arrive.
 */
.study-panel.is-right {
    right: 0;
    left: auto;
    /* Mirrored: the screen edge is now on the right. */
    padding: 2rem var(--panel-gut-in) 2rem var(--panel-gut-out);
}

/* Only the mask flips; there is no longer a gradient to mirror. */
.study-panel.is-right::before {
    -webkit-mask-image: linear-gradient(to left, #000 var(--panel-fade), transparent);
    mask-image: linear-gradient(to left, #000 var(--panel-fade), transparent);
}

.study-panel.is-right .study-panel-eyebrow,
.study-panel.is-right .study-panel-title,
.study-panel.is-right .study-panel-intro,
.study-panel.is-right .study-panel-list li {
    transform: translateX(1.25rem);
}

.study-panel.is-right.is-open .study-panel-eyebrow,
.study-panel.is-right.is-open .study-panel-title,
.study-panel.is-right.is-open .study-panel-intro,
.study-panel.is-right.is-open .study-panel-list li {
    transform: none;
}

.study-panel-inner {
    /* Above ::before, so the mask never touches the type. */
    position: relative;
    z-index: 1;
    width: 100%;
    max-height: calc(100% - 5em);
    overflow-y: auto;
    /* Only the content is clickable; the rest of the slab lets the
       board through. */
    pointer-events: auto;
    scrollbar-width: thin;
}

.study-panel-eyebrow {
    margin: 0 0 0.35rem;
    font-size: 1.1rem;
    font-weight: 600;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: var(--ar-circuit);

    /* The FLIP in circuit3d.js writes transform and transition here
       directly and clears them when the move lands, so nothing in
       this file may set transform on it. */
    transform-origin: left top;
}

/* Empty in the list view: collapsed so it reserves no height above
   the section name, which would otherwise sit lower than the story
   list it belongs to. */
/*
 * Nothing above the section name in the list view, so the whole
 * line goes rather than sitting empty and holding height. Was
 * :empty, which no longer catches it now that the <p> always
 * contains a button.
 */
.study-panel:not(.is-article) .study-panel-eyebrow {
    display: none;
}

.study-panel-title {
    margin: 0 0 1.5rem;
    font-size: clamp(1.6rem, 3.2vw, 2.6rem);
    font-weight: 700;
    line-height: 1.1;
    letter-spacing: 0.02em;
    text-transform: uppercase;
}

/* --------------------------------------------------------------
   Reading a story in the panel.

   Clicking a story sends the list out the way it came in, flies the
   section name up into the sub-head slot, and brings the article
   down from the top. The list and the article share one place in
   the flow — whichever is not showing carries [hidden] and takes no
   room at all, so the panel never holds height for both.
   -------------------------------------------------------------- */


/*
 * The sub-head IS the way back.
 *
 * A button rather than a link because it goes nowhere: it closes
 * the story and returns the panel to its list. Inherits its type
 * from the <p> around it, except for the two properties a browser
 * hard-codes on every button — text-transform and letter-spacing
 * are reset to inherit or the caps and tracking are silently lost.
 */
.study-panel-back {
    display: inline-flex;
    align-items: baseline;
    gap: 0.55em;
    margin: 0;
    padding: 0;
    border: 0;
    background: none;
    color: inherit;
    font: inherit;
    letter-spacing: inherit;
    text-transform: inherit;
    cursor: pointer;
    transition: color 0.2s;
}

.study-panel-back-arrow {
    /* Nudges toward the exit on hover, which the words cannot do
       without reflowing the line. */
    transition: transform 0.2s ease;
}

.study-panel-back:hover,
.study-panel-back:focus-visible { color: #fff; }

.study-panel-back:hover .study-panel-back-arrow,
.study-panel-back:focus-visible .study-panel-back-arrow {
    transform: translateX(-0.25em);
}

/* Images an author places in the story body, as blocks. Stories no
   longer open with their featured image, so this is the only way one
   gets into the text — and it is placed where the author put it. */
.study-article-body img {
    display: block;
    max-width: 100%;
    height: auto;
    border-radius: 2px;
    width: 100%;
}

.study-article-body figure {
    margin: 4rem 0 4rem 0 !important;
}

.study-article-body figcaption {
    margin-top: 0.5rem;
    font-size: 0.8125rem;
    line-height: 1.45;
    color: #ffffff;
}

.study-article-body p,
.study-article-body ul,
.study-article-body ol {
    margin: 0 auto 2rem auto;
    font-size: 1rem;
    letter-spacing: .05em;
    line-height: 1.5em;
    color: #ffffff;
    max-width: 42rem;
}

.study-article-body .wp-block-heading {
    max-width: 42rem;
    margin: 0 auto 1.5rem auto;
    margin-bottom: 1.5rem !important;
}

.wp-block-pullquote p {
    font-size: 1.5em;
    font-weight: 900;
    text-shadow: 23px 26px 18px rgba(0,0,0,.5);
    text-transform: uppercase;
}

.study-article-lead {
    font-size: 1.0625rem !important;
    line-height: 1.5 !important;
    color: #fff !important;
}

/* Tags, where the post has any. */
.study-article-tags {
    margin-top: 1.75rem;
    padding-top: 1rem;
    border-top: 1px solid rgba(255, 255, 255, 0.18);
    font-size: 0.8125rem !important;
    max-width: 100% !important;
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 0.5em;
}

.study-article-tags a {
    background-color: #d00000;
    color: #fff;
    padding: 0.45rem 0.6rem;
    border-radius: 6px;
    text-decoration: none;
    /* The gap on the container already spaces these, in both
       directions; margins on top of it space them twice. */
}

/* A section with nothing in it yet. */
.study-panel-empty {
    border-bottom: 0;
}

.study-panel-empty p {
    margin: 0;
    padding: 0.85rem 0;
    font-size: 0.875rem;
    color: rgba(255, 255, 255, 0.55);
}

/*
 * Top to bottom.
 *
 * --i is set on each block by circuit3d.js after the content is
 * cloned in, because the content comes from WordPress and nothing
 * here can know how many blocks there will be.
 */
.study-article-next,
.study-article-body > * {
    opacity: 0;
    transform: translateY(0.75rem);
    transition:
        opacity 0.5s ease,
        transform 0.55s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.study-article.is-reading .study-article-next,
.study-article.is-reading .study-article-body > * {
    opacity: 1;
    transform: none;
    transition-delay: calc(var(--i, 0) * 70ms);
    margin-bottom: 2em;
}

@media (prefers-reduced-motion: reduce) {
    .study-article-next,
    .study-article-body > * { transition-duration: 0.01ms; }
}

.study-panel-list {
    margin: 0;
    padding: 0;
    list-style: none;
    border-top: 1px solid rgba(255, 255, 255, 0.18);
}

.study-panel-list li {
    border-bottom: 1px solid rgba(255, 255, 255, 0.18);
}

/* --------------------------------------------------------------
   A story row, and the featured image that opens out of it.

   The picture belongs to one story, so it lives in that story's
   link rather than behind the whole panel. Hovering the row opens
   a column on the trailing edge and the image slides out into it.

   Width, not opacity: an image that merely fades in would have to
   reserve its space permanently, which leaves a gap down the side
   of every row that is not being hovered.
   -------------------------------------------------------------- */

.study-panel-list a {
    display: flex;
    align-items: center;
    padding: 0.85rem;
    color: inherit;
    text-decoration: none;
    transition: background-color 0.3s cubic-bezier(0.42, 0.04, 1, 1);

    /* How wide the image opens, and how tall it sits. */
    --shot-w: 8.5rem;
    --shot-h: 5rem;
}

.study-story-text {
    /* min-width:0 so the flex item may shrink below its content —
       without it the text refuses to give up room and the image
       pushes the row wider instead of opening inside it. */
    flex: 1 1 auto;
    min-width: 0;
}

.study-story-shot {
    flex: 0 0 auto;
    width: 0;
    height: var(--shot-h);
    margin-left: 0;
    overflow: hidden;
    border-radius: 2px;
    transition:
        width 0.45s cubic-bezier(0.22, 0.61, 0.36, 1),
        margin-left 0.45s cubic-bezier(0.22, 0.61, 0.36, 1);
}

/*
 * The image keeps its full width while the box around it is still
 * closed, so it is revealed rather than squashed and then stretched
 * back out. It slides in from the trailing edge at the same time.
 */
.study-story-shot img {
    display: block;
    width: var(--shot-w);
    height: 100%;
    object-fit: cover;
    transform: translateX(1.5rem);
    opacity: 0;
    transition:
        transform 0.45s cubic-bezier(0.22, 0.61, 0.36, 1),
        opacity 0.35s ease 0.08s;
}

.study-panel-list a:hover .study-story-shot,
.study-panel-list a:focus-visible .study-story-shot {
    width: var(--shot-w);
    margin-left: 1rem;
}

.study-panel-list a:hover .study-story-shot img,
.study-panel-list a:focus-visible .study-story-shot img {
    transform: none;
    opacity: 1;
}

@media (prefers-reduced-motion: reduce) {
    .study-story-shot,
    .study-story-shot img { transition-duration: 0.01ms; }
    .study-story-shot img { transform: none; }
}

/* Narrow panels have no room to give away, so the image stays put
   and the row is text only. */
@media (max-width: 40rem) {
    .study-story-shot { display: none; }
}

.study-panel-list a:hover,
.study-panel-list a:focus-visible {
    background-color: #d00000;
}

.study-panel-list h3 {
    margin: 0 0 0.25rem;
    font-size: 1.0625rem;
    font-weight: 600;
    line-height: 1.3;
    transition: color 0.2s;
}

.study-panel-list p {
    margin: 0;
    font-size: 0.875rem;
    line-height: 1.45;
    color: rgba(255, 255, 255, 0.7);
    /* Three lines, however long the excerpt is. */
    display: -webkit-box;
    -webkit-line-clamp: 3;
    -webkit-box-orient: vertical;
    overflow: hidden;
}

/* Each row arrives just after the one above it. */
.study-panel-eyebrow,
.study-panel-title,
.study-panel-intro,
.study-panel-list li {
    opacity: 0;
    transform: translateX(-1.25rem);
    transition:
        opacity 0.5s ease,
        transform 0.55s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.study-panel.is-open .study-article-body{
    padding-top: 3em;
    padding-bottom: 5em;
    padding-right: var(--panel-padding-right);
}

.study-panel.is-open .study-panel-eyebrow {
    padding-top: 5em;
}

.study-panel.is-open .study-panel-eyebrow,
.study-panel.is-open .study-panel-title,
.study-panel.is-open .study-panel-intro,
.study-panel.is-open .study-panel-list li {
    opacity: 1;
    transform: none;
    transition-delay: calc(var(--i, 0) * 70ms);
}

/*
 * Opening a story sends the list back out the way it came in: same
 * direction, same stagger, faster and on an accelerating curve —
 * an exit that takes as long as an entrance reads as hesitation.
 *
 * It has to come after the rule above, and carry .is-open as well
 * as .is-article, because that rule says the opposite about the
 * same elements and .study-panel.is-right.is-open beats a plain
 * two-class selector. Equal weight, later position, wins.
 */
.study-panel.is-open.is-article .study-panel-intro,
.study-panel.is-open.is-article .study-panel-list li {
    opacity: 0;
    transform: translateX(-1.25rem);
    transition:
        opacity 0.28s ease,
        transform 0.32s cubic-bezier(0.55, 0, 1, 0.45);
    transition-delay: calc(var(--i, 0) * 45ms);
}

.study-panel.is-article .study-panel-list { pointer-events: none; }

/*
 * Reading takes more room than browsing.
 *
 * A list row is a title and three clamped lines, and it reads fine
 * in a narrow column. A whole story does not: at 34rem with 2rem of
 * gutter the copy runs close to the screen edge on one side and to
 * the board on the other. So the panel opens out — wider overall,
 * more air at both edges, and a longer measure for the text.
 *
 * Transitioned rather than snapped, because the panel is already on
 * screen when a story opens; it is the same slab getting bigger, not
 * a new one arriving. It runs on the same curve as the list leaving.
 */
.study-panel.is-article {
    --panel-w: 102vw;
    --panel-gut-in: 2vw;
    --panel-gut-out: 2vw;
    --panel-measure: calc(100%);
    --panel-fade: 40%;
    --panel-blur: 2px;
    --panel-padding-right: 30%;
}

/*
 * The reading column.
 *
 * The panel is now far wider than the text wants to be, so the measure
 * stops being a ceiling the copy grows into and starts being a column
 * placed inside a room. The eyebrow, the title and the article all share
 * it and all centre on it — constrain only the body and the headline
 * would sit alone at the panel's left edge with the text adrift in the
 * middle of the page.
 */
.study-panel.is-article .study-panel-inner > * {
    max-width: 100%;
    margin-inline: auto;
}

.study-panel-title {
    background-color: rgba(208, 0, 0, .8);
    padding: 1rem 1.5rem;
    box-shadow: 23px 31px 29px rgba(0, 0, 0, .3);
    border-radius: 8px 0 0 8px;
    padding-right: var(--panel-padding-right);
}

/*
 * The transition lives on the base rule, not on .is-article, so the
 * panel animates back to its browsing width as well as out to its
 * reading one. visibility keeps its own instant, delayed timing.
 */
.study-panel {
    transition:
        visibility 0s linear 0.6s,
        width 0.45s cubic-bezier(0.22, 0.61, 0.36, 1),
        padding 0.45s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.study-panel.is-open {
    transition:
        visibility 0s,
        width 0.45s cubic-bezier(0.22, 0.61, 0.36, 1),
        padding 0.45s cubic-bezier(0.22, 0.61, 0.36, 1);
}

@media (prefers-reduced-motion: reduce) {
    .study-panel,
    .study-panel.is-open { transition-duration: 0.01ms; }
}

/* A full-width panel has nothing to widen into. */
@media (max-width: 48rem) {
    .study-panel.is-article {
        --panel-w: 100%;
        --panel-gut-in: 1.5rem;
        --panel-gut-out: 1.5rem;
        --panel-padding-right: 0px;
    }
}

@media (prefers-reduced-motion: reduce) {
    .study-panel.is-open.is-article .study-panel-intro,
    .study-panel.is-open.is-article .study-panel-list li {
        transition-duration: 0.01ms;
    }
}

@media (prefers-reduced-motion: reduce) {
    .study-panel,
    .study-panel-eyebrow,
    .study-panel-title,
    .study-panel-list li {
        transform: none;
        transition-duration: 0.01ms;
    }
}

@media (max-width: 48rem) {
    .study-panel { width: 100%; }
}

.study-hud {
    position: fixed;
    left: 1rem;
    /* Clear of the section bar, which is always up. */
    bottom: 4.75rem;
    z-index: 5;
    max-width: 26rem;
    padding: 0.75rem 1rem;
    border: 1px solid rgba(255, 255, 255, 0.16);
    border-radius: 3px;
    background: rgba(0, 0, 0, 0.42);
    color: rgba(255, 255, 255, 0.86);
    font: 400 0.8125rem/1.5 ui-monospace, "Cascadia Code", Consolas, monospace;
    -webkit-backdrop-filter: blur(6px);
    backdrop-filter: blur(6px);
    pointer-events: none;
}
.study-hud strong {
    display: block;
    margin-bottom: 0.25rem;
    font-weight: 600;
    letter-spacing: 0.04em;
    text-transform: uppercase;
    font-size: 0.6875rem;
    color: rgba(255, 255, 255, 0.55);
}
.study-hud em {
    display: block;
    margin-top: 0.5rem;
    font-style: normal;
    font-size: 0.75rem;
    color: rgba(255, 255, 255, 0.45);
}
.study-hud pre {
    margin: 0.6rem 0 0;
    font: inherit;
    line-height: 1.45;
    white-space: pre;
    color: #ffd9c9;
    /* Selectable so the numbers can be grabbed without the button. */
    pointer-events: auto;
    user-select: text;
}
.study-hud button {
    margin-top: 0.6rem;
    padding: 0.3rem 0.7rem;
    border: 1px solid rgba(255, 255, 255, 0.3);
    border-radius: 2px;
    background: rgba(255, 255, 255, 0.08);
    color: inherit;
    font: inherit;
    font-size: 0.75rem;
    cursor: pointer;
    pointer-events: auto;
}
.study-hud button:hover,
.study-hud button:focus-visible {
    background: rgba(255, 255, 255, 0.18);
}
/* --------------------------------------------------------------
   Temporary tuning panel. Delete along with the TUNERS block in
   circuit3d.js once the numbers are settled.
   -------------------------------------------------------------- */
.study-tune {
    position: fixed;
    top: 1rem;
    right: 1rem;
    z-index: 6;
    width: 17rem;
    max-height: calc(100vh - 2rem);
    overflow-y: auto;
    padding: 0.75rem 1rem 1rem;
    border: 1px solid rgba(255, 255, 255, 0.16);
    border-radius: 3px;
    background: rgba(0, 0, 0, 0.5);
    color: rgba(255, 255, 255, 0.86);
    font: 400 0.75rem/1.4 ui-monospace, "Cascadia Code", Consolas, monospace;
    -webkit-backdrop-filter: blur(6px);
    backdrop-filter: blur(6px);
}
.study-tune h2 {
    margin: 1rem 0 0.5rem;
    font-size: 0.6875rem;
    font-weight: 600;
    letter-spacing: 0.04em;
    text-transform: uppercase;
    color: rgba(255, 255, 255, 0.5);
}
.study-tune h2:first-child { margin-top: 0; }
.study-tune label {
    display: grid;
    grid-template-columns: 1fr auto;
    gap: 0 0.5rem;
    margin-bottom: 0.55rem;
}
.study-tune output { color: #ffd9c9; }
.study-tune input[type="range"] {
    grid-column: 1 / -1;
    width: 100%;
    margin: 0.15rem 0 0;
    accent-color: #ffab8d;
}
.study-tune button {
    width: 100%;
    margin-top: 0.9rem;
    padding: 0.4rem;
    border: 1px solid rgba(255, 255, 255, 0.3);
    border-radius: 2px;
    background: rgba(255, 255, 255, 0.08);
    color: inherit;
    font: inherit;
    cursor: pointer;
}
.study-tune button:hover,
.study-tune button:focus-visible {
    background: rgba(255, 255, 255, 0.18);
}
.study-tune p {
    margin: 0.6rem 0 0;
    color: rgba(255, 255, 255, 0.4);
}
/* --------------------------------------------------------------
   Section navigation. Unlike the HUD and the sliders this is not
   working chrome â€” it is the page's own UI and stays up in both
   modes.
   -------------------------------------------------------------- */
.study-nav {
    position: fixed;
    right: 0;
    bottom: 0;
    left: 0;
    z-index: 4;
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: 0.25rem 1rem;
    /*
     * Barely there. The board is the picture and the scrim only
     * has to keep the type off a bright trace, so this is a third
     * of the weight it started at and it runs out well before the
     * top of the bar.
     */
    color: #ffffff;
    font: 400 0.875rem/1.5 "Work Sans", system-ui, sans-serif;
    letter-spacing: 0.08em;
    padding: 2em;
    transition: background 0.5s;
}
.study-nav.is-revealed {
    background-color: rgba(208,0,0,.7);
    backdrop-filter: blur(4px);
}
/* A button, because it moves the camera â€” but it is the wordmark,
   so none of the chrome that implies. */
.study-nav-title {
    margin: 0;
    padding: 0.2rem 0;
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: 0 0.5em;
    border: 0;
    border-bottom: 2px solid transparent;
    background: none;
    color: inherit;
    font: inherit;
    font-size: 0.9375rem;
    /* A button matches the UA stylesheet rule that sets
       letter-spacing: normal and text-transform: none, and a rule
       that matches beats anything inherited â€” so the bar's casing
       and tracking have to be handed back explicitly. */
    letter-spacing: inherit;
    text-transform: inherit;
    white-space: nowrap;
    cursor: pointer;
}
.study-nav-title:hover,
.study-nav-title:focus-visible {
    border-bottom-color: #ffffff;
}
.study-nav-title[aria-pressed="true"] {
}
/* 900 is loaded too, if this wants to be heavier still. */
.study-nav-office { font-weight: 700; color: #fff; }
.study-nav-edition { font-weight: 400; color: #ffffff; }
/* --------------------------------------------------------------
   Reveal. The bar is not in the document's flow of attention until
   the camera has landed, so it starts hidden and is let in by JS
   once the opening move finishes. visibility, not just opacity,
   so nothing is tabbable while it is invisible.
   -------------------------------------------------------------- */
.study-nav-title {
        text-transform: uppercase;
}
.study-nav-title,
.study-nav-list li {
    opacity: 0;
    visibility: hidden;
    transform: translateY(0.6rem);
    transition:
        opacity 0.7s ease,
        transform 0.7s cubic-bezier(0.22, 0.61, 0.36, 1),
        visibility 0s linear 0.7s;
}
.study-nav.is-revealed .study-nav-title,
.study-nav.is-revealed .study-nav-list li {
    opacity: 1;
    visibility: visible;
    transform: none;
    /* Title first, then each section in turn. */
    transition-delay:
        calc(var(--i, 0) * 80ms),
        calc(var(--i, 0) * 80ms),
        0s;
}
@media (prefers-reduced-motion: reduce) {
    .study-nav-title,
    .study-nav-list li {
        transform: none;
        transition-duration: 0.01ms;
    }
}
.study-nav-list {
    display: flex;
    flex-wrap: wrap;
    gap: 0.25rem 1rem;
    margin: 0;
    padding: 0;
    padding-left: .5rem;
    list-style: none;
}
@media (max-width: 1240px) {
    .study-nav-list {
        display: none;
    }

    /*
     * order -1 puts the list above the wordmark rather than below it.
     * The bar is pinned to the bottom of the window, so a menu that
     * opened downward would open off the screen.
     */
    .study-nav.is-open .study-nav-list {
        display: flex;
        order: -1;
        width: 100%;
        flex-direction: column;
        align-items: flex-start;
        gap: 0;
        margin-bottom: 0.75rem;
        padding-left: 0;
        /* The rule that draws this is written for the horizontal bar. */
        border-left: 0;
    }

    .study-nav.is-open .study-nav-list li {
        width: 100%;
    }

    .study-nav.is-open .study-nav-list button {
        width: 100%;
        padding: 0.55rem 0;
        text-align: left;
        border-bottom-color: rgba(255, 255, 255, 0.2);
    }
}

.is-revealed .study-nav-list {
    border-left: 2px solid rgba(255, 255, 255, 0.5);
}
.study-nav-list button {
    padding: 0.2rem .5rem;
    border: 0;
    border-bottom: 2px solid transparent;
    background: none;
    color: #ffffff;
    font: inherit;
    /* See the note on .study-nav-title. */
    letter-spacing: inherit;
    text-transform: inherit;
    cursor: pointer;
    transition: border-bottom-color 0.2s;
}
.study-nav-list button:hover,
.study-nav-list button:focus-visible {
    color: #ffffff;
    border-bottom: 3px solid #ffffff;
}
.study-nav-list button[aria-pressed="true"] {
    color: #fff;
    border-bottom-color: #ffffff;
}
/* The board is the point; on a short window the bar gets out of
   its way rather than eating the view. */
@media (max-height: 34rem) {
    .study-nav {font-size: 0.8125rem;}
}

/* --------------------------------------------------------------
   Countdown chrome.

   The promotional board carries no navigation — there is nothing to
   navigate to — so instead it wears two lines: the report's name above
   the numerals and what the numerals mean below them.

   Both are centred on the viewport rather than on the board, because
   the asset is a screenshot of the window and the window is the frame.
   Pointer events stay off throughout: nothing here is clickable, and a
   caption that eats a drag would make the board feel stuck.
   -------------------------------------------------------------- */

.countdown-chrome {
    position: fixed;
    inset: 0;
    z-index: 4;
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    align-items: center;
    padding: 2.5rem 1.5rem;
    box-sizing: border-box;
    pointer-events: none;
    color: #fff;
    font: 400 1rem/1.4 "Work Sans", system-ui, sans-serif;
    text-align: center;
    text-shadow: 1px 1px 8px black;
}

.countdown-title {
    margin: 0;
    font-size: clamp(1rem, 2.1vw, 1.75rem);
    letter-spacing: 0.16em;
    /* Set in caps here rather than typed in caps, so the markup still
       reads normally to a screen reader. */
    text-transform: uppercase;
    /* The two halves sit on one line when there is room and stack when
       there is not, which is what a phone screenshot needs. */
    display: flex;
    flex-direction: column;
    flex-wrap: wrap;
    justify-content: center;
    gap: 0.15em 0.6em;
    margin-top: calc(50vh - 4em);
}

.countdown-office { font-weight: 700; }
.countdown-edition { font-weight: 400; }

.countdown-caption {
    margin: 0;
    font-size: clamp(0.8rem, 1.5vw, 1.25rem);
    font-weight: 600;
    letter-spacing: 0.22em;
    text-transform: uppercase;
    color: rgba(255, 255, 255, 0.88);
}

/* --------------------------------------------------------------
   Reveal, on the same cue the section bar uses: the container carries
   data-circuit3d-nav, so the JS that lets the bar in lets these in.
   visibility as well as opacity, so nothing is read out or focused
   while the opening move is still running.
   -------------------------------------------------------------- */

.countdown-title,
.countdown-caption {
    opacity: 0;
    visibility: hidden;
    transform: translateY(0.6rem);
    transition:
        opacity 0.7s ease,
        transform 0.7s cubic-bezier(0.22, 0.61, 0.36, 1),
        visibility 0s linear 0.7s;
}

.countdown-chrome.is-revealed .countdown-title,
.countdown-chrome.is-revealed .countdown-caption {
    opacity: 1;
    visibility: visible;
    transform: none;
    /* Title first, then the caption under the board. */
    transition-delay:
        calc(var(--i, 0) * 160ms),
        calc(var(--i, 0) * 160ms),
        0s;
}

@media (prefers-reduced-motion: reduce) {
    .countdown-title,
    .countdown-caption {
        transform: none;
        transition-duration: 0.01ms;
    }
}

/* --------------------------------------------------------------
   The editor link at the foot of a story.

   Only rendered for people who can edit the post, so this never
   reaches a visitor. Set apart from the tags above it rather than
   styled like them: it is a tool, not part of the story.
   -------------------------------------------------------------- */

.study-article-edit {
    margin-top: 1.5rem !important;
    font-size: 0.75rem !important;
    font-weight: 600;
    letter-spacing: 0.14em;
    text-transform: uppercase;
}

.study-article-edit a {
    color: rgba(255, 255, 255, 0.5);
    text-decoration: none;
    border-bottom: 1px solid rgba(255, 255, 255, 0.25);
    padding-bottom: 0.15em;
    transition: color 0.2s, border-color 0.2s;
}

.study-article-edit a:hover,
.study-article-edit a:focus-visible {
    color: #fff;
    border-bottom-color: rgba(255, 255, 255, 0.7);
}

/* --------------------------------------------------------------
   Additional Content.

   The strip of buttons an author added with the core Buttons block,
   lifted out of the story body by ar2026_split_buttons(). The whole
   section is absent from the markup when there are none, so there is
   nothing here to hide.

   Core's button styles assume a light page. These are restated for a
   dark panel rather than left to whatever the block editor's defaults
   resolve to, which is grey-on-grey here.
   -------------------------------------------------------------- */

.study-article-extra {
    /* Sits wherever the author put the buttons, so it needs room on
       both sides rather than only above — it is no longer the last
       thing on the page. */
    margin: 2rem 0;
    padding-top: 1.25rem;
    border-top: 1px solid rgba(255, 255, 255, 0.18);
}

.study-article-extra h3 {
    margin: 0 0 1rem;
    font-size: 1.25rem;
    font-weight: 600;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: var(--ar-circuit);
}

.study-article-extra .wp-block-buttons {
    display: flex;
    flex-wrap: wrap;
    gap: 0.6rem;
    margin: 0;
    padding: 0;
    list-style: none;
}

.study-article-extra .wp-block-button {
    margin: 0;
}

/* The element the editor's colour controls write to, so anything set
   per-button in the editor still wins over this. */
.study-article-extra .wp-block-button__link {
    display: inline-block;
    padding: 0.6rem 1.1rem;
    border: 1px solid #ffffff;
    border-radius: 2px;
    background: transparent;
    color: #fff;
    font-size: 0.875rem;
    font-weight: 600;
    line-height: 1.2;
    text-decoration: none;
    transition: background-color 0.25s, border-color 0.25s, color 0.25s;
}

.study-article-extra .wp-block-button__link:hover,
.study-article-extra .wp-block-button__link:focus-visible {
    background: #fff;
    border-color: #fff;
    color: #d00000;
}

/* Core's "filled" style, kept distinct from the outline above. */
.study-article-extra .wp-block-button.is-style-fill .wp-block-button__link {
    background: #d00000;
    border-color: #d00000;
}

.study-article-extra .wp-block-button.is-style-fill .wp-block-button__link:hover,
.study-article-extra .wp-block-button.is-style-fill .wp-block-button__link:focus-visible {
    background: #fff;
    border-color: #fff;
    color: #6d0a14;
}

@media (prefers-reduced-motion: reduce) {
    .study-article-extra .wp-block-button__link { transition-duration: 0.01ms; }
}

.study-article-body img {
    box-shadow: 29px 33px 38px rgba(0, 0, 0, .5);
    border-radius: 20px;
}

.study-article-body figure {
    position: relative;
    left: 1rem;
}

.study-article-body .png_style {
    left: 0em;
    max-width: 42rem;
    margin: 0px auto !important;
    display: block;
}

.study-article-body .png_style img {
    box-shadow: none;
}

.study-article-body .wp-block-image.size-large,
.study-article-body .wp-block-columns {
    width: 100%;
    max-width: 42em;
    position: relative;
    left: 0em;
    margin: 4rem auto 4rem auto !important;
}

.study-article-body .wp-block-gallery .wp-block-image.size-large{
    margin: 0px !important;
}

.study-article-body .alignright,
.study-article-body .alignright.wp-block-image.size-large {
    float: right;
    width: 40%;
    margin: 1em !important;
}

.study-article-body .alignfull,
.study-article-body .alignfull.wp-block-image.size-large {
    width: calc(100vw - 4vw);
    max-width: 100vw;
    position: relative;
    left: 0em;
    margin: 8rem 0 8rem 0 !important;
}

.study-article-body .alignwide {
    width: 100%;
    max-width: 100% !important;
    position: relative;
    left: 0em;
    margin-top: 8rem !important;
    margin-bottom: 8rem !important;
}

.study-article-body .wp-block-columns .wp-block-image {
    margin: 0rem auto 0rem auto !important;
}

.wp-block-quote p {
    box-sizing: border-box;
    overflow-wrap: break-word;
    font-weight:800;
    font-size: 2rem;
    text-shadow: 10px 10px 20px rgba(0, 0, 0, .55);
}

.wp-block-quote {
    margin: 4em 10% !important;
}

 
/* --------------------------------------------------------------
   What to read next.

   Built by circuit3d.js at the foot of every story: the following row
   in the same section, then the first row of the next, wrapping at the
   end so the last story leads back to the first rather than stopping.
   -------------------------------------------------------------- */

.study-article-next {
    margin-top: 2.5rem;
    padding-top: 1.5rem;
    border-top: 1px solid rgba(255, 255, 255, 0.18);
}

.study-article-next-link {
    /*
     * inline-grid, not grid: as a block it filled the reading
     * column, so the shadow it casts ran the full width of the page
     * and it read as a band rather than as something to press.
     * Sized to its contents, it is a button.
     */
    display: inline-grid;
    /* Image, then the words beside it; one column when there is no
       image, because the row is defined by its content rather than by
       a fixed track. The title is held short enough that the card
       stays a button instead of growing into a banner. */
    grid-template-columns: auto minmax(0, 22rem);
    align-items: center;
    gap: 0 1.25rem;
    max-width: 100%;
    color: inherit;
    text-decoration: none;
}

.study-article-next-link:only-child:not(:has(.study-article-next-shot)) {
    grid-template-columns: 1fr;
}

.study-article-next-label {
    grid-column: 2;
    margin-bottom: 0.35rem;
    font-size: 0.75rem;
    font-weight: 600;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: rgba(255, 171, 141, 0.9);
}

.study-article-next-shot {
    grid-column: 1;
    grid-row: 1 / span 2;
    width: 7.5rem;
    height: 5rem;
    object-fit: cover;
    border-radius: 2px;
    transition: transform 0.35s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.study-article-next-title {
    grid-column: 2;
    font-size: 1.0625rem;
    font-weight: 600;
    line-height: 1.3;
    transition: color 0.2s;
}

/* No image: the words take the whole width rather than leaving a gap
   where one would have been. */
.study-article-next-link:not(:has(.study-article-next-shot)) .study-article-next-label,
.study-article-next-link:not(:has(.study-article-next-shot)) .study-article-next-title {
    grid-column: 1;
}


/*
 * Fills with white on the way up, the same as an Additional Content
 * button. Both labels have to invert with it — the eyebrow is a pale
 * salmon and the title is white, and neither survives the change of
 * background. The underline goes: on a filled button the fill is
 * already saying the thing the underline was there to say.
 */
.study-article-next-link:hover .study-article-next-label,
.study-article-next-link:focus-visible .study-article-next-label {
    color: #d00000;
}

.study-article-next-link:hover .study-article-next-title,
.study-article-next-link:focus-visible .study-article-next-title {
    color: #6d0a14;
}

@media (prefers-reduced-motion: reduce) {
    .study-article-next-shot { transition-duration: 0.01ms; }
}

.figcaption, .wp-element-caption { 
    color: #ffffff;
}
/* --------------------------------------------------------------
   A section's standing introduction.

   Set as the category description in wp-admin and shown above that
   section's stories. Sized between the title above it and the rows
   below, so it reads as the section speaking rather than as the first
   story in the list.
   -------------------------------------------------------------- */

.study-panel-intro {
    margin: 0 0 1.5rem;
    max-width: 34rem;
}

.study-panel-intro p {
    margin: 0 0 0.75rem;
    font-size: 0.9375rem;
    line-height: 1.6;
    color: rgba(255, 255, 255, 0.82);
}

.study-panel-intro p:last-child {
    margin-bottom: 0;
}

/* --------------------------------------------------------------
   A row that leaves the report.

   Built to read as a story row, because to the reader it is one more
   thing in the list — only the small mark after the title says it goes
   somewhere else. It carries no data-story, so the panel never tries to
   open it in place.
   -------------------------------------------------------------- */

.study-panel-away h3::after {
    content: "\2197";
    display: inline-block;
    margin-left: 0.4em;
    font-weight: 400;
    /* Optically aligned with the cap height rather than the baseline. */
    transform: translateY(-0.05em);
    transition: transform 0.2s ease;
}

.study-panel-away a:hover h3::after,
.study-panel-away a:focus-visible h3::after {
    transform: translate(0.15em, -0.2em);
}

@media (prefers-reduced-motion: reduce) {
    .study-panel-away h3::after { transition-duration: 0.01ms; }
}

/* --------------------------------------------------------------
   Statistics and charts inside a story.

   Carries the printed report's treatment across: silver numerals for
   the research figures, ember for the rankings and the economic ones,
   and the agency breakdown as the same lollipop chart.

   Everything animates on arrival rather than on scroll. The content is
   cloned into the panel at the moment a story opens, so an animation
   declared here simply begins then — no observer, and nothing to
   re-arm when the story is opened a second time.
   -------------------------------------------------------------- */

.ar-stats {
    margin: 6rem 0;
    max-width: 100vw;
    width: calc(100vw - 4vw);
}

.ar-stats-group {
    text-align: center;
}

.ar-stats-group + .ar-stats-group {
    margin-top: 2.75rem;
}


/* ---- the figures ---- */

.ar-stat-grid {
    /*
     * A centred row, not a track grid.
     *
     * Each figure is sized in cqw against its own box, so anything that
     * ties that box's width to how many stats a section happens to hold
     * sets that section's numbers at a different size from the rest of
     * the page. An auto-fit grid did exactly that: a group of two filled
     * the row in two cells and came out at roughly twice the size of a
     * group of four. auto-fill fixed the size by keeping the tracks it
     * had no items for — which is how a group of four came to sit in a
     * five-column grid with a hole on the end.
     *
     * Flex has no tracks to leave empty. The width is pinned on the item
     * instead, below, so every figure on the page is the same size
     * whatever its section holds, and a short row simply centres.
     */
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: 5.75rem 5rem;
    margin: 0;
}

.ar-stat {
    /*
     * Takes the room it is offered up to this width, which is what sets
     * the figure size for the whole page; where there is less than the
     * basis to go round, the row wraps instead of squeezing.
     */
    flex: 1 1 14rem;
    max-width: 18rem;
    margin: 3em 1em;
}

.ar-stat-value {
    display: block;
    margin: 0 0 0.35rem;
    font-size: 28cqw;
    font-weight: 800;
    line-height: 0.95;
    letter-spacing: -0.02em;
    /* Tabular figures, so a counting number does not jiggle its own
       width as the digits change. */
    font-variant-numeric: tabular-nums;
    background-clip: text;
    -webkit-background-clip: text;
    color: transparent;
}

/* The printed report's two treatments. */
.ar-stat-value.is-silver {
    background-image: linear-gradient(170deg, #ffffff 18%, #b9c0c7 92%);
}

.ar-stat-value.is-ember {
    background-image: linear-gradient(170deg, #ffc24a 12%, #f6701f 88%);
}

.ar-stat dd {
    margin: 0;
    font-size: 0.875rem;
    line-height: 1.45;
    color: rgba(255, 255, 255, 0.82);
}

/* ---- the agency chart ---- */

.ar-chart {
    /*
     * The three bands a column is made of. They are named here so
     * they add up to the height above: a stem measured against the
     * whole column instead of its own band is taller than the column
     * itself at 100%, and the flex layout then takes the difference
     * out of whichever child will give — which was the name block,
     * leaving the first bar visibly shorter than the rest.
     *
     * Headroom is what the circle on the tallest stem sits in. The
     * reveal clips to the column, so anything above the top edge is
     * cut off rather than merely overflowing.
     */
    --stem-track: 32rem;
    --name-band: 11rem;
    --headroom: 2.4rem;
    display: flex;
    align-items: flex-end;
    gap: 1.4rem;
    height: calc(var(--stem-track) + var(--name-band) + var(--headroom) + 2rem);
    margin: 0;
    padding: 0;
    list-style: none;
    margin: 6rem 0;
    max-width: 100vw !important;
    width: calc(100vw - 20vw);
}

.ar-bar {
    display: flex;
    flex: 1 1 0;
    flex-direction: column;
    justify-content: flex-end;
    align-items: center;
    height: 100%;
    min-width: 0;
}

/*
 * The stem carries the value. Its height is the only thing that
 * differs between bars; the block beneath is a constant that exists to
 * hold the agency's name.
 */
.ar-bar-stem {
    position: relative;
    /* Never shrinks: the stem IS the measurement, so it is the one
       thing in the column that must keep the size it is given. */
    flex: 0 0 auto;
    width: 6px;
    height: calc(var(--h, 0) * var(--stem-track) / 100);
    background: rgba(255, 255, 255, 0.85);
}

.ar-bar-stem::before {
    content: "";
    position: absolute;
    top: -0.85rem;
    left: 12%;
    width: 0.7rem;
    height: 0.7rem;
    margin-left: -0.35rem;
    border: 3px solid #fff;
    border-radius: 50%;
    background: transparent;
}

.ar-bar-pct {
    flex: 0 0 auto;
    margin: 0.5rem 0 0.35rem;
    padding: 0.15rem 0.35rem;
    border-radius: 2px;
    background: rgba(255, 255, 255, 0.92);
    color: #3a1116;
    font-size: 0.625rem;
    font-weight: 700;
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
}

.ar-bar-name {
    display: flex;
    align-items: flex-end;
    justify-content: flex-start;
    width: 100%;
    /* The block the name sits in. Fixed, so every agency reads off the
       same baseline and only the stems vary. */
    /* Tied to the band declared on the chart, and told not to give any
       of it up — this is the child flex chose to shrink before. */
    flex: 0 0 var(--name-band);
    height: var(--name-band);
    padding: 0.5rem 10px;
    box-sizing: border-box;
    border: 2px solid #d00000;
    background: linear-gradient(180deg, #f9a03f 0%, #ef5a24 100%);
    color: #fff;
    font-size: 0.75rem;
    font-weight: 700;
    line-height: 1.1;
    /* Reading up the bar, as the printed chart does. */
    writing-mode: vertical-rl;
    transform: rotate(180deg);
    border-radius: 0px 0px 8px 8px;
}

.ar-bar-name i {
    font-style: normal;
    font-weight: 400;
    opacity: 0.85;
}

/* ---- arrival ---- */

@keyframes ar-rise {
    from { clip-path: inset(100% 0 0 0); }
    to   { clip-path: inset(0 0 0 0); }
}

@keyframes ar-lift {
    from { opacity: 0; transform: translateY(0.75rem); }
    to   { opacity: 1; transform: none; }
}

/*
 * The whole column is revealed upward rather than the bar being scaled.
 * Scaling would squash the rotated name and flatten the circle on the
 * stem; a clip reveals the same shape without distorting any of it.
 */
.ar-bar {
    animation: ar-rise 0.85s cubic-bezier(0.22, 0.61, 0.36, 1) both;
    animation-delay: calc(var(--i, 0) * 70ms + 150ms);
}

.ar-stat {
    animation: ar-lift 0.6s cubic-bezier(0.22, 0.61, 0.36, 1) both;
    container-type: inline-size;
    text-align: center;
}

.ar-stat:nth-child(2) { animation-delay: 80ms; }
.ar-stat:nth-child(3) { animation-delay: 160ms; }
.ar-stat:nth-child(4) { animation-delay: 240ms; }

@media (prefers-reduced-motion: reduce) {
    .ar-bar,
    .ar-stat { animation: none; }
}

/* ---- narrow ---- */

@media (max-width: 46rem) {
    /*
     * Ten vertical bars in a phone-width column leaves each about 30
     * pixels, which no rotated label survives. Laid on its side the
     * chart reads the same and the names stay horizontal.
     */
    .ar-chart {
        display: grid;
        grid-template-columns: 1fr;
        gap: 0.5rem;
        height: auto;
    }

    .ar-bar {
        display: grid;
        grid-template-columns: 1fr auto;
        align-items: center;
        gap: 0.25rem 0.75rem;
        height: auto;
    }

    .ar-bar-stem {
        /* Now a horizontal rule whose LENGTH carries the value. */
        grid-column: 1;
        grid-row: 2;
        width: calc(var(--h, 0) * 1%);
        min-width: 2px;
        height: 3px;
        border-radius: 2px;
        background: linear-gradient(90deg, #f9a03f, #ef5a24);
    }

    .ar-bar-stem::before {
        top: 50%;
        left: auto;
        right: -0.35rem;
        margin: -0.35rem 0 0;
    }

    .ar-bar-pct {
        grid-column: 2;
        grid-row: 2;
        margin: 0;
    }

    .ar-bar-name {
        grid-column: 1 / -1;
        grid-row: 1;
        height: auto;
        padding: 0;
        background: none;
        writing-mode: horizontal-tb;
        transform: none;
        font-size: 0.8125rem;
    }
}

/* --------------------------------------------------------------
   Lifting off the page.

   One gesture shared by the three things in a story that can be
   clicked: the Additional Content buttons, the tags, and the card
   pointing at the next story. Flat at rest, and on hover or keyboard
   focus they rise while a shadow grows underneath — the shadow is the
   evidence of the lift rather than a decoration they wear all the time.

   The resting shadow is written out in full as transparent rather than
   as `none`. A shadow cannot animate out of `none` — it would snap in
   on hover and snap out again, which is the one thing this is trying
   not to do.

   Shared through a custom property so the three stay in step, and so
   the distance can be changed in one place.
   -------------------------------------------------------------- */

.study-article-extra .wp-block-button__link,
.study-article-tags a,
.study-article-next-link {
    --lift: 0.3rem;

    box-shadow: 0 0 0 rgba(0, 0, 0, 0);
    transform: translateY(0);
    /* will-change is deliberately absent: three small elements do not
       need their own compositor layers held open permanently. */
    transition:
        transform 0.28s cubic-bezier(0.22, 0.61, 0.36, 1),
        box-shadow 0.28s ease,
        background-color 0.25s ease,
        border-color 0.25s ease,
        color 0.25s ease;
}

.study-article-extra .wp-block-button__link:hover,
.study-article-extra .wp-block-button__link:focus-visible,
.study-article-tags a:hover,
.study-article-tags a:focus-visible,
.study-article-next-link:hover,
.study-article-next-link:focus-visible {
    transform: translateY(calc(var(--lift) * -1));
    box-shadow: 6px 12px 22px rgba(0, 0, 0, 0.38);
}

/*
 * The card has no surface of its own, and a shadow cast by nothing
 * reads as a grey rectangle floating on the board. So it gets one on
 * the way up — declared here at zero alpha rather than omitted,
 * because a colour cannot animate out of nothing.
 *
 * The border is there at rest too, transparent, for the same reason:
 * adding one on hover would change the box size and shift the words
 * inside it by a pixel.
 */
.study-article-next-link {
    padding: 0.75rem;
    margin-left: -0.75rem;
    border: 1px solid rgba(255, 255, 255, 0);
    border-radius: 6px;
    background-color: rgba(255, 255, 255, 0);
}

.study-article-next-link:hover,
.study-article-next-link:focus-visible {
    border-color: #fff;
    background-color: #fff;
}

@media (prefers-reduced-motion: reduce) {
    .study-article-extra .wp-block-button__link,
    .study-article-tags a,
    .study-article-next-link {
        transition-duration: 0.01ms;
        transform: none;
    }
}


a:where(:not(.wp-element-button)) {
    color: #ffffff !important;
}
/* --------------------------------------------------------------
   The sections toggle.

   Hidden by default and shown only at the width where the list has
   collapsed, so it never offers to open something already open. The
   bars become a cross when the list is out, which is the only visual
   confirmation a bare icon can give.
   -------------------------------------------------------------- */

.study-nav-toggle {
    display: none;
    align-items: center;
    gap: 0.6rem;
    margin-left: auto;
    padding: 0.35rem 0;
    border: 0;
    background: none;
    color: inherit;
    font: inherit;
    /* Buttons inherit neither of these. */
    letter-spacing: inherit;
    text-transform: inherit;
    cursor: pointer;
}

/*
 * One element and its two pseudo-elements make three bars: the middle
 * one is the element itself. The outer two are positioned off it, so
 * the whole thing collapses to a cross by rotating them onto the
 * middle and fading the middle out.
 */
.study-nav-toggle-bars {
    position: relative;
    display: block;
    width: 1.25rem;
    height: 2px;
    background: currentColor;
    transition: background-color 0.2s;
}

.study-nav-toggle-bars::before,
.study-nav-toggle-bars::after {
    content: "";
    position: absolute;
    left: 0;
    width: 100%;
    height: 2px;
    background: currentColor;
    transition: transform 0.25s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.study-nav-toggle-bars::before { top: -0.4rem; }
.study-nav-toggle-bars::after  { top: 0.4rem; }

.study-nav.is-open .study-nav-toggle-bars {
    /* Transparent rather than removed: the box still has to hold the
       two bars that are now crossing over it. */
    background: transparent;
}

.study-nav.is-open .study-nav-toggle-bars::before {
    transform: translateY(0.4rem) rotate(45deg);
}

.study-nav.is-open .study-nav-toggle-bars::after {
    transform: translateY(-0.4rem) rotate(-45deg);
}

/* On the narrowest windows the icon says it on its own. */
@media (max-width: 26rem) {
    .study-nav-toggle-word {
        position: absolute;
        width: 1px;
        height: 1px;
        margin: -1px;
        padding: 0;
        overflow: hidden;
        clip-path: inset(50%);
        white-space: nowrap;
    }
}

@media (prefers-reduced-motion: reduce) {
    .study-nav-toggle-bars,
    .study-nav-toggle-bars::before,
    .study-nav-toggle-bars::after { transition-duration: 0.01ms; }
}

/*
 * Shown only where the list has collapsed.
 *
 * This has to come AFTER the rule above that hides it. A media query
 * adds nothing to specificity, so the two `display` declarations are
 * equally weighted and the later one wins at every width — with the
 * order reversed, the button was hidden on every screen there is.
 */
@media (max-width: 1240px) {
    .study-nav-toggle {
        display: inline-flex;
    }
}

/* ---------------------------------------------------------------
   Which section a tagged story belongs to

   Only on the tag list. A section list already says where its
   stories live — it is the heading above them — so there the label
   would be the same four words on every row. A tag draws from the
   whole report, and where a story sits is part of what it is.

   Set above the title and under it in weight, so the eye still
   lands on the headline first.
   --------------------------------------------------------------- */

.study-story-where {
    margin: 0 0 0.15rem;
    font-size: 0.72rem;
    font-weight: 600;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    opacity: 0.62;
}
