/* ==========================================================================
   منصة التطوع — التسجيل على خطوات
   vo.alehsan.org.sa/register  ·  rewritten from zero 2026-09-03

   قرار فارس: «الستايل كله ارميه بالقمامة وخلنا نبدا من جديد» — وهذه هي الثالثة.
   فتوقّفت عن الاختراع.

   ── من أين جاء هذا الشكل ───────────────────────────────────────────────────
   **من نظام الموارد البشرية.** Faris asked for the top bar to be «موحد زي hr»,
   which says plainly which design language he has already approved — so this
   page is built in it rather than in a fourth one of my invention. The tokens
   below are `theme.css`'s, copied by value:

     --brand-700 #a44320   --brand-600 #cf6028   --brand-500 #f18927
     --brand-200 #ffd4af   --brand-100 #fff0e2   --line     #e8e0d7
     --ink-900   #242824   --ink-700   #505650   --ink-500  #7c837b
     --paper     #fffefa   --canvas    #f6f4ef

   وقواعده أيضًا: بطاقات بيضاء على أرضية دافئة، زوايا `1.35rem .7rem 1.35rem
   1.35rem`، ظلال ناعمة واسعة، وأزرار بتدرّج برتقالي. لا حبر ولا ورق، ولا أرقام
   مفرّغة، ولا حقول بلا إطار — كلها من التصميم الذي رُفض.

   ── ماذا تغيّر عن المحاولة السابقة، صراحةً ─────────────────────────────────
     · الحقول عادت **صناديق** واضحة بحدود وخلفية بيضاء وارتفاع مريح للإصبع
     · البطاقات عادت **مدوّرة** وعليها ظلّ، لا خطوط حادّة
     · الترتيب صار **خطوة واحدة على الشاشة**، لا نموذجًا طويلًا بعمودين
     · الخلفية صارت أرضية دافئة، لا شرائط حبر وورق متناوبة
     · البنر صار **صورًا للمتطوعين**، وهو أول ما يُرى

   ── البنر ──────────────────────────────────────────────────────────────────
   الصور تأتي من `public/assets/img/vo` كما هي، بلا قائمة يدوية — يضيف فارس صورة
   فتظهر. See `App\Support\VolunteerPhotos`. On a phone only the first is shown:
   five slivers on a 375px screen is not a photograph of anything.
   ========================================================================== */

.rg {
    --brand-700: #a44320;
    --brand-600: #cf6028;
    --brand-500: #f18927;
    --brand-200: #ffd4af;
    --brand-100: #fff0e2;
    --rg-line: #e8e0d7;
    --rg-ink: #242824;
    --rg-ink-700: #505650;
    --rg-ink-500: #7c837b;
    --rg-paper: #fffefa;
    --rg-canvas: #f6f4ef;
    --rg-danger: #a53636;
    --rg-danger-bg: #fdecec;
    /* From theme.css `--success` / `--success-bg`. The verification sequence needs a positive
       accent and the system already has exactly one; nothing new is invented here. */
    --rg-success: #27734e;
    --rg-success-bg: #e9f7ef;
    --rg-radius: 1.35rem .7rem 1.35rem 1.35rem;
    --rg-shadow: 0 14px 40px rgba(34, 31, 25, .07);

    background: var(--rg-canvas);
    color: var(--rg-ink);
    padding-block-end: clamp(3rem, 7vw, 5rem);
}

/* ── البنر: صور المتطوعين ─────────────────────────────────────────────────── */
.rg-banner {
    position: relative;
    display: flex;
    /* Tall enough to hold the heading *and* the card's overlap without the two touching —
       measured: the card rises 3.5rem into it and the heading needs ~5rem of clear air. */
    height: clamp(15rem, 30vw, 22rem);
    margin-block-start: 1rem;
    overflow: hidden;
    background: var(--rg-ink);
}

/* The first frame is wider than the rest: a row of identical slices reads as a texture,
   and one lead photograph with supporting frames reads as a photograph. */
.rg-banner__photo:first-child {
    flex-grow: 1.7;
}

.rg-banner__photo {
    flex: 1 1 0;
    min-width: 0;
    width: 100%;
    height: 100%;
    object-fit: cover;
    /* A hairline of the ground between frames, so a row of photographs reads as
       a row rather than as one wide picture with seams in it. */
    border-inline-start: 2px solid var(--rg-canvas);
}

.rg-banner__photo:first-child {
    border-inline-start: 0;
}

/*
    التعتيم. Warm rather than neutral black: the photographs are all daylight and
    orange lanyards, and a grey scrim over them turns the association's own
    pictures grey. Bottom-heavy so the caption has contrast and the faces do not
    sit under the darkest part of it.
*/
.rg-banner::after {
    content: "";
    position: absolute;
    inset: 0;
    /*
        Lighter than the first attempt, which took 86% at the foot and turned the two darkest
        photographs — an indoor iftar and a warehouse — into black rectangles. The heading gets
        its contrast from the band under it rather than from darkening the whole picture.
    */
    background:
        linear-gradient(180deg, rgba(36, 40, 36, .18) 0%, rgba(36, 40, 36, .10) 30%, rgba(26, 20, 16, .55) 72%, rgba(26, 20, 16, .82) 100%);
}

.rg-banner__caption {
    position: absolute;
    inset-inline: 0;
    bottom: 0;
    z-index: 1;
    /*
        Clears the card, which rises 3.5rem into the banner. Without this the heading is behind
        it and the sentence under the heading is invisible — which is what the first build did.
    */
    padding-block-end: clamp(4.75rem, 9vw, 6.5rem);
    color: #fff;
    /* The picture is behind the text, so the text gets its own shadow rather than relying on
       the scrim being dark enough for every photograph anybody ever adds to that folder. */
    text-shadow: 0 1px 12px rgba(20, 15, 12, .55);
}

.rg-banner__caption p {
    margin: 0;
    max-width: 40rem;
    /* Not dimmed. It sits over the brightest part of some photographs, and 82% white on a
       sunlit warehouse is a line nobody reads. */
    color: #fff;
    font-size: clamp(.92rem, 2.2vw, 1.05rem);
    line-height: 1.7;
}

.rg-banner__caption h1 {
    margin: 0 0 .4rem;
    font-weight: 400;
    font-size: clamp(1.65rem, 4.6vw, 2.8rem);
    line-height: 1.25;
}

.rg-wrap {
    width: 100%;
    max-width: 60rem;
    margin-inline: auto;
    padding-inline: clamp(1rem, 4vw, 2rem);
}

/* ── البطاقة ──────────────────────────────────────────────────────────────── */
/*
    ترتفع فوق حافة البنر. The overlap is what ties the two together — a card that
    began below the photographs would read as a second, unrelated page stacked
    under the first.
*/
.rg-card {
    position: relative;
    z-index: 2;
    margin-block-start: clamp(-3.5rem, -6vw, -2rem);
    border: 1px solid rgba(255, 255, 255, .9);
    border-radius: var(--rg-radius);
    background: var(--rg-paper);
    box-shadow: var(--rg-shadow);
    overflow: hidden;
}

.rg-card__body {
    padding: clamp(1.4rem, 4vw, 2.6rem);
}

/* ── شريط الخطوات ─────────────────────────────────────────────────────────── */
.rg-steps {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    margin: 0;
    padding: clamp(1.1rem, 3vw, 1.5rem) clamp(1rem, 3vw, 2rem);
    border-block-end: 1px solid var(--rg-line);
    background: linear-gradient(180deg, var(--brand-100) 0%, var(--rg-paper) 100%);
    list-style: none;
}

.rg-step {
    position: relative;
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    align-items: center;
    gap: .7rem;
    min-width: 0;
}

/*
    الخيط الواصل بين الخطوات.

    It is drawn from each step towards the *previous* one and stops at the
    circle, so the strip never ends in a line pointing at nothing. RTL-safe by
    construction: `inset-inline-end` is the previous step's side in both
    directions, which a `left`/`right` pair would not be.
*/
.rg-step::before {
    content: "";
    position: absolute;
    top: 1.25rem;
    inset-inline-end: 100%;
    width: clamp(.5rem, 4vw, 3rem);
    height: 2px;
    background: var(--rg-line);
}

.rg-step:first-child::before {
    display: none;
}

.rg-step--done::before {
    background: var(--brand-500);
}

.rg-step__mark {
    display: grid;
    place-items: center;
    width: 2.5rem;
    height: 2.5rem;
    border: 2px solid var(--rg-line);
    border-radius: 50%;
    background: var(--rg-paper);
    color: var(--rg-ink-500);
    font-size: 1rem;
    /* «١» و«٢» و«٣» بالأرقام العربية هنا مقروءة لأنها كبيرة وفي دائرة — بخلاف
       «٠١» المفرّغة التي قيست في vo-site.css ولم تُقرأ. */
    line-height: 1;
}

.rg-step--current .rg-step__mark {
    border-color: var(--brand-600);
    background: linear-gradient(135deg, var(--brand-700), var(--brand-500));
    color: #fff;
    box-shadow: 0 6px 16px rgba(198, 90, 40, .28);
}

.rg-step--done .rg-step__mark {
    border-color: var(--brand-500);
    background: var(--brand-100);
    color: var(--brand-700);
}

.rg-step__label {
    min-width: 0;
    font-size: .95rem;
    color: var(--rg-ink-500);
}

.rg-step__label b {
    display: block;
    font-weight: 400;
    color: var(--rg-ink-700);
}

.rg-step--current .rg-step__label b {
    color: var(--brand-700);
}

.rg-step__label span {
    display: block;
    font-size: .8rem;
}

/* ── عنوان الخطوة ─────────────────────────────────────────────────────────── */
.rg-head {
    margin-block-end: clamp(1.4rem, 3vw, 2rem);
}

.rg-head h2 {
    margin: 0 0 .45rem;
    font-weight: 400;
    font-size: clamp(1.35rem, 3.4vw, 1.8rem);
    line-height: 1.3;
}

.rg-head p {
    margin: 0;
    max-width: 42rem;
    color: var(--rg-ink-700);
    font-size: .98rem;
    line-height: 1.75;
}

/* ── الحقول ───────────────────────────────────────────────────────────────── */
.rg-fields {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 1.15rem 1.2rem;
}

.rg-field {
    display: grid;
    gap: .45rem;
    min-width: 0;
}

.rg-field--wide {
    grid-column: 1 / -1;
}

.rg-field > label,
.rg-field > span {
    font-size: .93rem;
    color: var(--rg-ink-700);
}

.rg-field b {
    color: var(--brand-600);
    font-weight: 400;
}

/*
    صناديق إدخال عادية ومريحة — وهذا هو التصحيح الأساسي في هذه النسخة.

    3.15rem is the same target height as HR's buttons, and it is above the 44px
    a thumb needs. The radius, the border and the paper fill are theme.css's.
*/
.rg-field input,
.rg-field select {
    width: 100%;
    min-height: 3.15rem;
    padding: .7rem .9rem;
    border: 1px solid var(--rg-line);
    border-radius: .7rem;
    background: #fff;
    color: var(--rg-ink);
    font: inherit;
    font-size: 1rem;
    transition: border-color .15s ease, box-shadow .15s ease;
}

.rg-field input::placeholder {
    color: #a9a29a;
}

.rg-field input:focus,
.rg-field select:focus {
    outline: 0;
    border-color: var(--brand-500);
    /* A ring rather than an outline, so the rounded corner is followed. */
    box-shadow: 0 0 0 3px rgba(241, 137, 39, .22);
}

.rg-field small {
    color: var(--rg-ink-500);
    font-size: .82rem;
}

.rg-field--error input,
.rg-field--error select {
    border-color: var(--rg-danger);
}

.rg-error {
    color: var(--rg-danger);
    font-size: .86rem;
}

/* Under the code boxes, which are centred and not in a field grid. */
.rg-error--centred {
    margin: 0;
    text-align: center;
}

/* ── الاختيارات: المهارات والأوقات ────────────────────────────────────────── */
.rg-checks {
    display: flex;
    flex-wrap: wrap;
    gap: .6rem;
}

.rg-check {
    display: inline-flex;
    align-items: center;
    gap: .55rem;
    min-height: 2.9rem;
    padding: .55rem 1rem;
    border: 1px solid var(--rg-line);
    border-radius: 999px;
    background: #fff;
    color: var(--rg-ink-700);
    cursor: pointer;
    font-size: .95rem;
    transition: border-color .15s ease, background-color .15s ease, color .15s ease;
}

.rg-check input {
    width: 1.05rem;
    height: 1.05rem;
    margin: 0;
    flex: 0 0 auto;
    accent-color: var(--brand-600);
}

/* `:has()` as progressive enhancement over `accent-color`: the tick is brand
   coloured everywhere, and the whole pill fills where it is supported. */
.rg-check:has(:checked) {
    border-color: var(--brand-200);
    background: var(--brand-100);
    color: var(--brand-700);
}

.rg-check:focus-within {
    outline: 2px solid var(--brand-600);
    outline-offset: 2px;
}

/* ── الموافقة على إظهار الاسم ─────────────────────────────────────────────── */
.rg-consent {
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    gap: .9rem;
    margin-block-start: 1.6rem;
    padding: 1.2rem 1.3rem;
    border: 1px solid var(--rg-line);
    border-radius: 1rem .5rem 1rem 1rem;
    background: var(--rg-canvas);
    cursor: pointer;
}

.rg-consent input {
    width: 1.25rem;
    height: 1.25rem;
    margin: .2rem 0 0;
    accent-color: var(--brand-600);
}

.rg-consent strong {
    display: block;
    font-weight: 400;
    font-size: 1rem;
}

.rg-consent p {
    margin: .4rem 0 0;
    color: var(--rg-ink-700);
    font-size: .9rem;
    line-height: 1.7;
}

.rg-consent:has(:checked) {
    border-color: var(--brand-200);
    background: var(--brand-100);
}

.rg-consent:focus-within {
    outline: 2px solid var(--brand-600);
    outline-offset: 2px;
}

/* ══════════════════════════════════════════════════════════════════════════
   رمز التحقق — الخانات، والختم، والحكم

   الحركة من النموذج المرجعي (otp-seal.html) — **وهي وحدها** ما أُخذ منه.
   كل لون ونصف قطر وخط وظلّ هنا من هذه الصفحة نفسها ومن theme.css، بلا استثناء:

     سطح البطاقة   .rg-card   →   --rg-paper + --rg-radius + --rg-shadow
     سطح الخانة    الحقل      →   #fff، وهو نفسه ما تلبسه .rg-field input
     الحدّ الشعري   --rg-line
     لون الدخول    --brand-500 / --brand-600  (نفس لون حلقة التركيز في الصفحة)
     لون القبول    --rg-success       (من theme.css)
     لون الرفض     --rg-danger        (من theme.css)
     نصف قطر الخانة  .7rem            (نفس نصف قطر حقول الإدخال)
     الأرقام       خط الصفحة + tabular-nums (لا خط أحادي في هذا النظام)

   المقاسات مؤلَّفة هنا لا منقولة: النموذج المرجعي 56×64px ثابتة، وهذه تتقلّص مع
   الشاشة حتى 320px بتقليل العرض والفراغ — لا بتصغير نصف القطر.
   ══════════════════════════════════════════════════════════════════════════ */

.otp {
    --otp-tile-w: clamp(3.1rem, 14vw, 3.9rem);
    --otp-tile-h: clamp(3.6rem, 16vw, 4.5rem);
    --otp-gap: clamp(.45rem, 2.2vw, .8rem);
    --otp-radius: .7rem;
}

/*
    المسرح: ارتفاعه ثابت.

    Four tiles in a row become four tiles in a square, and the card must not jump between the
    two — so the stage is as tall as the square needs and the row simply sits in the middle of
    it. `overflow: visible` because the fan rotates the tiles outside their own box.
*/
.otp-stage {
    position: relative;
    height: calc(var(--otp-tile-h) * 2 + var(--otp-gap) + 2.5rem);
    margin-block: 1.6rem .4rem;
    overflow: visible;
    /* الأرقام تُقرأ من اليسار حتى داخل صفحة عربية، فالخانة الأولى هي اليسرى. */
    direction: ltr;
}

/* ── الختم ────────────────────────────────────────────────────────────────── */
.otp-seal {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    overflow: visible;
    pointer-events: none;
}

.otp-seal rect {
    fill: none;
    stroke-width: 1.5;
    stroke-linecap: round;
}

.otp-seal__track {
    stroke: var(--rg-line);
}

/*
    لون الدخول، لا لون الحكم.

    The seal is drawn while the server is still deciding, so it must not pre-announce the answer:
    it is the brand accent until there is a verdict, and only then does it become success or
    failure. A seal that went green before the response arrived would be a lie on a slow network.
*/
.otp-seal__draw {
    stroke: var(--brand-500);
    opacity: 0;
}

.otp.is-ok .otp-seal__draw {
    stroke: var(--rg-success);
}

.otp.is-bad .otp-seal__draw {
    stroke: var(--rg-danger);
}

/* ── الصفّ، والأشباح التي يقاس إليها ──────────────────────────────────────── */
.otp-rack,
.otp-ghosts {
    position: absolute;
    left: 50%;
    top: 50%;
    transform: translate(-50%, -50%);
}

.otp-rack {
    display: flex;
    gap: var(--otp-gap);
}

/*
    الأشباح: شبكة ٢×٢ فارغة، لا تُرى، ووظيفتها أن تُقاس.

    The square arrangement is laid out by CSS and read back with getBoundingClientRect, so the
    travel distance is measured at the size the browser actually rendered. Hard-coded pixel
    offsets would be wrong at the next breakpoint, and wrong again once the webfont lands and
    the tiles reflow.
*/
.otp-ghosts {
    display: grid;
    grid-template-columns: repeat(2, var(--otp-tile-w));
    gap: var(--otp-gap);
    opacity: 0;
    pointer-events: none;
}

.otp-ghosts i {
    display: block;
    width: var(--otp-tile-w);
    height: var(--otp-tile-h);
}

/* ── الخانة ───────────────────────────────────────────────────────────────── */
.otp-slot {
    position: relative;
    width: var(--otp-tile-w);
    height: var(--otp-tile-h);
    border: 1px solid var(--rg-line);
    border-radius: var(--otp-radius);
    /* معتمة لا شفّافة: الختم يمرّ تحتها، فيجب أن تحجبه. */
    background: #fff;
    /* محور الدوران أسفل البطاقة بكثير: دورة واحدة تعطي الانتشار والقوس معًا. */
    transform-origin: 50% 340%;
    transition: border-color .28s ease, box-shadow .28s ease;
}

.otp-slot input {
    width: 100%;
    height: 100%;
    padding: 0;
    border: 0;
    outline: 0;
    border-radius: var(--otp-radius);
    background: transparent;
    color: var(--rg-ink);
    font: inherit;
    font-size: clamp(1.5rem, 5.5vw, 1.9rem);
    text-align: center;
    /* أرقام بعرض واحد: «١» و«٨» لا يغيّران عرض الصفّ. */
    font-variant-numeric: tabular-nums;
    caret-color: var(--brand-600);
    -webkit-appearance: none;
    appearance: none;
}

/* نفس حلقة التركيز التي تلبسها كل حقول هذه الصفحة. */
.otp-slot:has(input:focus-visible),
.otp-slot:has(input:focus) {
    border-color: var(--brand-500);
    box-shadow: 0 0 0 3px rgba(241, 137, 39, .22);
}

.otp-slot[data-filled] {
    border-color: var(--brand-200);
}

.otp.is-ok .otp-slot[data-filled] {
    border-color: var(--rg-success);
}

.otp.is-bad .otp-slot[data-filled] {
    border-color: var(--rg-danger);
}

/* ضوء يلفّ حافة الخانة عند كل ضغطة — يجعل الإدخال ميكانيكيًّا لا صامتًا. */
/*
    `width`/`height` صريحان — و`inset: 0` وحده لا يكفي.

    An `<svg>` is a *replaced* element, and an absolutely positioned replaced element with `auto`
    width resolves to its **intrinsic** size, not to its containing block — which for an SVG with
    no `width` attribute and no `viewBox` is the CSS default 300×150. So four of these sat 300px
    wide inside 50px tiles and pushed 11px of horizontal overflow onto the document at 320px:
    exactly the class of bug the honeypot's `left: -9999px` once caused, from a different cause.
    Measured at 320px, which is the width the brief asks this component to survive.
*/
.otp-lap {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    overflow: visible;
    pointer-events: none;
}

.otp-lap rect {
    fill: none;
    stroke: var(--brand-500);
    stroke-width: 1.5;
    opacity: 0;
}

/* ── الحكم: الختم الواحد، والهالة، والشرر ─────────────────────────────────── */
.otp-medal {
    position: absolute;
    left: 50%;
    top: 50%;
    display: grid;
    place-items: center;
    width: calc(var(--otp-tile-w) * 1.15);
    height: calc(var(--otp-tile-w) * 1.15);
    margin: calc(var(--otp-tile-w) * -.575) 0 0 calc(var(--otp-tile-w) * -.575);
    border: 1px solid var(--rg-success);
    border-radius: calc(var(--otp-radius) * 1.5);
    background: var(--rg-success-bg);
    opacity: 0;
    transform: scale(.5);
}

.otp-medal svg {
    width: 45%;
    height: 45%;
}

.otp-medal path {
    fill: none;
    stroke: var(--rg-success);
    stroke-width: 2.2;
    stroke-linecap: round;
    stroke-linejoin: round;
}

.otp-halo {
    position: absolute;
    left: 50%;
    top: 50%;
    width: calc(var(--otp-tile-w) * 2.1);
    height: calc(var(--otp-tile-w) * 2.1);
    margin: calc(var(--otp-tile-w) * -1.05) 0 0 calc(var(--otp-tile-w) * -1.05);
    opacity: 0;
}

.otp-halo circle {
    fill: none;
    stroke: var(--rg-success);
    stroke-width: 1;
    stroke-dasharray: 3 9;
    opacity: .45;
}

.otp-spark {
    position: absolute;
    left: 50%;
    top: 50%;
    width: 1.5px;
    height: 9px;
    margin: -4px 0 0 -1px;
    border-radius: 2px;
    background: linear-gradient(var(--rg-success), transparent);
    opacity: 0;
    pointer-events: none;
}

/* ── الهزّة عند الرفض ─────────────────────────────────────────────────────── */
/*
    Three beats and done. A long shake reads as punishment, and the copy is already carrying the
    instruction — this only has to say «that did not go through» before the row comes back.
*/
.otp-shake {
    animation: otp-knock .42s cubic-bezier(.36, .07, .19, .97);
}

@keyframes otp-knock {
    10%, 90% { transform: translateX(-2px); }
    30%, 70% { transform: translateX(4px); }
    50% { transform: translateX(-6px); }
}

/* ── نصّ الحالة، والذيل ───────────────────────────────────────────────────── */
.otp-note {
    margin: 0;
    min-height: 1.6em;
    text-align: center;
    color: var(--rg-ink-500);
    font-size: .93rem;
}

.otp-note b {
    color: var(--rg-ink-700);
    font-weight: 400;
    /* رقم داخل جملة عربية يُقرأ من اليسار. */
    display: inline-block;
    direction: ltr;
    unicode-bidi: isolate;
}

.otp-foot {
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    align-items: center;
    gap: .4rem .9rem;
    margin-block-start: 1.3rem;
    min-height: 3.15rem;
}

.otp-resend {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: center;
    gap: .35rem .8rem;
}

/* شارة «موثّق» بعد القبول — تحمل الحكم بلا اعتماد على اللون وحده. */
.otp-guard {
    display: inline-flex;
    align-items: center;
    gap: .5rem;
    color: var(--rg-success);
    font-size: .93rem;
}

.otp-guard svg {
    width: .95rem;
    height: .95rem;
    fill: none;
    stroke: currentColor;
    stroke-width: 1.6;
}

/* حالة انتظار الشبكة: نبضة خفيفة، ولا نتيجة مُختلَقة. */
.otp-pending .otp-note {
    color: var(--rg-ink-700);
}

@media (prefers-reduced-motion: reduce) {
    .otp-shake {
        animation: none;
    }
}
/* ── الأزرار ──────────────────────────────────────────────────────────────── */
.rg-actions {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: .8rem 1rem;
    margin-block-start: clamp(1.6rem, 4vw, 2.4rem);
    padding-block-start: clamp(1.4rem, 3vw, 1.8rem);
    border-block-start: 1px solid var(--rg-line);
}

.rg-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: .5rem;
    min-height: 3.15rem;
    padding: .75rem 1.6rem;
    border: 1px solid var(--brand-600);
    border-radius: .9rem .45rem .9rem .9rem;
    background: linear-gradient(135deg, var(--brand-700), var(--brand-500));
    color: #fff;
    box-shadow: 0 10px 24px rgba(198, 90, 40, .22);
    cursor: pointer;
    font: inherit;
    font-size: 1rem;
    font-weight: 700;
    text-decoration: none;
    transition: transform .15s ease, box-shadow .15s ease;
}

.rg-btn:hover {
    color: #fff;
    box-shadow: 0 13px 30px rgba(198, 90, 40, .3);
    transform: translateY(-1px);
}

.rg-btn:focus-visible {
    outline: 2px solid var(--rg-ink);
    outline-offset: 3px;
}

.rg-btn[disabled],
.rg-btn[aria-disabled="true"] {
    cursor: wait;
    opacity: .6;
    transform: none;
}

.rg-btn--ghost {
    border-color: var(--rg-line);
    background: var(--rg-paper);
    color: var(--rg-ink-700);
    box-shadow: none;
    font-weight: 400;
}

.rg-btn--ghost:hover {
    border-color: var(--brand-200);
    background: var(--brand-100);
    color: var(--brand-700);
    box-shadow: none;
}

.rg-btn--wide {
    width: 100%;
}

/* A plain link that is still a form submit — «إعادة الإرسال», «غيّر الرقم». */
.rg-link {
    padding: .35rem .2rem;
    border: 0;
    background: none;
    color: var(--brand-700);
    cursor: pointer;
    font: inherit;
    font-size: .93rem;
    text-decoration: underline;
    text-underline-offset: .25em;
}

.rg-link:hover {
    color: var(--brand-600);
}

.rg-link[disabled] {
    color: var(--rg-ink-500);
    cursor: default;
    text-decoration: none;
}

.rg-actions__note {
    margin: 0;
    max-width: 24rem;
    color: var(--rg-ink-500);
    font-size: .86rem;
    line-height: 1.6;
}

/* ── الرسائل ──────────────────────────────────────────────────────────────── */
.rg-alert {
    margin-block-end: 1.5rem;
    padding: .95rem 1.15rem;
    border: 1px solid var(--rg-danger);
    border-radius: .8rem .4rem .8rem .8rem;
    background: var(--rg-danger-bg);
    color: #6e1616;
}

.rg-alert strong {
    font-weight: 400;
}

.rg-alert ul {
    margin: .45rem 0 0;
    padding-inline-start: 1.2rem;
    font-size: .94rem;
    line-height: 1.8;
}

.rg-note {
    margin-block-end: 1.5rem;
    padding: .95rem 1.15rem;
    border: 1px solid var(--brand-200);
    border-radius: .8rem .4rem .8rem .8rem;
    background: var(--brand-100);
    color: var(--brand-700);
    font-size: .95rem;
    line-height: 1.7;
}

.rg-note b {
    font-weight: 400;
    color: var(--rg-ink);
}

/* البطاقة المثبّتة: الفرصة التي جاء منها. */
.rg-pinned {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: .35rem .7rem;
    margin-block-end: 1.5rem;
    padding: .85rem 1.15rem;
    border: 1px solid var(--rg-line);
    border-radius: .8rem .4rem .8rem .8rem;
    background: var(--rg-canvas);
    font-size: .93rem;
}

.rg-pinned span {
    color: var(--rg-ink-500);
}

.rg-pinned strong {
    color: var(--rg-ink);
    font-weight: 400;
}

/*
    شارة وضع التطوير: الرمز على الشاشة لأن لا شيء يرسله هنا.

    Deliberately ugly. It only ever renders when `APP_DEBUG` is on and WhatsApp
    is unconfigured — see `PhoneVerification::deliver()` — and it should look
    like something that must never be seen in production.
*/
.rg-devcode {
    margin-block-end: 1.5rem;
    padding: .8rem 1.1rem;
    border: 2px dashed #8a5a12;
    border-radius: .5rem;
    background: #fff5d9;
    color: #8a5a12;
    text-align: center;
    font-size: .95rem;
}

.rg-devcode b {
    font-size: 1.4rem;
    letter-spacing: .3em;
    direction: ltr;
    display: inline-block;
    unicode-bidi: isolate;
}

/* ── المقاسات ─────────────────────────────────────────────────────────────── */
@media (max-width: 760px) {
    .rg-fields {
        grid-template-columns: 1fr;
    }

    /*
        الشريط يصير أرقامًا فقط. Three labels beside three circles do not fit on
        a 375px screen without wrapping into six lines; the heading under the
        strip already names the step in full.
    */
    .rg-step__label {
        display: none;
    }

    .rg-step {
        justify-content: center;
        grid-template-columns: auto;
    }

    .rg-step::before {
        width: 100%;
        inset-inline-end: 50%;
    }

    .rg-actions .rg-btn {
        width: 100%;
    }

    .rg-actions__note {
        max-width: none;
    }
}

@media (max-width: 640px) {
    /*
        صورة واحدة على الجوال. Five frames across 375px is five 70px slivers,
        and a photograph nobody can make out is decoration pretending to be
        content.
    */
    .rg-banner__photo:not(:first-child) {
        display: none;
    }

    .rg-card {
        margin-block-start: -1.5rem;
    }
}

@media (prefers-reduced-motion: reduce) {
    .rg-btn {
        transition: none;
    }

    .rg-btn:hover {
        transform: none;
    }
}
