/* ==========================================================================
   Events listing page (Figma: QF - BilAraby - WebsiteDesign-Concept-2,
   node 40001286:71113 "events"). Reuses the --hr-* tokens declared globally
   in layout-revamp.css and follows the same page-pattern established by
   podcasts-revamp.css / partnership-revamp.css: an "Innerpage-hero"
   (breadcrumb + diamond divider) on a flat "liquid" gradient wash, no photo
   banner — here the wash is blue rather than coral/amber, matching Figma's
   hero for this page.
   ========================================================================== */
.events-revamp .hr-accent { color: var(--hr-yellow-500); }

/* ---------- Hero ---------- */
/* Wash, grain and hero height are deliberately identical to the Annual
   Gatherings and Speakers listings - same stops, same tile, same .7 overlay,
   same decay mask, same 256/200/160 hero. They had drifted into three
   different treatments of the same Figma hero. */
.events-revamp {
    /* The filter pill's raised state, shared by the active tab and the hover
       preview of it. Same four layers the videos listing carries as
       --vid-pill-shadow and the Search page as --srp-pill-shadow - three
       ambient drops under an inset white highlight. Figma's ramp opens with two
       further layers at alpha 0; they paint nothing, so they are documented
       rather than emitted. Keep the three in step. */
    --evt-pill-shadow:
        2px 23px 14px rgba(0, 0, 0, .02),
        1px 10px 10px rgba(0, 0, 0, .03),
        0 3px 6px rgba(0, 0, 0, .03),
        inset 0 4px 6.1px rgba(255, 255, 255, .23);
    /* Hero height as a variable so the wash derives from it instead of the two
       drifting apart - same pattern as summit-listing-revamp.css. */
    --evt-hero-h: 256px;
    --evt-wash-h: calc(var(--evt-hero-h) + 80px);
    position: relative;
    overflow-x: hidden;
    /* Matched to the Annual Gatherings / Speakers wash: identical stops, and a
       height tied to the hero rather than a flat 468px. The px-stop version
       here ran 468px down the page, well past the h1; ending after the hero
       stops it above the heading like the other two.

       Curve borrowed from About Us, which is the one that reads as a liquid flow
       into the cream rather than a band that stops - the same change made to
       .summit-listing-revamp (which carries the full derivation) and
       .speakers-revamp. Its wash is a Figma SVG export
       (about-revamp/hero-banner.svg) whose alpha, sampled down its 424px box,
       runs .91 / .84 / .75 / .59 / .42 / .23 / .01 at 0 / 42 / 106 / 170 / 233 /
       297 / 348px and is spent by 82% of the box; those samples are renormalised
       onto 0-100% here (each position over that 0.82). The four stops this
       replaces held .55 all the way to 80% and then fell to zero inside the last
       64px - the whole transition happened at the end, at roughly twice About
       Us's rate, which is the hard edge.
       Colour is untouched; only the falloff is borrowed. This page's geometry is
       the listing's exactly (256px hero, h1 at 376px), so hero + 80px leaves the
       same 40px of clearance under the heading. */
    background: var(--hr-cream-500) linear-gradient(to bottom,
        rgba(0, 80, 135, .91) 0%,
        rgba(0, 80, 135, .84) 12.2%,
        rgba(0, 80, 135, .75) 30.5%,
        rgba(0, 80, 135, .59) 48.8%,
        rgba(0, 80, 135, .42) 67.1%,
        rgba(0, 80, 135, .23) 85.4%,
        rgba(0, 80, 135, 0) 100%) no-repeat top center;
    background-size: 100% var(--evt-wash-h);
}
/* Figma's hero asset carries a fine grain/noise texture baked into the PNG
   (same reason bilaraby-talks-revamp.css/press-releases-revamp.css keep a
   checked-in banner instead of a flat gradient) — a plain linear-gradient()
   can't reproduce that, it renders perfectly flat/plastic instead of the
   "brushed" look. Re-add it as a tiny tiled feTurbulence SVG blended over
   the gradient rather than switching back to a raster banner. The
   feComponentTransfer re-centers the turbulence output to ~mid-gray before
   the overlay blend — without it the raw noise is skewed bright, so overlay
   tints the whole wash lighter instead of just adding grain. */
.events-revamp::before {
    content: "";
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: var(--evt-wash-h);
    background-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0naHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnIHdpZHRoPScxODAnIGhlaWdodD0nMTgwJz48ZmlsdGVyIGlkPSduJz48ZmVUdXJidWxlbmNlIHR5cGU9J2ZyYWN0YWxOb2lzZScgYmFzZUZyZXF1ZW5jeT0nMC44NScgbnVtT2N0YXZlcz0nMicgc3RpdGNoVGlsZXM9J3N0aXRjaCcvPjxmZUNvbG9yTWF0cml4IHR5cGU9J3NhdHVyYXRlJyB2YWx1ZXM9JzAnLz48ZmVDb21wb25lbnRUcmFuc2Zlcj48ZmVGdW5jUiB0eXBlPSdsaW5lYXInIHNsb3BlPScxJyBpbnRlcmNlcHQ9Jy0wLjIzMDInLz48ZmVGdW5jRyB0eXBlPSdsaW5lYXInIHNsb3BlPScxJyBpbnRlcmNlcHQ9Jy0wLjIzMDInLz48ZmVGdW5jQiB0eXBlPSdsaW5lYXInIHNsb3BlPScxJyBpbnRlcmNlcHQ9Jy0wLjIzMDInLz48L2ZlQ29tcG9uZW50VHJhbnNmZXI+PC9maWx0ZXI+PHJlY3Qgd2lkdGg9JzEwMCUnIGhlaWdodD0nMTAwJScgZmlsdGVyPSd1cmwoI24pJy8+PC9zdmc+");
    background-repeat: repeat;
    opacity: .7;
    mix-blend-mode: overlay;
    /* Decays at the wash's own rate (its alphas normalised against the .91
       start), so the texture cannot outlive the blue beneath it. Same mask,
       opacity and tile as the Annual Gatherings and Speakers heroes. */
    -webkit-mask-image: linear-gradient(to bottom,
        rgba(0,0,0,1) 0%, rgba(0,0,0,.923) 12.2%, rgba(0,0,0,.824) 30.5%,
        rgba(0,0,0,.648) 48.8%, rgba(0,0,0,.462) 67.1%, rgba(0,0,0,.253) 85.4%,
        rgba(0,0,0,0) 100%);
    mask-image: linear-gradient(to bottom,
        rgba(0,0,0,1) 0%, rgba(0,0,0,.923) 12.2%, rgba(0,0,0,.824) 30.5%,
        rgba(0,0,0,.648) 48.8%, rgba(0,0,0,.462) 67.1%, rgba(0,0,0,.253) 85.4%,
        rgba(0,0,0,0) 100%);
    pointer-events: none;
    z-index: 0;
}
.evt-hero-decor {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: var(--evt-hero-h);
    overflow: hidden;
    pointer-events: none;
    z-index: 0;
}
/* Geometry copied from .sml-hero-pattern (summit-listing-revamp.css) so both
   heroes carry the same corner wedges: anchored to the hero's BOTTOM edge, and
   the end one blended through overlay exactly as Figma composites it. */
.evt-hero-pattern {
    position: absolute;
    bottom: 0;
    z-index: 0;
    background-repeat: no-repeat;
    background-size: 100% 100%;
    pointer-events: none;
}
.evt-hero-pattern-start {
    inset-inline-start: 0;
    width: 305.329px;
    height: 160.658px;
    background-image: url("../images/innerpage-hero/hero-pattern-nobanner-left.svg");
}
.evt-hero-pattern-end {
    inset-inline-end: 0;
    width: 305.29px;
    height: 204.731px;
    background-image: url("../images/innerpage-hero/hero-pattern-nobanner-right.svg");
    mix-blend-mode: overlay;
}
[dir="rtl"] .evt-hero-pattern { transform: scaleX(-1); }
/* Kept on phones, both corners, rather than dropped - the wedges are part of
   the hero at every width.

   They scale instead of holding 305px: at that size the pair is 610px against a
   390px screen, so they would overlap in the middle and be clipped. min() caps
   them at 190px (reached at ~432px, so 430/440-class phones render at the full
   190) and below that holds the pair at 88% of the width with a real gap
   between them. aspect-ratio carries each asset's own proportions - 305.329 x
   160.658 and 305.29 x 204.731 - which at 190px resolve to 100px and 128px, and
   both stay inside .evt-hero-decor's 160px clip box. Same treatment and the same
   numbers as .pr-hero-decor on the press releases hero, which uses assets of
   identical dimensions. */
@media (max-width: 767.98px) {
    .evt-hero-pattern-start {
        width: min(190px, 44%);
        height: auto;
        aspect-ratio: 305.329 / 160.658;
    }
    .evt-hero-pattern-end {
        width: min(190px, 44%);
        height: auto;
        aspect-ratio: 305.29 / 204.731;
    }
}

.evt-hero {
    position: relative;
    z-index: 1;
    height: var(--evt-hero-h);
    display: flex;
    align-items: flex-end;
    padding: 0 160px 24px;
}
.evt-hero-inner { position: relative; z-index: 1; max-width: 1600px; width: 100%; margin-inline: auto; }
.evt-breadcrumb-row { display: flex; align-items: center; justify-content: space-between; gap: 24px; }
.evt-breadcrumb { display: flex; align-items: center; gap: 12px; font-size: 20px; color: var(--hr-cream-500); text-transform: uppercase; }
/* Full strength per Figma's Breadcrumb component - only font weight marks the
   current crumb, there is no resting opacity on the others. Full note in
   press-releases-revamp.css. */
.evt-breadcrumb a,
.evt-breadcrumb span:not(.evt-breadcrumb-sep) { opacity: 1; }
.evt-breadcrumb a { color: inherit; text-decoration: none; transition: opacity .2s ease; }
.evt-breadcrumb a:hover { opacity: 1; color: inherit; text-decoration: underline; }
.evt-breadcrumb-current { font-weight: 700; opacity: 1 !important; }
.evt-breadcrumb-sep { width: 1px; height: 16px; background: rgba(249, 247, 234, .5); }
.evt-hero-divider { display: none; }
@media (min-width: 1200px) {
    .evt-hero-divider {
        display: flex;
        align-items: center;
        flex-shrink: 0;
        width: 280px;
        margin-inline-end: calc(-160px - max(0px, (100vw - 1920px) / 2));
    }
    .evt-hero-divider .evt-diamond {
        /* 20 * (sqrt(2) - 1) / 2. A rotated 20px square is 28.28px wide visually
           but still occupies a 20px layout box, so the 4.142px overhang per side
           would make neighbours merge into one continuous zigzag. This margin
           separates the boxes by exactly that overhang, so adjacent tips just
           touch - corner to corner, 0px visible gap, no merge. Carried on the
           diamond rather than as a `gap` on the row so the last one also spaces
           itself off the line. Matches .abt-diamond / .tnc-diamond / .sml-*. */
        width: 20px;
        height: 20px;
        margin-inline: 4.142px;
        transform: rotate(45deg);
        background: var(--hr-cream-500);
        flex-shrink: 0;
    }
    .evt-hero-divider-line { flex: 1 1 auto; height: 1px; background: rgba(249, 247, 234, .5);        /* The last diamond's own 4.142px slot margin supplies the gap now, so a
           negative offset here would eat into it. */
        margin-inline-start: 0; }
}
.evt-hero::after {
    content: "";
    position: absolute;
    inset-inline: 0;
    bottom: 0;
    height: 1px;
    background: rgba(249, 247, 234, .35);
}

/* ---------- Intro tagline ---------- */
/* 120px, matching .sml-listing on the Annual Gatherings page: with the shared
   256px hero and hero+64 wash, that is what leaves the same 56px between the
   wash's end and the h1. At the previous 64px the wash finished exactly on the
   title's top edge. */
.evt-intro { position: relative; z-index: 1; padding: 120px 160px 0; }
.evt-intro-inner { max-width: 1600px; margin-inline: auto; display: flex; flex-direction: column; gap: 16px; }
.evt-intro-inner h1 { font-size: 56px; line-height: 64px; font-weight: 700; color: var(--hr-brown-500); margin: 0; }
.evt-intro-inner p { font-size: 20px; line-height: 32px; color: var(--hr-brown-300); margin: 0; max-width: 900px; }

/* ---------- Featured spotlight event ---------- */
/* overflow:visible explicitly: app.css has a sitewide `section { overflow:
   hidden }` rule, and this is a <section> — without overriding it here, the
   watermark's intentional overflow past this section's own bottom edge (into
   .evt-listing below) gets clipped at this box's own edge regardless of
   anything else. Deliberately kept at the SAME z-index as .evt-listing (not
   raised above it): with equal z-index, DOM order means .evt-listing's own
   actual content (heading, filters, grid) still correctly paints over the
   diamond wherever that content exists, while .evt-listing's empty
   top-padding gap lets the diamond show through there — exactly "visible in
   the gap, hidden behind real content" rather than obscuring the heading. */
/* padding-bottom:120px (not 0): gives the bottom diamond accent (see
   .evt-bg-watermark below) enough clear room to render in full between the
   card and "All Events" — without it there's only .evt-listing's own 60px
   top padding to work with, less than the accent's own height, so it either
   gets clipped or has to be shifted up behind the card to avoid overlapping
   the heading. positionEventWatermark() in index.blade.php still nudges it
   further if needed for unusually tall cards, but that's a safety net now,
   not the primary mechanism. */
/* 80px top, not Figma's 60px: the watermark below is anchored to the CARD and
   overhangs it upward, so the gap above the card is also the room that overhang
   has to land in. At 60px a short card - a featured event with no description,
   which is how the Arabic page currently renders - put the mark's top edge 12px
   above this section on a wide monitor, grazing the intro line above. The extra
   20px moves card and mark down together, so the overhang stays inside the
   section. */
.evt-featured-wrap { position: relative; z-index: 1; overflow: visible; padding: 80px 160px 120px; }
.evt-featured-inner { position: relative; z-index: 1; max-width: 1600px; margin-inline: auto; }
/* The brand mark, pale and oversized, bleeding behind the featured card
   (Figma node 40001286:71114, exported as a flattened raster with its cream
   fill chroma-keyed to transparent — the vector-layer extractor dropped 2 of
   its 4 diamond accents, so the raster is the faithful source here).

   In Figma the card sits at a fixed fraction of this image's own box
   (left 8.333% / right 91.667% / top 5.451% / bottom 79.652% — derived
   directly from the vector's and the card's real Figma coordinates). Our
   card's aspect ratio doesn't match Figma's static 1600x627 mock, so no
   fixed CSS width/vw can keep that fraction correct at every viewport —
   only recomputing it against the CARD'S OWN rendered box does. top/left/
   width are therefore set by the positionEventWatermark() script in
   index.blade.php, on load and on resize; the rules below are just the
   base/pre-JS state. It sits behind .evt-featured-inner via z-index only,
   and .evt-featured-wrap has overflow:visible set (overriding app.css's
   sitewide `section { overflow: hidden }`) so it isn't clipped. */
.evt-bg-watermark {
    position: absolute;
    z-index: 0;
    top: 0;
    left: 0;
    max-width: none;
    height: auto;
    pointer-events: none;
}
/* Deliberately NOT mirrored in RTL (BIL-795). Every other decorative shape on
   this page flips - the hero wedges, the Past Gatherings corner - because they
   are abstract geometry with a handed composition. This one is not geometry: it
   is the brand wordmark, the word "بالعربي" itself, so scaleX(-1) rendered the
   Arabic script back-to-front on precisely the pages whose readers can see that.
   A wordmark reads the same in both locales. */
.evt-featured {
    position: relative;
    display: flex;
    align-items: stretch;
    border: 1px solid #fff;
    border-radius: 40px;
    /* Figma's card is p-[8px] around a rounded-[32px] image container (node
       40001286:71123), same as .sml-featured on the Summit listing page. Without
       it the media ran flush to the card's edge, so the 40px corner clipped the
       artwork square at the top-end/bottom-end corners instead of showing the
       image's own 32px rounding inside a cream inset. */
    padding: 8px;
    overflow: hidden;
    background: linear-gradient(to top, rgba(255,255,255,.6) 0%, rgba(255,255,255,.8) 76%, rgba(255,255,255,.8) 100%);
    -webkit-backdrop-filter: blur(53px);
    backdrop-filter: blur(53px);
    box-shadow: 0 3px 6px rgba(0,0,0,.03), 1px 10px 10px rgba(0,0,0,.03), 2px 23px 14px rgba(0,0,0,.02);
}
/* BIL-581 responsive pass: every size in the copy column is fluid rather than
   snapping at breakpoints, because the CARD's width is `viewport - 2x gutter`
   and so slides continuously - it only reaches Figma's 1600 at a 1920 viewport
   (1120 at 1440, 960 at 1280). Fixed desktop sizes in a continuously shrinking
   box are what drove the title to 5 lines and the card to 1204px tall at 1280.

   Each clamp is a straight line through two design points - its Figma value at
   a 1920 viewport, and a floor at 1200 (where the card stacks) - expressed as
   `Avw + B` so it lands exactly on both. The 1200 floors were re-derived to
   hold Figma's own card PROPORTION (1600x627, i.e. 2.55:1) rather than just to
   keep the type readable: at the previous floors the card ran 1114x627 at a
   1440 viewport - a 1.78 ratio, 40% taller than the design - and a card that
   far off proportion is what forced the background wordmark's MAX_INFLATE
   ceiling to clamp, which in turn is what left the mark stranded behind the
   card instead of bleeding past it the way the design shows. Same fluid-ratio approach
   as .hr-testimonial-card on the home page. Below 1200 the card is stacked and
   full-width, so the clamps sit at their floor and the <=767 block tightens
   further from there. */
.evt-featured-copy {
    flex: 1 1 0;
    min-width: 0;
    display: flex;
    flex-direction: column;
    justify-content: center;
    gap: clamp(28px, 3.89vw - 18.7px, 56px);
    padding: clamp(32px, 3.33vw - 8px, 56px);
}
.evt-featured-badge {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    align-self: flex-start;
    padding: 8px 16px;
    border-radius: 8px;
    background: var(--hr-blue-500);
    color: #e6f0ef;
    font-size: 14px;
    font-weight: 700;
    text-transform: uppercase;
}
.evt-featured-body { display: flex; flex-direction: column; gap: clamp(16px, 1.11vw + 2.7px, 24px); }
.evt-featured-body h2 {
    margin: 0;
    /* 48px at 1920 -> 28px floor. Unitless line-height so it tracks the
       font-size instead of leaving 56px of leading on 28px type. */
    font-size: clamp(28px, 2.78vw - 5.3px, 48px);
    line-height: 1.1667;
    font-weight: 700;
    background: linear-gradient(90deg, #d09a38 0%, #ac853a 100%);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}
/* Two lines, as in Figma. The blade already caps the description at 160
   characters, but how many LINES that is depends on the column width, and a
   third line at a narrow width is 25px of card height that the background mark
   then has to stretch to cover. */
.evt-featured-body p {
    margin: 0;
    font-size: clamp(14px, 0.56vw + 7.3px, 18px);
    line-height: 1.5556;
    color: var(--hr-brown-300);
    overflow: hidden;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
}
/* align-items:stretch, not center: the separator between Date and Place is a
   full-height rule with a diamond on it (below), so it has to take the row's
   height rather than its own content's. */
.evt-featured-meta { display: flex; align-items: stretch; gap: 24px; }
/* Date holds its own width on one line and Place takes the slack, the same
   split .sml-meta-item uses on the Summit listing page. Without it both columns
   shared the row evenly, which squeezed "26 - 27 January 2027" into four
   stacked lines and made the meta row the tallest thing in the card. */
.evt-featured-stat { display: flex; flex-direction: column; gap: clamp(6px, 0.28vw + 2.7px, 8px); flex: 1 1 auto; min-width: 0; }
.evt-featured-stat:first-child { flex: 0 0 auto; }
.evt-featured-stat:first-child strong { white-space: nowrap; }
/* Two lines max. A long real venue string ("Multaqa (Education City Student
   Center), Doha, Qatar.") runs to three at narrow widths, which no design
   shows and which makes the meta row the tallest block in the card. */
.evt-featured-stat strong {
    overflow: hidden;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
}
.evt-featured-stat span { font-size: clamp(15px, 0.69vw + 6.7px, 20px); line-height: 1.4; color: var(--hr-brown-300); }
.evt-featured-stat strong { font-size: clamp(18px, 0.83vw + 8px, 24px); line-height: 1.3333; font-weight: 700; color: var(--hr-brown-900); }
/* Figma node 40001286:71136 is a vertical hairline with a rotated square
   centred on it, not the bare 12px diamond this used to draw. Same recipe as
   .sml-meta-separator on the Summit listing page: a 16px-wide column carrying
   the 1px rule as a background, and the diamond as a centred ::before. */
.evt-featured-meta-sep {
    flex-shrink: 0;
    width: 16px;
    align-self: stretch;
    position: relative;
    /* Figma's "Line 21" is a GRADIENT stroke, not the flat rule this used to
       draw: it runs from the card surface at either end to #2f897f (green-400)
       at the 49% mark where the diamond sits, so both ends dissolve into the
       panel instead of stopping on a hard edge. Both orientations export the
       same three stops - the desktop node (40001286:71136) and the phone one
       (40004763:12940) - so the ramp lives here and only its AXIS flips at the
       phone breakpoint. Ends on transparent rather than Figma's literal white
       so it fades into the card's own glass instead of painting a white stub
       over it. The diamond keeps green-500; only the line is the lighter tone. */
    background: linear-gradient(to bottom, transparent 0%, var(--hr-green-400) 49%, transparent 100%) center / 1px 100% no-repeat;
}
.evt-featured-meta-sep::before {
    content: "";
    position: absolute;
    top: 50%;
    left: 50%;
    width: 16px;
    height: 16px;
    transform: translate(-50%, -50%) rotate(45deg);
    background: var(--hr-green-500);
}
.evt-featured-actions { display: flex; gap: 12px; align-items: center; flex-wrap: wrap; }
.evt-btn-primary,
.evt-btn-ghost {
    display: inline-flex;
    align-items: center;
    gap: 8px;
    padding: 16px 24px;
    border-radius: 61px;
    font-size: 16px;
    font-weight: 700;
    border: 1.5px solid transparent;
    text-decoration: none;
    cursor: pointer;
    box-shadow: inset 0 4px 6.1px rgba(255, 255, 255, .23), 0 3px 6px rgba(0, 0, 0, .03);
}
/* Same recipe as the home page's .hr-btn-primary (BIL-557/539). Two things
   were missing and one was invented:
   - `border: 2px outset #ffffff9c` with the bottom edge dropped is what gives
     the pill its lit top edge; a flat transparent 1.5px border read as a plain
     amber capsule.
   - the ambient shadow was a single layer instead of the four-layer stack, so
     the button sat flat on the card rather than lifting off it.
   - the hover fill swap to --hr-yellow-400 was invented: Figma's Variant2
     (1558:35896) keeps #d98500 and the same shadow stack, and lights the
     bottom ellipse instead (now shared from layout-revamp.css). The swap
     fought that glow for the same "something lit up" read. */
.evt-btn-primary {
    background: var(--hr-yellow-500);
    color: var(--hr-cream-50);
    border: 2px outset #ffffff9c;
    border-bottom-width: 0;
    box-shadow:
        inset 0 4px 6.1px rgba(255, 255, 255, .23),
        7px 63px 18px rgba(0, 0, 0, .02),
        2px 23px 14px rgba(0, 0, 0, .02),
        1px 10px 10px rgba(0, 0, 0, .03),
        0 3px 6px rgba(0, 0, 0, .03);
}
.evt-btn-primary:hover { color: var(--hr-cream-50); }
/* BIL-605: border was rgba(255,255,255,.1) - all but invisible against the
   featured card's own near-white glass background (rgba(255,255,255,.6-.8)),
   which made the button read as borderless/flat despite the inset glass
   highlight above already being there. Same visible tone .evt-past already
   uses below for the identical reason. */
/* Same recipe as the home page's .hr-btn-ghost-dark, the secondary pill on
   light surfaces (Figma nodes 40001286:67789 "Discover More", 40001286:67838
   "View All"). The .2 white fill already matched; what differed was the
   border-color (transparent, so the shared masked rim on ::after in
   layout-revamp.css had nothing to start from) and the ambient shadow. The
   hover fill swap to .4 was invented for the same reason as the primary's -
   Variant3 holds the .2 fill and lights the bottom ellipse instead.

   This rule also covers .evt-past's "View All Memories", which sits on the
   plain cream page background rather than the featured card's glass; the
   white-tinted fill is what shows up against both. */
.evt-btn-ghost {
    background: rgba(255, 255, 255, .2);
    border-color: rgba(255, 255, 255, .2);
    color: var(--hr-brown-900);
    box-shadow: 0 4px 6.1px rgba(0, 0, 0, .06);
    transition: all .2s ease-in-out;
}
.evt-btn-ghost:hover { color: var(--hr-brown-900); }
[dir="rtl"] .evt-btn-primary img,
[dir="rtl"] .evt-btn-ghost img { transform: scaleX(-1); }

.evt-featured-media {
    position: relative;
    /* A fixed share of the card, not a fixed pixel floor.

       This carried `min-width: 640px` to keep object-fit:cover's crop shallow,
       but a px floor against a card that slides from 1594 (at a 1920 viewport)
       down to 880 (at 1200) stops being a floor and becomes a hog: at 1280 it
       took 640 of the card's 954, leaving the copy 200px of inner width, which
       ran the title to 5 lines and the card to 1204px tall - and that runaway
       height in turn pinned the background wordmark at its 1920px ceiling
       instead of letting it shrink.

       46.5% is the proportion the two sides already had at 1920 (740/1594), so
       desktop is unchanged and every narrower width now scales instead of
       squeezing one side.

       On object-fit:cover's crop, measured rather than assumed: the box runs
       1.17 (1920 viewport) -> 0.97 (1600) -> 0.85 (1440) -> 0.76 (1280), so it
       does still turn portrait as the card narrows, and the side crop deepens
       with it (source art is 1584x1176, i.e. 1.35). That is strictly better
       than the px floor managed - 640 against a 1204-tall card at 1280 was an
       0.53 box - but it is not the design's own 1.17 either. Holding 1.17 needs
       a media box >=715px, which needs a card >=1537, which needs a ~1860
       viewport; below that a full-bleed photo and a readable copy column cannot
       both fit side by side, so the row band trades crop depth for legibility
       until the <=1199 stack takes over. */
    /* 42%, not the 46.5% this held: every px handed back to the copy column is
       a px of text that no longer has to wrap, and wrapped lines are what push
       the card off Figma's 2.55 proportion. Figma's own split is 49.5/50.5, but
       Figma's copy is also shorter than real CMS content at every field. The
       crop stays acceptable because both sides still scale together. */
    flex: 0 0 42%;
    min-width: 0;
    max-width: 792px;
    /* Figma's "Image container" is rounded-[32px] (node 40001286:71146), the
       same radius .sml-featured-media uses. Paired with .evt-featured's 8px
       padding above, this is what puts the image inside the card's corner
       instead of running under it. */
    border-radius: 32px;
    overflow: hidden;
    /* Matches the static artwork's own near-white backdrop (same fix as
       .sml-featured-media on the Summit listing page, which uses the same
       image) so there's no seam where the image meets the card. */
    background-color: #f6f5f1;
}
.evt-featured-media::before {
    content: "";
    position: absolute;
    inset: 0;
    /* Soft-edged radial gradients (long, transparent-ending stops) stand in for
       a blurred colour blob — an actual `filter: blur()` this large is
       expensive to composite and was intermittently blanking the viewport
       during scroll in headless Chromium. */
    background: radial-gradient(circle at 25% 20%, rgba(51, 138, 129, .5) 0%, rgba(51, 138, 129, .3) 25%, transparent 55%),
                radial-gradient(circle at 80% 70%, rgba(217, 133, 0, .45) 0%, rgba(217, 133, 0, .25) 25%, transparent 55%);
    z-index: 0;
}
.evt-featured-media img {
    /* Absolute + inset instead of width/height:100% — as a flex item capped
       by max-height, this container's height that a percentage would resolve
       against isn't reliably the same as its post-clamp rendered size in
       every engine, so height:100% could compute taller than the box and
       get hard-clipped by overflow:hidden. Absolute positioning fills the
       padding box directly, sidestepping that. */
    position: absolute;
    inset: 0;
    z-index: 1;
    display: block;
    width: 100%;
    height: 100%;
    object-fit: cover;
}

/* ---------- Listing ---------- */
.evt-listing { position: relative; z-index: 1; padding: 60px 160px 100px; }
.evt-listing-inner { position: relative; z-index: 1; max-width: 1600px; margin-inline: auto; }
.evt-listing-head { position: relative; z-index: 1; display: flex; align-items: flex-end; justify-content: space-between; gap: 16px; flex-wrap: wrap; margin-bottom: 40px; }
.evt-listing-title { font-size: 40px; font-weight: 700; color: var(--hr-brown-500); margin: 0; }
.evt-listing-count { font-size: 24px; color: var(--hr-brown-300); margin: 0; }

.evt-filters { position: relative; z-index: 1; display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 16px; margin-bottom: 40px; }
/* Inert above the phone breakpoint: the wrapper exists only so the tabs and the
   three selects can scroll as one row down there (see the <=767 block), and
   display:contents leaves this row the same flat flex it has always been. */
.evt-filter-row { display: contents; }
/* Upcoming/Past toggle — a plain two-state pill switch, not a dropdown. */
/* The auto end-margin absorbs the row's free space, which is what keeps the
   selects and the search box grouped together at the end of it. justify-content
   did that on its own while .evt-filters had exactly two children; the search
   box is now a third, having moved out of .evt-filter-fields so it can sit on
   its own row on a phone. */
.evt-tabs { display: flex; gap: 16px; align-items: center; flex-wrap: wrap; margin-inline-end: auto; }
.evt-tab {
    padding: 12px 20px;
    border-radius: 61px;
    border: 1px solid rgba(177, 175, 165, .5);
    background: rgba(236, 230, 211, .4);
    font-size: 16px;
    color: var(--hr-brown-500);
    cursor: pointer;
    transition: background-color .2s ease, border-color .2s ease, box-shadow .2s ease, transform .2s ease;
}
/* Hovering an inactive tab previews the active pill exactly - same cream-50
   fill, white rim and shadow - plus a 2px lift, which is how the videos listing
   (.vid-tab) answers the cursor. Scoped off .is-active: that pill is already at
   the destination and is not a target, so it should not move. */
.evt-tab:not(.is-active):hover {
    background: var(--hr-cream-50, #fefefd);
    border-color: #fff;
    box-shadow: var(--evt-pill-shadow);
    transform: translateY(-2px);
}
/* No bold on the selected tab - the white fill and the white rim are what mark
   it. Matches .pr-tab.is-active on the press releases listing, where Figma's own
   active tab (node 40000567:27721) is Almarai Regular; the 700 that was here
   made the filter row read heavy. */
.evt-tab.is-active {
    background: var(--hr-cream-50, #fefefd);
    border-color: #fff;
    /* The full stack, not the single 0 3px 6px this carried: the same raise the
       videos page gives its active pill, so the two rows read alike. */
    box-shadow: var(--evt-pill-shadow);
}
.evt-search {
    flex: 0 1 300px;
    max-width: 300px;
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 12px 20px 12px 16px;
    border-radius: 61px;
    background: rgba(236, 230, 211, .4);
    border: 1px solid rgba(177, 175, 165, .5);
}
.evt-search img { flex-shrink: 0; opacity: .7; }
.evt-search input {
    flex: 1 1 auto;
    min-width: 0;
    border: 0;
    background: transparent;
    font-size: 16px;
    color: var(--hr-brown-500);
}
.evt-search input:focus { outline: none; }
/* No opacity here: the colour token already matches .evt-select's own text
   (--hr-brown-500), so the .7 was the whole difference - it washed the
   placeholder to grey while "Type"/"Year"/"Location" next to it sat at full
   strength. Firefox also applies its own default placeholder opacity, so that
   is reset explicitly rather than left to the UA. */
.evt-search input::placeholder { color: var(--hr-brown-500); opacity: 1; }
/* app.css has a sitewide, unscoped `input:-webkit-autofill` rule that paints
   a solid green inset background behind autofilled text on EVERY input.
   Override it here — same trick used by podcasts-revamp.css. */
.evt-search input:-webkit-autofill,
.evt-search input:-webkit-autofill:hover,
.evt-search input:-webkit-autofill:focus,
.evt-search input:-webkit-autofill:active {
    -webkit-text-fill-color: var(--hr-brown-500) !important;
    box-shadow: 0 0 0 1000px transparent inset !important;
    -webkit-box-shadow: 0 0 0 1000px transparent inset !important;
    transition: background-color 5000s ease-in-out 0s !important;
}

/* nowrap at desktop — Figma shows Type/Year/Location/Search all on one row;
   wraps back to multiple rows only at the tablet/mobile breakpoints below,
   where there genuinely isn't room. */
.evt-filter-fields { display: flex; gap: 16px; align-items: center; flex-wrap: nowrap; }
/* A CAP rather than a fixed width. A bare <select> is sized by its widest
   option, which is why Location (longest value "Multaqa, Education City") sat at
   225px next to Year's 95px, and why the row re-flowed every time a filter
   changed - hence a width here at all. But 180px was far wider than the design:
   measuring the artboard's own row (node 40001286:71113) gives Type 98, Year 95
   and Location 121 - each pill is its LABEL plus the 20/40 padding, nothing
   more. Three 180px pills made the row 1107px wide against the design's 877,
   and that overflow is what broke it onto a second line on any laptop narrower
   than 1440, costing the section a whole wasted band under the filters.

   124px is Location's own 121 rounded up: the widest of the three labels still
   fits its placeholder un-truncated (the Arabic labels are shorter), while
   anything longer - a selected venue, a long category - is cut with an ellipsis
   rather than widening the control. Year sizes itself below the cap, at ~100,
   a four-digit option being all it has to fit. The open dropdown list is not
   constrained by any of this, so long values stay readable while choosing.

   Shrinking stays allowed on top of the cap: the row only stacks below 768px,
   so in the tablet range the pills compress rather than overflow. */
.evt-select {
    appearance: none;
    /* A CAP, not a fixed width: each pill is its LABEL plus the 20/40 padding,
       which is how the artboard draws them - and they are not equal there.
       Pixel-scanning the row in the exported render of node 40001286:71113 gives
       Type 98, Year 95, Location 121 against a 300px search field, on 14px gaps,
       and the same three measure ~103 / 98 / 128 off the design screenshot QA
       supplied at a different scale. Equal 180px pills came from reading the
       frame widths rather than what the frames actually paint.

       The wide gap that leaves between the tabs and the fields is the design's
       too, not a void to be filled: the artboard's own tabs end at x=359 and its
       Type pill starts at x=1102 inside a 1600 column. The row is
       justify-content: space-between - tabs at one end, fields at the other -
       so growing the pills to close that gap is what pushed this row away from
       the design, not toward it.

       124px is Location's 121 rounded up: the longest of the three labels still
       fits un-truncated (the Arabic ones are shorter), while a long selected
       value - a venue, a category - ellipsises rather than stretching the pill,
       so the row stays put whatever the option lists hold. Year sizes itself to
       ~96 below the cap, a four-digit option being all it has to fit. */
    width: auto;
    max-width: 124px;
    flex: 0 1 auto;
    min-width: 0;
    text-overflow: ellipsis;
    white-space: nowrap;
    overflow: hidden;
    padding: 12px 40px 12px 20px;
    border-radius: 61px;
    font-size: 16px;
    /* !important: custom.js sets an inline "placeholder" gray on every
       <select> site-wide on load. Ours always has a real selected value. */
    color: var(--hr-brown-500) !important;
    background: rgba(236, 230, 211, .4) url("../images/press-releases-revamp/icon-chevron-down.svg") no-repeat;
    background-size: 11px;
    background-position: right 20px center;
    border: 1px solid rgba(177, 175, 165, .5);
    cursor: pointer;
}
/* No focus styling of its own, matching every other filter select on the site
   (.sml-select, .vid-select, .blg-select, .pod-select, .tlk-select,
   .spk-select all leave this to the browser).
   There was a green ring here on :focus, which stayed on screen after picking a
   filter because Chrome keeps focus on a <select> once its popup closes. Moving
   it to :focus-visible did not help: Chrome matches :focus-visible on a select
   even for a mouse click, so the ring still appeared on every pick. The only
   way to be rid of it is not to draw one, which also makes this control
   consistent with the rest of the filters - the browser's own focus indicator
   is what remains, so keyboard focus is still visible. */
[dir="rtl"] .evt-select { background-position: left 20px center; padding: 12px 20px 12px 40px; }
/* No .evt-select width override here any more: the cap on the base rule already
   resolves to 124 / 96 / 124 at every width, and the row it makes (tabs 203 +
   16 + 344 + 32 + search 300 = 895) fits the content column down to 1280. The
   1200-1439 band below is what covers the last stretch, by shrinking the search
   field rather than breaking the row. */
@media (max-width: 1439.98px) {
}

/* ---------- Card grid ---------- */
.evt-grid {
    position: relative;
    z-index: 1;
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    align-items: stretch;
    gap: 24px;
    margin-bottom: 48px;
}
.evt-card {
    position: relative;
    display: flex;
    flex-direction: column;
    /* Grid stretches this to the row's tallest card by default, but nothing
       makes the card's own CONTENT grow to fill that height — a shorter
       description just left blank space, and depending on content it could
       still end up shorter than siblings. height:100% + .evt-card-body's
       flex:1/space-between (below) instead pins the chip/arrow row to the
       bottom and lets the description's own gap absorb the slack, so every
       card in a row matches its tallest sibling exactly. */
    height: 100%;
    border: 1px solid #fff;
    border-radius: 40px;
    padding: 8px;
    overflow: hidden;
    background: var(--hr-cream-600, #e3e1d4);
    -webkit-backdrop-filter: blur(53px);
    backdrop-filter: blur(53px);
    box-shadow: 0 3px 6px rgba(0,0,0,.03), 1px 10px 10px rgba(0,0,0,.03), 2px 23px 14px rgba(0,0,0,.02);
    isolation: isolate;
    text-decoration: none;
    color: inherit;
}
.evt-card:hover { color: inherit; }
/* Figma's "Frame 2147239190" - the geometric wordmark watermark sitting in the
   card's bottom-right corner, between the flat cream fill and the media/body
   above it. It was missing entirely, which is half of why the card read as flat
   cream: the body's gradient (below) now fades to transparent, so this is what
   shows through at the bottom of the panel. Same 512x329 exported asset the
   blog cards already use (identical path data), so no new file. z-index:-1
   keeps it above .evt-card's own background but under the in-flow content -
   .evt-card's isolation:isolate stops it escaping behind the card. */
.evt-card-motif {
    position: absolute;
    inset-inline-end: 0;
    bottom: 0;
    z-index: -1;
    width: 512px;
    height: 329px;
    background: url("../images/blogs-revamp/card-motif.svg") no-repeat right bottom / contain;
    opacity: .5;
    pointer-events: none;
}
[dir="rtl"] .evt-card-motif { transform: scaleX(-1); }
.evt-card-media {
    position: relative;
    height: 302px;
    /* Bottom radius (28px) matches .evt-card-body's own rounding exactly —
       .evt-card-body overlaps 40px on top of this image (margin-top:-40px),
       so its rounded top corners reveal whatever's behind them; if this
       image were square there, that showed as a visible straight-edge seam
       cutting across the body's curve. Matching radii here means the same
       curve continues underneath instead of clashing with a square corner. */
    border-radius: 32px 32px 28px 28px;
    overflow: hidden;
    background-image: var(--evt-card-bg);
    background-size: cover;
    background-position: center;
    background-color: var(--hr-brown-300);
}
/* The blurred bottom band, the layer the video cards also carry as
   .vid-card-media::before: an oversized copy of the same still, blurred and
   masked to the bottom of the box, so the caption row sits on softened image
   rather than on sharp detail. The ::after scrim below darkens that band but
   does not blur it - and that order matters. A backdrop-filter on the caption
   was tried instead, to size the band by the text's own box; it sits ABOVE the
   scrim, so it blurred the scrim's near-black bottom along with the photo and
   smeared it into a solid dark bar across the foot of every card. Blurring a
   copy of the STILL, underneath the scrim, is what keeps the darkening a clean
   gradient.

   inset:-30px gives the blur a runway outside the visible box, so its edges are
   fed by real image instead of fading into transparency inside the frame;
   .evt-card-media's overflow:hidden clips the overhang. The mask holds full
   strength across the band and closes over a short transition rather than
   dissolving across the whole card - the band is meant to read as a defined
   region, not a wash.

   The stops are in PX, not the 44%/51% they were. As percentages of a box 60px
   taller than the image, they put the band's edge ~155px up from the bottom of
   a 302px card while the caption's text ends at ~80px, leaving some 70px of
   blurred photo above the text it was supposed to be softening. Measured from
   this box's bottom - 30px below the image's own - 118px/142px puts full
   strength just past the caption and closes it out ~30px above, so the band
   reads as the caption's own strip. A caption that wraps to two rows reaches
   above the band; its upper row then sits on the scrim alone, as this card did
   before the band existed at all. */
.evt-card-media::before {
    content: "";
    position: absolute;
    inset: -30px;
    z-index: 0;
    background-image: var(--evt-card-bg);
    background-size: cover;
    background-position: center;
    filter: blur(12px);
    -webkit-mask-image: linear-gradient(to top, #000 0, #000 118px, transparent 142px);
    mask-image: linear-gradient(to top, #000 0, #000 118px, transparent 142px);
    pointer-events: none;
}
.evt-card-media::after {
    content: "";
    position: absolute;
    inset: 0;
    z-index: 1;
    background: linear-gradient(to top, rgba(0,0,0,.65) 0%, rgba(0,0,0,0) 55%);
    pointer-events: none;
}
/* bottom:56px, not 16px: .evt-card-body now overlaps the image by 40px
   (margin-top:-40px) — without the extra clearance here, the white gradient
   panel washes out this caption text right as it fades in. */
/* z-index:2, above both .evt-card-media pseudo-layers (the blurred band at 0
   and the scrim at 1) - at z-index:1 it tied with the scrim, which paints after
   in-flow children by default. */
/* nowrap: the date and the venue share ONE line, per the design. Wrapping put a
   long venue on a second row - "Doha Exhibition and Convention Center" dropped
   below its own date, so cards with a long venue stood two rows tall and cards
   with a short one stood one, and the caption sat at a different height on every
   card in the same grid. The phone board is a deliberate exception and stacks
   them under a hairline (see the flex-direction: column override below); this is
   the desktop row only. */
.evt-card-caption { position: absolute; z-index: 2; left: 24px; right: 24px; bottom: 56px; display: flex; flex-wrap: nowrap; gap: 11px; align-items: center; }
/* Which item gives way when the line is short: the venue, never the date. The
   date and the 1px tick hold their size (`flex: none`), and the venue is the
   only shrinkable item, so it takes the ellipsis the span rule below already
   sets up. Without this every item shrinks by its content ratio and the date
   truncates too - "27 - 28 July 2026" would come out as "27 - 28 Jul...". The
   venue is addressed as :last-child rather than by class because these spans
   carry none; it is last whenever it is present, and when it is absent the date
   inherits the rule harmlessly - a lone item on the line has nothing to shrink
   against. */
.evt-card-caption > span { flex: none; }
.evt-card-caption > span:last-child { flex: 0 1 auto; }
/* display:block rather than inline-flex, so a long venue string truncates
   instead of running off the card. The text sits as a bare text node beside the
   icon, and text-overflow only ellipsises text in a BLOCK formatting context -
   as an anonymous flex item it just overflowed: "Qatar National Convention
   Centre, Education City" measured 489px inside a 289px caption and was cut off
   at the card's edge on the details page's related row. min-width:0 is what lets
   the item shrink below that content width in the caption's own flex row. */
.evt-card-caption span {
    display: block;
    min-width: 0;
    max-width: 100%;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    font-size: 16px;
    font-weight: 300;
    color: var(--hr-cream-500);
}
/* The icon is an inline box now that its span is a block, so its 8px of
   separation is a margin rather than the flex gap it used to take. */
.evt-card-caption img { width: 16px; height: 16px; margin-inline-end: 8px; vertical-align: middle; filter: brightness(0) invert(1); }
.evt-card-caption-sep { width: 1px; height: 14px; background: rgba(249, 247, 234, .5); }
/* White-to-transparent gradient overlay, matching the Figma component spec
   (`bg-gradient-to-b from-white to-transparent`) — a separate layer from
   .evt-card's own flat cream background, not the same thing. Missed this
   entirely in the first pass; the card read as flat cream all the way
   through instead of fading lighter toward the title.

   position:relative + negative margin-top pulls this on top of the image
   above it instead of sitting flush below it — the white gradient starts
   fading in while still over the photo instead of starting at a hard seam. */
.evt-card-body {
    position: relative;
    z-index: 1;
    display: flex;
    flex: 1 1 auto;
    flex-direction: column;
    justify-content: space-between;
    gap: 16px;
    padding: 32px 24px 24px;
    margin-top: -40px;
    /* Title/description are the only things that normally give this box
       height beyond its padding+foot; when a translation is missing and
       the title renders empty (no title, no description), the box
       collapses to ~128px. At that height the 40px image overlap eats a
       third of the box, so the white gradient below is still only ~90%
       opaque by the time it clears the photo — reading as a short white
       "pill" floating on the image with a visible seam/shade underneath
       it, instead of a normal card panel. 160px matches a single-line
       title with no description (the shortest *intentional* case), so a
       genuinely empty title still gets a proportionate, seamless panel. */
    min-height: 160px;
    border-radius: 28px;
    /* Was `#fff 19%, transparent 150%` — percentage stops, so the flat
       100%-white plateau always ended and the fade always began at the
       same FRACTION of this box's own height, no matter how tall the box
       actually is. That fraction lands well inside the plain, textureless
       title/foot gap on most cards, and a gradient's slope changing from
       flat to declining reads to the eye as a faint straight line (Mach
       banding) even though the underlying colour change is smooth — the
       "shade line" cutting across the white panel. Fixed-px stops tie the
       transition to the actual 40px photo overlap instead: nearly opaque
       already at the top, fully solid #fff by the time the panel clears
       the photo, and flat (no further stop, so no further kink) for
       everything below.

       The Figma node is `bg-gradient-to-b from-white to-transparent`: the panel
       is meant to FADE OUT down its own height so the card's cream fill (and
       the watermark above) shows through toward the chip/arrow row. Stopping at
       a flat `#fff` made the whole panel solid white - the flat, disconnected
       white block in the reported screenshot. The final transparent stop
       restores the fade; the two fixed-px stops before it still do their job of
       staying opaque across the 40px photo overlap. */
    background: linear-gradient(to bottom, rgba(255, 255, 255, .92) 0, #fff 40px, rgba(255, 255, 255, 0) 100%);
}
/* Single-line truncation, matching the Figma component spec exactly
   (`whitespace-nowrap` + `text-ellipsis` on the title node) — not a 2-line
   clamp, which was wrapping long titles to a second line instead of cutting
   them off after the first. */
.evt-card-title {
    font-size: 24px;
    line-height: 32px;
    font-weight: 700;
    color: var(--hr-brown-900);
    margin: 0;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
.evt-card-desc {
    font-size: 16px;
    line-height: 24px;
    color: var(--hr-brown-300);
    margin: 0;
    overflow: hidden;
    text-overflow: ellipsis;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
}
.evt-card-foot { display: flex; align-items: center; gap: 24px; }
.evt-chip {
    display: inline-flex;
    align-items: center;
    padding: 8px 16px;
    border-radius: 6px;
    font-size: 14px;
    font-weight: 700;
    text-transform: uppercase;
    color: #e6f0ef;
    background: var(--hr-green-500);
    white-space: nowrap;
}
.evt-chip-green { background: var(--hr-green-400, #338a81); }
.evt-chip-amber { background: var(--hr-yellow-500); }
.evt-chip-purple { background: var(--hr-purple-500, #a56293); }
.evt-chip-blue { background: var(--hr-blue-400); }
/* Border was rgba(255,255,255,.1) - next to invisible against the card's
   own light cream background, and it had no inset glass highlight at all
   (same two issues as the featured card's "Discover More" button, BIL-605). */
.evt-card-arrow {
    flex-shrink: 0;
    margin-inline-start: auto;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 56px;
    height: 56px;
    border-radius: 61px;
    background: rgba(255, 255, 255, .2);
    border: 1.5px solid transparent;
    box-shadow: 0 3px 6px rgba(0, 0, 0, .03), inset 0 4px 6.1px rgba(255, 255, 255, .23);
    transition: background-color .2s ease, transform .2s ease;
}
/* Figma's "Ellipse 262" bloom is NOT declared here: .evt-card-arrow is on the
   shared glass-circle glow list in layout-revamp.css, the same recipe the home
   page's memories filmstrip arrows use. Don't re-add a local ::before for it -
   that pseudo-element is the shared glow, and clipping this button
   (overflow:hidden) to contain a blurred disc also eats the shared ::after rim,
   which sits 1.5px outside the border box. */
.evt-card:hover .evt-card-arrow { background: rgba(255, 255, 255, .5); }
[dir="rtl"] .evt-card-arrow img { transform: scaleX(-1); }

/* ---------- Pagination ---------- */
.evt-pagination { position: relative; z-index: 1; display: flex; align-items: center; gap: 8px; }
.evt-page-arrow,
.evt-page-number {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 56px;
    height: 56px;
    border-radius: 61px;
    background: rgba(255, 255, 255, .2);
    border: 1.5px solid transparent;
    box-shadow: 0 3px 6px rgba(0, 0, 0, .03);
    text-decoration: none;
    font-size: 16px;
    color: var(--hr-brown-500);
    transition: background-color .2s ease, color .2s ease, transform .2s ease;
}
[dir="rtl"] .evt-page-arrow img { transform: scaleX(-1); }
.evt-page-arrow:hover,
.evt-page-number:hover { text-decoration: none; color: var(--hr-brown-500); background: rgba(255, 255, 255, .4); }
.evt-page-arrow.is-disabled { opacity: .35; pointer-events: none; }
.evt-page-number.is-active,
.evt-page-number.is-active:hover {
    background: var(--hr-yellow-500);
    border-color: var(--hr-yellow-500);
    color: var(--hr-cream-50);
    font-weight: 700;
}
.evt-page-ellipsis { display: inline-flex; align-items: center; justify-content: center; width: 56px; height: 56px; color: var(--hr-brown-300); }

.evt-empty { padding: 60px 0; text-align: center; font-size: 18px; color: var(--hr-brown-300); }

/* ---------- Divider between the grid and "Past Annual Gatherings" ---------- */
/* Same divider the home page (.hr-diamond-border), About (.abt-diamond-divider)
   and Summit (.smt-diamond-divider) draw, from Figma node 40001286:68074:
   solid #f3d9b0 20px squares rotated 45deg, over a 2px hairline in the same
   colour, with a cluster inset by the page's 160px gutter at each end and the
   line running past them to the viewport edges. This instance had drifted -
   a 1px line at rgba(217,133,0,.3) (so, thinner and browner), diamonds with
   4px rounded corners, and a cream strip painted behind each cluster to hide
   the line - which is why it read as a different component from the same
   divider everywhere else. */
.evt-divider {
    position: relative;
    z-index: 1;
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 5px 160px;
}
.evt-divider::before {
    content: "";
    position: absolute;
    inset-inline: 0;
    top: 50%;
    height: 2px;
    transform: translateY(-50%);
    background: #f3d9b0;
}
/* gap = 20 * (sqrt(2) - 1) ≈ 8.284px separates the layout boxes by exactly
   the amount each rotated point overhangs its own box, so the five points
   meet edge-to-edge - closing the line off between them without needing a
   painted strip behind the cluster. Same formula as .hr-diamond-border-cluster. */
.evt-divider-diamonds { position: relative; z-index: 1; display: flex; align-items: center; gap: 8.284px; flex-shrink: 0; }
.evt-divider-diamond { width: 20px; height: 20px; transform: rotate(45deg); background: #f3d9b0; flex-shrink: 0; }

/* ---------- Past Annual Gatherings ---------- */
/* overflow:visible explicitly, same reason as .evt-featured-wrap above: this
   is a <section>, and app.css's sitewide `section { overflow: hidden }`
   would otherwise clip .evt-past-motif's intentional bleed past this box's
   own edge. */
.evt-past { position: relative; z-index: 1; overflow: visible; padding: 120px 160px; }
.evt-past-inner { position: relative; z-index: 1; max-width: 1600px; margin-inline: auto; }
.evt-past-head { display: flex; align-items: center; justify-content: space-between; gap: 16px; flex-wrap: wrap; margin-bottom: 40px; }
/* The teal sweep with its two diamonds — body-corner-motif.svg, the same asset
   the press release detail page draws as .prd-body-motif (Figma node
   40004073:55241), at its natural 300.078 x 175.676. There it hangs from the
   workspace's top-end corner; here it is anchored to this section's bottom-start
   corner, so it is rotated 180deg to match — the sweep sits along the bottom
   edge with the two diamond points reaching up into the section.

   Replaces .evt-past-decor (past-gatherings-decor.svg, the blue diamond and
   quarter-arch that used to sit in the bottom-END corner). That asset is now
   unreferenced. z-index:0 keeps it below .evt-past-inner's 1, so the cards
   always paint over it. */
.evt-past-motif {
    position: absolute;
    z-index: 0;
    bottom: 0;
    inset-inline-start: 0;
    width: 300px;
    height: 176px;
    background: url("../images/press-releases-revamp/body-corner-motif.svg") no-repeat center / 100% 100%;
    transform: rotate(180deg);
    pointer-events: none;
}
/* In RTL the motif moves to the other corner with inset-inline-start; mirroring
   it horizontally on top of the 180deg keeps the sweep opening toward the
   page's centre rather than pointing off the edge. Same convention as
   .prd-body-motif and .pr-hero-decor. */
[dir="rtl"] .evt-past-motif { transform: rotate(180deg) scaleX(-1); }
@media (max-width: 1199.98px) { .evt-past-motif { width: 240px; height: 141px; } }
@media (max-width: 767.98px) { .evt-past-motif { width: 84px; height: 49px; } }

/* 1200-1439 is the one band where even the trimmed row runs close: the 160px
   gutters leave 880px at 1200 against the row's ~915. nowrap lets the search box
   give up those few pixels rather than the whole row breaking onto a second
   line - below 1200 the gutters drop to 40px and the room comes back. */
@media (min-width: 1200px) and (max-width: 1439.98px) {
    .evt-filters { flex-wrap: nowrap; }
    /* ...and the compression has to land on the search box, not on the pills.
       Left shrinkable, .evt-tabs was squeezed under its content width and broke
       Upcoming/Past onto two lines inside itself - the same wasted band this
       rule exists to remove, just one level down. */
    .evt-tabs,
    .evt-select { flex-shrink: 0; }
}
@media (max-width: 1199.98px) {
    .evt-divider,
    .evt-past { padding-inline: 40px; }
}
@media (max-width: 991.98px) {
    /* 4.142px is the same s * (sqrt(2) - 1) formula at s = 10 - the base
       rule's 8.284px is sized for a 20px diamond and would leave daylight
       between these halved points. Matches .hr-diamond-border's own
       breakpoint. */
    .evt-divider-diamond { width: 10px; height: 10px; }
    .evt-divider-diamonds { gap: 4.142px; }
}
@media (max-width: 767.98px) {
    .evt-divider,
    .evt-past { padding-inline: 20px; }
}

/* ---------- Register popup (Bootstrap modal, restyled) ---------- */
.evt-modal .modal-dialog { max-width: 640px; }
.evt-modal .modal-content {
    position: relative;
    border: 1px solid rgba(255, 255, 255, .4);
    border-radius: 32px;
    overflow: hidden;
    padding: 48px;
    background: var(--hr-blue-500) linear-gradient(160deg, #33739f 0%, #005087 55%, #12736a 100%);
    box-shadow: 0 20px 60px rgba(0, 0, 0, .25);
}
.evt-modal .modal-header { border: 0; padding: 0 0 24px; display: flex; justify-content: flex-end; }
.evt-modal .btn-close { filter: invert(1) brightness(2); opacity: .8; margin: 0; }
.evt-modal .btn-close:hover { opacity: 1; }
.evt-modal .modal-body { padding: 0; }
.evt-modal-title { font-size: 32px; line-height: 40px; font-weight: 700; color: var(--hr-cream-500); margin: 0 0 8px; }
.evt-modal-context { display: flex; flex-direction: column; gap: 4px; margin-bottom: 32px; }
.evt-modal-context span { font-size: 16px; color: rgba(249, 247, 234, .8); }
.evt-modal-field-row { display: flex; gap: 16px; }
.evt-modal-field-row .evt-modal-field { flex: 1 1 0; }
.evt-modal-field { margin-bottom: 20px; }
.evt-modal-field label { display: block; font-size: 14px; color: rgba(249, 247, 234, .7); margin-bottom: 8px; }
.evt-modal-field input {
    width: 100%;
    background: rgba(255, 255, 255, .1);
    border: 1px solid rgba(255, 255, 255, .2);
    border-radius: 8px;
    padding: 14px 16px;
    font-size: 16px;
    color: var(--hr-cream-500);
}
.evt-modal-field input::placeholder { color: rgba(249, 247, 234, .5); }
.evt-modal-field input:focus { outline: none; border-color: var(--hr-yellow-500); }
.evt-modal-field .iti { width: 100%; }
.evt-modal-consent { display: flex; align-items: flex-start; gap: 10px; margin: 8px 0 28px; }
.evt-modal-consent input { margin-top: 4px; }
.evt-modal-consent label { font-size: 14px; color: rgba(249, 247, 234, .8); margin: 0; }
.evt-modal-error { font-size: 14px; color: #ffb4ae; margin: -12px 0 16px; display: none; }
.evt-modal-error.is-visible { display: block; }
.evt-modal .evt-btn-primary { width: 100%; justify-content: center; }
.evt-modal .evt-btn-primary:disabled { opacity: .6; cursor: not-allowed; }

@media (max-width: 1199.98px) {
    .evt-hero,
    .evt-intro,
    .evt-featured-wrap,
    .evt-listing { padding-inline: 40px; }
    .events-revamp { --evt-hero-h: 200px; }
    .evt-intro-inner h1 { font-size: 44px; line-height: 52px; }
    .evt-grid { grid-template-columns: repeat(2, 1fr); }

    /* Stacks here rather than at 991: side-by-side only works while the copy
       column still has room for the title at a readable size, and below 1200
       (card 880 and falling) it does not - that band is portrait tablets and
       small laptops, exactly where the squeeze was worst. */
    /* 120px of bottom padding here is desktop clearance for the watermark's
       bottom diamond accent. Once the card stacks the mark is capped by
       MAX_INFLATE (see positionEventWatermark) and hangs only ~116px below the
       card, so the desktop value left ~64px of dead cream between the mark and
       "All Events" on top of .evt-listing's own 60px top padding - the empty
       band in the report. 64px puts the accent back just above the heading,
       the way the design has it. */
    .evt-featured-wrap { padding-bottom: 64px; }
    .evt-featured { flex-direction: column; }
    /* flex-basis, not just height — the base rule's `flex: 0 0 46.5%` resolves
       against the main axis, which is now the BLOCK axis, so a bare height
       would fight a 46.5% flex-basis for the same dimension. Fluid band height
       so the photo shrinks with the viewport instead of holding 320px down to
       a phone. */
    .evt-featured-media {
        flex: 0 0 clamp(220px, 26vw, 360px);
        height: clamp(220px, 26vw, 360px);
        min-width: 0;
        max-width: none;
        order: -1;
    }
}

@media (max-width: 767.98px) {
    /* Phone artboard (Figma node 40004639:75277 "events"): 402 wide with a 362
       content column, so 20px gutters - not the 16 this used to carry. Every
       row on it (intro, featured card, filters, cards, pagination, Past Annual
       Gatherings) sits on that same 362, so the gutter is set once here and
       each section inherits it. */
    .evt-hero,
    .evt-intro,
    .evt-featured-wrap,
    .evt-listing { padding-inline: 20px; }
    .events-revamp {
        --evt-hero-h: 160px;
        /* Runs the wash INTO the first heading line, finishing on its middle.

           The heading's top edge sits at 220px on a phone (160px hero +
           .evt-intro's 60px top padding) and its line-height is 40, so the
           middle of "Where Arabic" is at 240 - which is what +80 resolves to.
           Measured, not estimated: at +60 the gradient ended at exactly 220,
           i.e. it stopped on the heading's top edge and never entered the word.

           This reverses an earlier decision, recorded so it is not flipped back
           without the reason: +60 was chosen deliberately to run "right down to
           the h1 and no further", on the view that +80 would "wash over the
           heading itself". Reaching the middle of that first line is the
           requested treatment, and it also puts the phone back on the same
           formula as desktop, so there is one wash rule rather than two. */
        --evt-wash-h: calc(var(--evt-hero-h) + 80px);
    }
    /* The artboard's own breadcrumb size on a phone, the same step
       .spk-breadcrumb takes at this breakpoint - at the desktop 20px, three
       crumbs wrap the hero onto two rows at 375px. */
    .evt-breadcrumb { font-size: 12px; gap: 8px; }
    .evt-breadcrumb-sep { height: 12px; }

    /* Vertical rhythm straight off the artboard: 60px from the hero to the h1,
       32px from the intro to the featured card, 60px from the card to "All
       Events", 32px between the filters, the grid and the pagination, then 60px
       on either side of the diamond divider and below "View All Memories".
       Desktop's 60-120px section padding was only ever trimmed on the inline
       axis for mobile, which left large empty bands stacked between the
       featured card, the divider and Past Annual Gatherings on a short
       viewport. The bg-wordmark watermark (whose clearance .evt-featured-wrap's
       120px bottom padding exists for) is decorative and cramped at this width
       anyway, so it is hidden rather than resized - positionEventWatermark() in
       index.blade.php already no-ops once its element isn't rendered
       (offsetParent check). */
    .evt-intro { padding-top: 60px; }
    .evt-featured-wrap { padding-top: 32px; padding-bottom: 0; }
    .evt-bg-watermark { display: none; }
    .evt-listing { padding-top: 60px; padding-bottom: 60px; }
    .evt-past { padding-top: 60px; padding-bottom: 60px; }
    /* The divider now takes its 60px from the two sections' own padding, so a
       grid that is the last thing in the results - the pagination isn't
       rendered at all when there's only one page - must not add its trailing
       margin on top of that. Scoped to .evt-listing so the past section's own
       grid keeps its margin above the button below it. */
    .evt-listing .evt-grid:last-child { margin-bottom: 0; }

    /* ---------- Intro ---------- */
    /* Centred on a phone, matching the other listing headers (.vid-featured-head,
       .tnc-title, .pp-title all centre at this breakpoint).

       Reversing an earlier decision, recorded here so it is not flipped back
       without the reason: this was deliberately set to `start` because centring
       the heading and its standfirst puts them on a different axis to everything
       under them - the featured card's copy, the filter row, the cards - so the
       column reads as two competing alignments. That trade-off still exists; it
       was re-decided in favour of a header treatment consistent across the
       listing pages. align-items with text-align because .evt-intro-inner is a
       flex column, the same pair .vid-featured-head uses. */
    .evt-intro-inner { gap: 24px; text-align: center; align-items: center; }
    .evt-intro-inner h1 { font-size: 32px; line-height: 40px; }
    /* The artboard breaks the heading between its two halves - "Where Arabic"
       on top, the accent "Comes Alive" below (node 40004763:12919 carries an
       explicit line break before it) - so the colour change and the line break
       land in the same place. Left to wrap on its own the line broke after
       "Comes" instead, splitting the amber half across both rows. A block-level
       accent does it without a <br> in the markup, so it holds for whatever
       each locale's two halves are. */
    .evt-intro-inner h1 .hr-accent { display: block; }
    .evt-intro-inner p { font-size: 16px; line-height: 24px; }

    /* ---------- Featured card ---------- */
    /* A tighter frame than desktop's: 4px of glass around a 30px corner and 26px
       on the photo inside it. The copy column is set from the leading edge; the
       phone artboard (node 40004763:12923) centres it, and this is a deliberate
       departure from that node, asked for so the card reads on the same axis as
       the intro above it and the listing below. The Featured/Flagship badge was
       already the one thing that stayed on the leading edge - it takes that from
       its own `align-self: flex-start` in the base rule, not from the text
       alignment, so it is unaffected either way. */
    .evt-featured { padding: 4px; border-radius: 30px; }
    /* Aspect-driven rather than a vw clamp: the artboard's photo is 354x282
       inside a 362 column - a fixed PROPORTION of the card, not a fixed height -
       and at this width the <=1199 clamp had bottomed out on its 220px floor. */
    .evt-featured-media {
        flex: 0 0 auto;
        height: auto;
        aspect-ratio: 354 / 282;
        border-radius: 26px;
    }
    .evt-featured-copy { padding: 24px; gap: 32px; text-align: start; }
    .evt-featured-badge { padding: 10px 12px; font-size: 10px; }
    .evt-featured-body { gap: 16px; }
    .evt-featured-body h2 { font-size: 24px; line-height: 32px; }
    /* Three lines here, not desktop's two: the artboard gives the description
       72px of a 306px-wide column. */
    .evt-featured-body p { font-size: 16px; line-height: 24px; -webkit-line-clamp: 3; }
    /* flex-start, not center, to follow the copy above: in a COLUMN flex
       container the cross axis runs horizontally and `flex-start` resolves per
       direction, so this is the left edge in English and the right one in
       Arabic - which is exactly what is wanted, and what a physical `left`
       would have got wrong. */
    .evt-featured-meta { flex-direction: column; align-items: flex-start; row-gap: 16px; }
    .evt-featured-stat,
    .evt-featured-stat:first-child { flex: 0 0 auto; align-items: flex-start; }
    .evt-featured-stat span { font-size: 12px; line-height: normal; }
    .evt-featured-stat strong { font-size: 16px; line-height: 24px; }
    /* Stacked, the separator turns 90deg with the row: a full-width hairline
       with the diamond centred ON it, between Date and Place, instead of the
       vertical rule that divides the two columns on desktop. The background
       flips with it - 1px tall across the full width rather than 1px wide down
       the full height. */
    .evt-featured-meta-sep {
        width: auto;
        height: 14px;
        align-self: stretch;
        background-image: linear-gradient(to right, transparent 0%, var(--hr-green-400) 49%, transparent 100%);
        background-size: 100% 1px;
    }
    .evt-featured-meta-sep::before { width: 10px; height: 10px; }
    /* Both CTAs stacked and full width, at the artboard's 48px button height -
       desktop's 16px block padding on a 24px line makes 56. */
    .evt-featured-actions { flex-direction: column; align-items: stretch; gap: 8px; }
    .evt-btn-primary,
    .evt-btn-ghost { padding: 12px 24px; justify-content: center; }

    /* ---------- Listing head and filters ---------- */
    .evt-listing-head { align-items: center; gap: 8px; margin-bottom: 16px; }
    .evt-listing-title { font-size: 24px; line-height: 32px; }
    .evt-listing-count { font-size: 12px; }
    /* Search on its own full-width row, then Upcoming/Past/Type/Year/Location as
       ONE horizontally-scrolling line, which is how the artboard runs them (node
       40004763:12964: five pills totalling 468px across a 362px column, so the
       row is meant to be scrolled, not wrapped or stacked). .evt-filter-row is
       the scroller; .evt-filter-fields collapses into it so the selects share
       that scrolling line with the tabs instead of forming a second flex row
       inside it. Replaces the one-control-per-row column this used to stack. */
    /* nowrap matters here: the base rule wraps, and in a WRAPPING column
       container a flex line takes its cross size from its widest item, so the
       scrolling row below sized itself to its own 491px of content instead of
       stretching to the 335px column. */
    .evt-filters { flex-direction: column; flex-wrap: nowrap; align-items: stretch; gap: 10px; margin-bottom: 32px; }
    .evt-search { order: -1; flex: none; max-width: none; padding: 12px 16px; }
    .evt-search input { font-size: 14px; }
    .evt-filter-row {
        display: flex;
        flex-wrap: nowrap;
        align-items: center;
        gap: 8px;
        overflow-x: auto;
        /* The row is meant to run past the edge, so the bar would only add noise
           on the platforms that draw a persistent one. */
        scrollbar-width: none;
        -ms-overflow-style: none;
        /* Room for the active pill's shadow inside the scroll box, cancelled
           again on the outside so the layout does not move.

           `overflow-x: auto` is why this is needed: once one axis is not
           `visible` the other computes to `auto` too, so this box clips
           vertically as well as horizontally - and --evt-pill-shadow reaches
           37px below the pill - its 2px/23px/14px layer is offsetY 23 plus 14 of
           blur - so the shadow was being sliced off flat along the row's bottom
           edge. The Videos page has no
           such cut because its tabs wrap instead of scrolling, so nothing clips
           them; the scrolling row is this artboard's own layout (five pills over
           a 362px column), so it is kept and given the clearance instead.

           40/8 is the clearance .vid-filters and .tlk-filters already use for the
           identical stack; the negative margins are equal and opposite, so the
           row occupies exactly the same space as before. */
        padding-block: 8px 40px;
        margin-block: -8px -40px;
    }
    .evt-filter-row::-webkit-scrollbar { display: none; }
    .evt-filter-fields { display: contents; }
    /* margin-inline-end back to 0: the desktop rule's `auto` would push the
       selects to the far end of the scroll content whenever the five pills
       happen to be narrower than the viewport. */
    .evt-tabs { flex: none; flex-direction: row; gap: 8px; margin-inline-end: 0; }
    .evt-tab { flex: none; width: auto; padding: 12px 16px; font-size: 14px; line-height: 20px; }
    /* A fixed width, tighter than the desktop rule's 180px. It cannot be `auto`:
       a bare <select> is sized by its widest OPTION (full note above), so one
       long venue name would blow a pill out to 400px in a row that no longer
       has a container width to hold it in check. 122px fits the longest of the
       three labels ("Location", 60px at this size) inside the artboard's own
       16/40 padding and keeps the three a matched set. */
    .evt-select {
        flex: none;
        width: 122px;
        padding: 12px 40px 12px 16px;
        font-size: 14px;
        line-height: 20px;
        background-position: right 16px center;
    }
    [dir="rtl"] .evt-select { padding: 12px 16px 12px 40px; background-position: left 16px center; }

    /* ---------- Cards ---------- */
    .evt-grid { grid-template-columns: 1fr; margin-bottom: 32px; }
    /* 20px between listing cards, against the 24px the past-gatherings row
       keeps from the base rule - the artboard pitches the two differently. */
    .evt-listing .evt-grid { gap: 20px; }
    /* The phone card (Figma node 40004763:12984) overlaps its copy panel onto the
       photo exactly as the desktop component does - only the numbers change.
       Its auto-layout reads as media(211) + gap(6) + panel(202), but that 6px is
       NOT a visible gap: the image container behind the media box is 396px tall,
       so it keeps painting underneath. Sampling the exported render bears that
       out - the photo runs unbroken into the panel's edge at every column, and
       goes 8px deeper still behind the panel's rounded top corners (photo pixels
       at x=20 down to y=224, against the panel starting at 217 mid-card). There
       is no cream anywhere between the two.
       So: a media box 20px taller than the visible photo, pulled back by the same
       20px, which puts the panel's top edge at 217 with the image running behind
       its corners - and leaves the card's own height at 8+237-20+202+8 = 435,
       the artboard's.
       The bottom corners are SQUARE here, unlike the desktop rule which matches
       its panel's radius. That rule matches a curve the panel sits BELOW; these
       20px sit BEHIND the panel's own top corners, and two 20px curves bowing
       opposite ways (the media's centred at y=217, the panel's at y=237) leave a
       crescent of bare cream between them - the hairline visible down each side
       of the seam. Square, the media fills every pixel behind that corner the
       way Figma's 396px-tall image container does. */
    .evt-card { border-radius: 30px; }
    .evt-card-media { height: 237px; border-radius: 22px 22px 0 0; }
    /* The white has to be FULLY opaque by the time it reaches the photo's bottom
       edge, or that edge ghosts through as a faint line across the panel. The
       base rule reaches #fff at 40px because that is desktop's overlap depth;
       here the overlap is 20px, where the base ramp is still ~4% short. Same
       trick, re-pointed at this breakpoint's own overlap. */
    .evt-card-body {
        margin-top: -20px;
        padding: 22px 16px 16px;
        border-radius: 20px;
        gap: 12px;
        background: linear-gradient(to bottom, rgba(255, 255, 255, .92) 0, #fff 20px, rgba(255, 255, 255, 0) 100%);
    }
    /* Date over Place, split by a hairline as wide as the longer of the two,
       instead of desktop's single row with a vertical tick between them.
       Releasing the far edge lets the block shrink-wrap so that hairline stops
       with the text rather than running the width of the card.
       bottom:31px is the artboard's 5px measured off the VISIBLE foot of the
       photo (5 + the 20px of media now hidden behind the copy panel, + the 6px
       the panel sits below the media box), not off this box's own edge.

       Logical insets, not left/right: this used to say `left: 14px; right: auto`,
       which pinned the block to the LEFT of the card in both languages, so the
       Arabic phone listing had its date and venue hanging off the wrong edge
       while the rest of the card mirrored. The base rule above sets both physical
       sides, and these two override whichever of them the writing direction maps
       them onto - 14px from the right and auto on the left under RTL. */
    .evt-card-caption {
        inset-inline-start: 14px;
        inset-inline-end: auto;
        bottom: 31px;
        max-width: calc(100% - 28px);
        flex-direction: column;
        align-items: flex-start;
        gap: 4px;
    }
    .evt-card-caption span { font-size: 14px; line-height: 20px; }
    /* rgba(255,255,255,.1), not the base rule's 50% cream: Figma's divider
       (Vector 2538 inside node 40004763:12984) is a plain white stroke at
       stroke-opacity .1 - five times fainter than what this was painting, which
       is why the break read as a hard bright rule across the photo rather than a
       hairline. No gradient on this one, unlike the featured card's separator:
       the stroke is a flat 10% end to end. */
    .evt-card-caption-sep { width: 100%; height: 1px; background: rgba(255, 255, 255, .1); }
    .evt-card-title { font-size: 20px; line-height: 28px; }
    .evt-card-desc { -webkit-line-clamp: 3; }
    .evt-card-foot { gap: 16px; }
    .evt-chip { font-size: 10px; }
    .evt-card-arrow { width: 40px; height: 40px; }
    .evt-card-arrow img { width: 17px; height: 17px; }

    /* ---------- Pagination ---------- */
    /* Centred, on 40px buttons - 270px of nav across the 362 column. */
    .evt-pagination { justify-content: center; gap: 6px; }
    .evt-page-arrow,
    .evt-page-number,
    .evt-page-ellipsis { width: 40px; height: 40px; font-size: 14px; }
    .evt-page-arrow img { width: 17px; height: 17px; }

    /* ---------- Past Annual Gatherings ---------- */
    /* Heading centred on its own line, and "View All Memories" moved to the
       foot of the section below the cards, full width (Figma node
       40004763:13006). display:contents dissolves the desktop heading/button
       row so .evt-past-inner can order the three blocks as one column. */
    .evt-past-inner { display: flex; flex-direction: column; }
    .evt-past-head { display: contents; }
    .evt-past-head .evt-listing-title { order: 1; margin-bottom: 32px; text-align: center; }
    .evt-past .evt-grid { order: 2; }
    .evt-past-head .evt-btn-ghost { order: 3; justify-content: center; }

    /* ---------- Register popup ---------- */
    .evt-modal .modal-content { padding: 32px 24px; }
    .evt-modal-field-row { flex-direction: column; gap: 0; }
}

/* Landscape phones and other short viewports (the "horizontal view" case).
   The stacked photo band above is sized off the viewport WIDTH, which on a
   landscape phone is generous while the height is not - at 844x390 a 220px
   band takes 56% of the screen before a word of copy appears. Sized against
   the viewport height here instead. Placed last so it wins over the <=1199
   band regardless of which of the two the device also matches. */
@media (orientation: landscape) and (max-height: 560px) {
    .evt-featured-media {
        flex-basis: clamp(150px, 40vh, 220px);
        height: clamp(150px, 40vh, 220px);
    }
    .evt-featured-copy { padding: 24px; gap: 24px; }
}
