/* ─────────────────────────────────────────────────────────────────────────
   editorial.css — Shared editorial layout system

   The vocabulary used by the redesigned Services and About pages:
     · dark-hero background layers (glow / grid / grain / 3D canvas)
     · scroll reveals
     · hairline index rows, outlined numerals, staggered step rails
     · logo & wordmark marquees

   Behaviour for reveals and counters lives in assets/js/editorial.js.
   Loaded globally from layouts/app.php — every rule is namespaced so it
   only applies to pages that opt in by using the classes.
───────────────────────────────────────────────────────────────────────── */

/* ══ Dark-hero background layers ═══════════════════════════════════════ */

/* Warm brand glow + cooler magenta counterweight. Low opacity so it reads
   as light falling on the section, not as a colour fill. */
.hero-glow {
    background:
        radial-gradient(46% 52% at 78% 44%, rgba(240, 90, 34, 0.14) 0%, rgba(240, 90, 34, 0) 68%),
        radial-gradient(42% 46% at 12% 88%, rgba(196, 38, 142, 0.10) 0%, rgba(196, 38, 142, 0) 70%);
    opacity: 0.55;
    animation: hero-breathe 12s ease-in-out infinite;
}
@keyframes hero-breathe {
    0%, 100% { opacity: 0.42; }
    50%      { opacity: 0.68; }
}

/* Softer sibling for dark bands further down a page */
.ed-glow {
    background:
        radial-gradient(38% 48% at 82% 18%, rgba(240, 90, 34, 0.10) 0%, rgba(240, 90, 34, 0) 70%),
        radial-gradient(40% 44% at 8% 92%, rgba(196, 38, 142, 0.09) 0%, rgba(196, 38, 142, 0) 72%);
}

/* 60px grid, masked so it dissolves toward every edge */
.hero-grid {
    opacity: 0.03;
    background-image:
        linear-gradient(rgba(255, 255, 255, 1) 1px, transparent 1px),
        linear-gradient(90deg, rgba(255, 255, 255, 1) 1px, transparent 1px);
    background-size: 60px 60px;
    -webkit-mask-image: radial-gradient(72% 68% at 62% 42%, #000 0%, rgba(0, 0, 0, 0.35) 58%, transparent 100%);
            mask-image: radial-gradient(72% 68% at 62% 42%, #000 0%, rgba(0, 0, 0, 0.35) 58%, transparent 100%);
}

/* Fine grain — inline fractal-noise SVG, no extra request. Kills the
   banding that large blurred gradients produce on 8-bit displays. */
.hero-grain {
    opacity: 0.035;
    mix-blend-mode: overlay;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='160' height='160' filter='url(%23n)'/%3E%3C/svg%3E");
}

/* Wrapper carries the fade-in so the canvas keeps its own responsive opacity */
.hero-canvas {
    opacity: 0;
    animation: hero-canvas-in 1.4s ease 0.15s forwards;
}
@keyframes hero-canvas-in { to { opacity: 1; } }

/* Below lg the 3D scene sits behind the copy rather than beside it */
@media (max-width: 1023px) {
    .hero-canvas canvas { opacity: 0.5; }
}


/* ══ Hero service/stat rail — the index rows in miniature ═══════════════ */
.hero-line-label,
.hero-line-num { transition: color 0.35s ease; }
.hero-line-label {
    padding-bottom: 2px;
    border-bottom: 1px solid transparent;
    transition: color 0.35s ease, border-color 0.35s ease;
}
.hero-line:hover  .hero-line-label,
.hero-line.is-active .hero-line-label { color: #ffffff; }
.hero-line.is-active .hero-line-label { border-bottom-color: rgba(240, 90, 34, 0.7); }
.hero-line.is-active .hero-line-num   { color: #f05a22; }


/* ══ Scroll reveal ═════════════════════════════════════════════════════ */
[data-reveal] {
    opacity: 0;
    transform: translateY(20px);
}
[data-reveal].is-in {
    opacity: 1;
    transform: none;
    transition: opacity 0.7s cubic-bezier(0.22, 1, 0.36, 1),
                transform 0.7s cubic-bezier(0.22, 1, 0.36, 1);
}


/* ══ Hairline index rows (sticky service/section switchers) ═════════════ */
.ed-idx-title,
.ed-idx-num { transition: color 0.28s ease, transform 0.28s ease; }
.ed-idx-arrow {
    opacity: 0;
    transform: translate(-4px, 4px);
    transition: opacity 0.28s ease, transform 0.28s ease;
}
.ed-idx-bar {
    transform: scaleX(0);
    transform-origin: left center;
    transition: transform 0.4s cubic-bezier(0.22, 1, 0.36, 1);
}
.ed-idx.is-active .ed-idx-title { color: #111827; transform: translateX(2px); }
.ed-idx.is-active .ed-idx-num   { color: #f05a22; }
.ed-idx.is-active .ed-idx-arrow { opacity: 1; transform: none; }
.ed-idx.is-active .ed-idx-bar   { transform: scaleX(1); }

/* Detail stage: hairline accent ties the panel back to its index row */
.ed-stage::before {
    content: '';
    position: absolute;
    top: 0; left: 0; right: 0;
    height: 2px;
    background: linear-gradient(90deg, #f05a22, #c4268e 45%, transparent);
}
.ed-stage-glyph { stroke-width: 1; }


/* ══ Staggered step rail (process / timeline) ══════════════════════════ */
@media (min-width: 1024px) {
    .ed-step-body { margin-left: var(--ed-shift, 0); }
}

.ed-step-rail {
    transform: scaleY(0);
    transform-origin: top center;
    transition: transform 0.8s cubic-bezier(0.22, 1, 0.36, 1) 0.1s;
}
.ed-step.is-in .ed-step-rail { transform: scaleY(1); }

.ed-step-node {
    transform: translateX(-50%) scale(0);
    transition: transform 0.5s cubic-bezier(0.34, 1.56, 0.64, 1);
    box-shadow: 0 0 0 4px rgba(240, 90, 34, 0.14);
}
.ed-step.is-in .ed-step-node { transform: translateX(-50%) scale(1); }

.ed-step-body { transition: transform 0.3s ease; }
.ed-step:hover .ed-step-body { transform: translateX(4px); }

/* Outlined numeral — the editorial anchor of a row. Light variant for
   white/gray bands, default for dark. */
.ed-numeral {
    color: transparent;
    -webkit-text-stroke: 1px rgba(255, 255, 255, 0.28);
    transition: -webkit-text-stroke-color 0.3s ease, color 0.3s ease;
}
.ed-numeral-dark { -webkit-text-stroke-color: rgba(17, 24, 39, 0.18); }

.ed-step:hover  .ed-numeral,
.ed-row:hover   .ed-numeral { -webkit-text-stroke-color: rgba(240, 90, 34, 0.85); }


/* ══ Hairline content rows ════════════════════════════════════════════ */
.ed-row { transition: background-color 0.3s ease; }
.ed-row-title { transition: color 0.25s ease, transform 0.3s ease; }
.ed-row:hover .ed-row-title { color: #f05a22; transform: translateX(3px); }


/* ══ CMS prose, set in two columns on wide screens ════════════════════ */
.ed-prose > * + * { margin-top: 1rem; }
.ed-prose p { break-inside: avoid; }

@media (min-width: 1024px) {
    .ed-prose {
        column-count: 2;
        column-gap: 4rem;
    }
    /* A first paragraph must not leave a one-line orphan at the column break */
    .ed-prose > *:first-child { margin-top: 0; }
}


/* ══ Text tabs + minimal pagination (shared by listing pages) ═════════ */
.ed-tabs {
    scrollbar-width: none;
    -ms-overflow-style: none;
}
.ed-tabs::-webkit-scrollbar { display: none; }

.ed-tab {
    border-bottom: 1px solid transparent;
    transition: color 0.25s ease, border-color 0.25s ease;
}
.ed-tab.is-active {
    color: #ffffff;
    border-bottom-color: #f05a22;
}
/* Light-background variant */
.ed-tab-light.is-active { color: #111827; border-bottom-color: #f05a22; }

.ed-page { border-bottom: 1px solid transparent; }
.ed-page.is-active {
    color: #111827;
    border-bottom-color: #f05a22;
}


/* ══ Case study (story) pages ═════════════════════════════════════════ */
/* Reading aids are driven by assets/js/story.js */

/* Sticky chapter rail with a reading-progress line along its bottom edge */
.cs-chapters {
    position: sticky;
    top: 4.2rem;
    z-index: 9000;
    background: rgba(11, 14, 22, 0.94);
    backdrop-filter: blur(14px);
    border-top: 1px solid rgba(255, 255, 255, 0.07);
    border-bottom: 1px solid rgba(255, 255, 255, 0.07);
}
.cs-rail {
    display: flex;
    align-items: center;
    gap: 1.75rem;
    overflow-x: auto;
    scrollbar-width: none;
    -ms-overflow-style: none;
}
.cs-rail::-webkit-scrollbar { display: none; }

.cs-chapter-link {
    flex-shrink: 0;
    display: inline-flex;
    align-items: baseline;
    gap: 0.5rem;
    padding: 0.9rem 0;
    font-size: 13px;
    color: rgba(255, 255, 255, 0.4);
    border-bottom: 1px solid transparent;
    transition: color 0.25s ease, border-color 0.25s ease;
}
.cs-chapter-link:hover { color: rgba(255, 255, 255, 0.75); }
.cs-chapter-link .cs-chapter-num {
    font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
    font-size: 10px;
    color: rgba(255, 255, 255, 0.25);
    transition: color 0.25s ease;
}
.cs-chapter-link.is-active { color: #ffffff; border-bottom-color: #f05a22; }
.cs-chapter-link.is-active .cs-chapter-num { color: #f05a22; }

.cs-progress {
    height: 2px;
    background: linear-gradient(90deg, #f05a22, #c4268e);
    transform: scaleX(0);
    transform-origin: left center;
    will-change: transform;
}

/* Long-form prose */
.cs-prose p {
    font-size: 1.0625rem;
    line-height: 1.75;
    color: #4b5563;
}
.cs-prose p + p { margin-top: 1.25rem; }
.cs-prose-dark p { color: rgba(255, 255, 255, 0.6); }

/* Opening statement — the one oversized paragraph per story */
.cs-lead {
    font-size: clamp(1.35rem, 2.4vw, 1.75rem);
    line-height: 1.5;
    color: #111827;
    font-weight: 500;
}

/* Pull quote */
.cs-quote {
    font-family: var(--font-heading);
    font-size: clamp(1.5rem, 3vw, 2.25rem);
    line-height: 1.25;
    font-weight: 700;
    letter-spacing: -0.01em;
}

/* Gallery stills */
.cs-shot-img { transition: transform 0.9s cubic-bezier(0.22, 1, 0.36, 1); }
.cs-shot:hover .cs-shot-img { transform: scale(1.045); }
.cs-shot { cursor: zoom-in; }

/* The hover scrim and caption sit above the image, so they were eating the
   click that opens the lightbox. Only the <img> is interactive. */
.cs-shot > *:not(img) { pointer-events: none; }
.cs-shot img { cursor: zoom-in; }
.cs-shot img:focus-visible {
    outline: 2px solid #f05a22;
    outline-offset: 3px;
}

/* Lightbox */
.cs-lb { z-index: 10100; }

@media (prefers-reduced-motion: reduce) {
    .cs-shot-img { transition: none; }
    .cs-progress { transition: none; }
}


/* ══ Parallax background layers ═══════════════════════════════════════ */
/* Behaviour lives in assets/js/parallax.js. The layer is inset beyond the
   section on both edges so the translated image can never expose a gap. */
.par-host { position: relative; overflow: hidden; }

.par-layer {
    position: absolute;
    inset: -14% 0;
    z-index: 0;
    overflow: hidden;
    pointer-events: none;
}

.par-img {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    object-fit: cover;
    object-position: center;
    will-change: transform;
    transform: translate3d(0, 0, 0);
}

/* Slow breathing zoom — applied to the PARENT so it cannot collide with the
   translate JS writes on .par-img. This is what keeps a still image alive. */
@keyframes par-drift {
    0%, 100% { transform: scale(1.03); }
    50%      { transform: scale(1.10); }
}
.par-layer-drift { animation: par-drift 26s ease-in-out infinite; }

/* Scrim: keeps small hairline-ledger text readable over a photograph */
.par-scrim {
    position: absolute;
    inset: 0;
    z-index: 0;
    pointer-events: none;
    background:
        linear-gradient(180deg,
            rgba(22, 29, 43, 0.92) 0%,
            rgba(22, 29, 43, 0.72) 38%,
            rgba(22, 29, 43, 0.76) 62%,
            rgba(22, 29, 43, 0.94) 100%);
}
.par-img-dim { opacity: 0.75; }

/* Type over a photograph: a hint of shadow keeps small mono lines crisp
   without having to dim the image itself. */
.par-host h2,
.par-host h3 { text-shadow: 0 1px 3px rgba(11, 15, 24, 0.45); }
.par-host p  { text-shadow: 0 1px 2px rgba(11, 15, 24, 0.55); }

@media (prefers-reduced-motion: reduce) {
    .par-layer-drift { animation: none; }
}


/* ══ Marquee (wordmarks or logos) ═════════════════════════════════════ */
.ed-marquee-mask {
    overflow: hidden;
    -webkit-mask-image: linear-gradient(90deg, transparent, #000 12%, #000 88%, transparent);
            mask-image: linear-gradient(90deg, transparent, #000 12%, #000 88%, transparent);
}
.ed-marquee {
    display: flex;
    align-items: center;
    gap: 2.5rem;
    width: max-content;
    animation: ed-scroll 42s linear infinite;
}
.ed-marquee-slow { animation-duration: 60s; }
.ed-marquee:hover { animation-play-state: paused; }
@keyframes ed-scroll { to { transform: translateX(-50%); } }

.ed-marquee-item {
    font-family: var(--font-heading);
    font-size: 1.5rem;
    font-weight: 700;
    color: rgba(255, 255, 255, 0.28);
    white-space: nowrap;
    transition: color 0.3s ease;
}
.ed-marquee-item:hover { color: rgba(255, 255, 255, 0.85); }
.ed-marquee-dot {
    width: 5px; height: 5px;
    border-radius: 50%;
    background: #f05a22;
    opacity: 0.5;
    flex-shrink: 0;
}

/* Logo variant — greyscale until hovered */
.ed-logo {
    flex-shrink: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    height: 4rem;
    width: 9rem;
    filter: grayscale(1);
    opacity: 0.45;
    transition: filter 0.3s ease, opacity 0.3s ease;
}
.ed-logo:hover { filter: grayscale(0); opacity: 1; }
.ed-logo img { max-height: 100%; max-width: 100%; object-fit: contain; }


/* ══ Portrait tiles (leadership) ══════════════════════════════════════ */
.ed-portrait img {
    filter: grayscale(1);
    transition: filter 0.5s ease, transform 0.7s cubic-bezier(0.22, 1, 0.36, 1);
}
.ed-portrait:hover img { filter: grayscale(0); transform: scale(1.04); }
.ed-portrait-name { transition: color 0.25s ease; }
.ed-portrait:hover .ed-portrait-name { color: #f05a22; }


/* ══ Reduced motion ══════════════════════════════════════════════════ */
@media (prefers-reduced-motion: reduce) {
    .hero-canvas   { opacity: 1; animation: none; }
    .hero-glow     { animation: none; }
    .ed-marquee    { animation: none; }
    [data-reveal]  { opacity: 1; transform: none; }
    .ed-step-rail  { transform: scaleY(1); }
    .ed-step-node  { transform: translateX(-50%) scale(1); }
    .hero-line-label,
    .hero-line-num,
    .ed-portrait img,
    .ed-row-title  { transition: none; }
}


/* ══ Form fields ═════════════════════════════════════════════════════
   Baseline horizontal padding for every text-entry control, so no field
   ever has its text or caret flush against its own edge. Element-level
   selectors wrapped in :where(), which keeps specificity at 0-0-1 so any
   padding utility in the markup still wins. (Bare :not() chains would each
   add specificity and override the utilities instead.) */
input:where(:not([type="checkbox"], [type="radio"], [type="hidden"], [type="submit"],
                 [type="button"], [type="reset"], [type="range"], [type="color"],
                 [type="file"])),
textarea,
select {
    padding-left: 0.9rem;
    padding-right: 0.9rem;
}
