/* =============================================================================
   Price ladder — rung selector, sticky mobile buy bar, upgrade card.

   Kept in its own sheet rather than appended to the 2,000-line style.css so the
   whole feature can be pulled by removing one <link>. Every rule is namespaced
   under .ek-tier* / .ek-upgrade* and nothing here restyles an existing class,
   so a product with no ladder renders exactly as it did before.

   Colours follow the storefront, not a new palette: #6e4ff5 (brand purple),
   #40c185 (buy green), #00a7d5 (accent).
   ========================================================================== */

.ek-tiers {
    display: block;
    margin: 0 0 20px;
    text-align: right;
}

.ek-tiers__title {
    display: block;
    font-size: 13.5px;
    font-weight: bold;
    color: #2b3245;
    margin-bottom: 6px;
}

.ek-tiers__note {
    display: block;
    font-size: 11px;
    color: #8b95a8;
    line-height: 1.7;
    margin-top: 8px;
}

/* --- one rung ------------------------------------------------------------ */

/* Sized so that both rungs' headlines clear the fold on a 667px phone with a
   63px buy bar over it. Everything a card is made of — its padding, the radio,
   the leading of every line in it — was set for a card seen on its own; two of
   them stacked, the second one starts 593px down and the buyer never learns
   there is a choice. */
.ek-tier {
    display: flex;
    align-items: flex-start;
    gap: 9px;
    width: 100%;
    margin: 0 0 8px;
    padding: 10px 12px;
    border: 1px solid #dfe4ec;
    border-radius: 10px;
    background: #fff;
    cursor: pointer;
    transition: border-color .15s ease, box-shadow .15s ease, background .15s ease;
}

.ek-tier:hover {
    border-color: #b9aef9;
}

.ek-tier.is-selected {
    border-color: #6e4ff5;
    border-width: 2px;
    padding: 9px 11px; /* keep the box the same size as the 1px state */
    background: #fbfaff;
    box-shadow: 0 4px 14px rgba(110, 79, 245, .12);
}

/* The native radio is replaced by .ek-tier__mark but stays in the DOM so the
   control remains keyboard-reachable and form-submittable. */
.ek-tier input[type="radio"] {
    position: absolute;
    opacity: 0;
    width: 0;
    height: 0;
}

.ek-tier__mark {
    flex: none;
    width: 16px;
    height: 16px;
    margin-top: 3px;
    border: 2px solid #c8cfdb;
    border-radius: 50%;
    background: #fff;
    position: relative;
}

.ek-tier.is-selected .ek-tier__mark {
    border-color: #6e4ff5;
}

.ek-tier.is-selected .ek-tier__mark::after {
    content: "";
    position: absolute;
    top: 2px;
    right: 2px;
    width: 8px;
    height: 8px;
    border-radius: 50%;
    background: #6e4ff5;
}

.ek-tier input[type="radio"]:focus-visible + .ek-tier__mark {
    outline: 2px solid #6e4ff5;
    outline-offset: 2px;
}

.ek-tier__body {
    flex: 1;
    min-width: 0;
}

/* Name on one side, price on the other. A grid rather than a baseline-aligned
   flex row: a name that wraps to two lines keeps the price pinned to its first
   line, and the price column sizes to its widest line (amount, or the
   difference under it) instead of squeezing the name word by word. */
.ek-tier__head {
    display: grid;
    grid-template-columns: minmax(0, 1fr) auto;
    align-items: start;
    column-gap: 10px;
}

.ek-tier__name {
    font-size: 13.5px;
    font-weight: bold;
    color: #222a3d;
    line-height: 1.6;
    overflow-wrap: anywhere;
    text-wrap: balance;
}

/* «پیشنهاد ما» — a small amber label on the card's top border.
   In the flow it took a row of its own whenever the rung name wrapped; on the
   border it costs nothing and still marks the rung at a glance. Amber because
   on this site green means "done", not "the better one". */
.ek-tier {
    position: relative;
}

.ek-tier.has-badge {
    margin-top: 14px;
}

.ek-tier__badge {
    position: absolute;
    top: -10px;
    right: 12px;
    display: inline-flex;
    align-items: center;
    gap: 3px;
    white-space: nowrap;
    font-size: 10px;
    font-weight: bold;
    color: #8a5a06;
    background: #fdf2d6;
    border: 1px solid rgba(190, 141, 40, .35);
    border-radius: 5px;
    padding: 0 7px;
    line-height: 18px;
}

.ek-tier.is-selected .ek-tier__badge {
    top: -11px; /* the 2px border moves the edge out by 1px */
    right: 11px;
}

.ek-tier__badge::before {
    content: "\2605";
    font-size: 8.5px;
    line-height: 1;
    color: #d99a1f;
}

.ek-tier__tagline {
    display: block;
    margin-top: 2px;
    font-size: 11.5px;
    color: #6d788c;
    line-height: 1.7;
}

.ek-tier__includes {
    list-style: none;
    margin: 6px 0 0;
    padding: 0;
}

.ek-tier__includes li {
    position: relative;
    padding-right: 16px;
    font-size: 11.5px;
    color: #4a5568;
    line-height: 1.7;
}

.ek-tier__includes li::before {
    content: "";
    position: absolute;
    top: .72em;
    right: 3px;
    width: 6px;
    height: 6px;
    border-radius: 2px;
    background: #40c185;
}

/* Price column: the amount, and under it what this rung costs over the
   cheapest one. Aligned to the card's outer edge so both lines share it. */
.ek-tier__price {
    display: flex;
    flex-direction: column;
    align-items: flex-end;
    white-space: nowrap;
}

.ek-tier__price-line {
    display: flex;
    align-items: baseline;
    gap: 4px;
    line-height: 1.6;
}

.ek-tier__amount {
    font-size: 15.5px;
    font-weight: bold;
    color: #6e4ff5;
    line-height: 1.4;
}

.ek-tier__amount.is-free {
    color: #40c185;
}

.ek-tier__currency {
    font-size: 11px;
    color: #8b95a8;
}

.ek-tier__was {
    font-size: 12px;
    color: #a9b2c1;
}

.ek-tier__delta {
    font-size: 10.5px;
    color: #8b95a8;
    line-height: 1.6;
}

/* A column too narrow for name and price side by side (a zoomed page, a large
   system font, a 320px phone): the price moves under the name instead of
   crushing it into one word per line. */
.ek-tiers {
    container-type: inline-size;
}

@container (max-width: 250px) {
    .ek-tier__head {
        grid-template-columns: minmax(0, 1fr);
        row-gap: 2px;
    }

    .ek-tier__price {
        flex-direction: row;
        align-items: baseline;
        flex-wrap: wrap;
        gap: 0 8px;
    }
}

/* --- sticky mobile buy bar ----------------------------------------------- */

.ek-buybar {
    display: none;
}

@media (max-width: 767px) {
    .ek-buybar {
        display: flex;
        align-items: center;
        gap: 10px;
        position: fixed;
        right: 0;
        left: 0;
        bottom: 0;
        z-index: 60;
        padding: 9px 13px calc(9px + env(safe-area-inset-bottom, 0px));
        background: #fff;
        border-top: 1px solid #e2e7ef;
        box-shadow: 0 -6px 20px rgba(15, 20, 35, .09);
    }

    .ek-buybar__price {
        flex: 1;
        min-width: 0;
        line-height: 1.4;
    }

    .ek-buybar__amount {
        display: block;
        font-size: 17px;
        font-weight: bold;
        color: #222a3d;
    }

    .ek-buybar__label {
        display: block;
        font-size: 11px;
        color: #8b95a8;
        overflow: hidden;
        text-overflow: ellipsis;
        white-space: nowrap;
    }

    .ek-buybar__btn {
        flex: none;
        display: inline-block;
        padding: 12px 20px;
        border-radius: 8px;
        background: #40c185;
        color: #fff;
        font-size: 13.5px;
        font-weight: bold;
        text-align: center;
        text-decoration: none;
    }

    .ek-buybar__btn:hover,
    .ek-buybar__btn:focus {
        color: #fff;
        opacity: .9;
        text-decoration: none;
    }

    /* The bar overlays the end of the page; give the footer room to clear it. */
    body.has-buybar {
        padding-bottom: 74px;
    }

    /* Two fixed things on the bottom edge of a phone is one too many, and the
       bar is the one the page exists for. The support FAB (style.css:2571) is
       pinned bottom-left with no z-index of its own, so the bar was already
       covering it — this only stops it peeking out from underneath. It is
       untouched on every other page and on desktop, and the page still says
       «پشتیبانی تمام وقت» and carries the channel link in the footer. */
    body.has-buybar a.support_telegram_static {
        display: none;
    }

    /* The nav drawer is z-index 1 (responsive.css:75) and this bar is 60, so an
       open menu had the bar cutting a bright stripe across its own dark
       overlay. */
    body.menu-is-open .ek-buybar {
        display: none;
    }

    /* The admin tools bar is fixed to the same edge (style.css:2544). Both
       belong on the page — an admin previewing it wants to see what a buyer
       sees AND reach their own tools — so they stack rather than fight. */
    body.has-admin-tools .ek-buybar {
        bottom: 70px;
        box-shadow: 0 -6px 20px rgba(15, 20, 35, .05);
    }

    body.has-buybar.has-admin-tools {
        padding-bottom: 144px;
    }
}

/* Narrow phones. The bar now carries every product, and «شروع آزمون بصورت
   آنلاین» is 19 characters — on a 320px screen the button at its normal size
   leaves the price too little room to stay on one line. */
@media (max-width: 359px) {
    .ek-buybar {
        gap: 8px;
        padding: 8px 10px calc(8px + env(safe-area-inset-bottom, 0px));
    }

    .ek-buybar__btn {
        padding: 11px 13px;
        font-size: 12.5px;
    }

    .ek-buybar__amount {
        font-size: 15.5px;
    }
}

/* --- upgrade offer: the foot of the buyer's file panel -------------------
   Purple, not the green the panel wears above it. On this page green means
   "your payment went through, here are your files"; an offer in the same
   colour reads as one more confirmation and gets scrolled past with the rest
   of the receipt. Purple is what the ladder wears everywhere else — the chips
   on the factor page, the panel on the product page — so a buyer meeting it
   here has met it twice already.

   Full-bleed inside the panel rather than a card with its own frame: it is the
   last section of the list above it, not a second thing on the page. */

.ek-upgrade {
    margin: 0;
    padding: 16px 20px 18px;
    border: 0;
    border-top: 1px solid #e6e1fb;
    border-radius: 0;
    background: #f6f4ff;
    text-align: right;
}

.ek-upgrade__head {
    display: flex;
    align-items: flex-start;
    gap: 10px;
    margin-bottom: 11px;
}

/* The same «+» the factor page uses to say "this one, and more" — one glyph
   doing one job across every surface the ladder appears on. */
.ek-upgrade__mark {
    flex: none;
    width: 26px;
    height: 26px;
    margin-top: 2px;
    border-radius: 50%;
    background: #6e4ff5;
    color: #fff;
    font-size: 17px;
    font-weight: bold;
    line-height: 26px;
    text-align: center;
}

.ek-upgrade__heading {
    min-width: 0;
}

.ek-upgrade__title {
    display: block;
    font-size: 15px;
    font-weight: 800;
    color: #2a2350;
    line-height: 1.75;
    text-wrap: pretty;
}

.ek-upgrade__tagline {
    display: block;
    margin-top: 2px;
    font-size: 12px;
    color: #6f6a8d;
    line-height: 1.9;
    text-wrap: pretty;
}

.ek-upgrade__list {
    list-style: none;
    margin: 0 0 14px;
    padding: 0;
}

.ek-upgrade__list li {
    position: relative;
    padding-right: 18px;
    font-size: 12.5px;
    color: #3f3a63;
    line-height: 2;
    text-wrap: pretty;
}

.ek-upgrade__list li::before {
    content: "";
    position: absolute;
    top: 10px;
    right: 3px;
    width: 6px;
    height: 6px;
    border-radius: 2px;
    background: #6e4ff5;
}

.ek-upgrade__list li.ek-upgrade__more {
    color: #8b85a8;
}

.ek-upgrade__list li.ek-upgrade__more::before {
    background: #c7c0e8;
}

.ek-upgrade__foot {
    display: flex;
    align-items: center;
    gap: 12px;
    flex-wrap: wrap;
}

.ek-upgrade__price b {
    font-size: 21px;
    font-weight: bold;
    color: #2a2350;
}

.ek-upgrade__price span {
    font-size: 12px;
    color: #6f6a8d;
    margin-right: 4px;
}

.ek-upgrade__btn {
    flex: 1;
    min-width: 200px;
    display: inline-block;
    padding: 13px 18px;
    border-radius: 10px;
    background: #6e4ff5;
    color: #fff;
    font-size: 13.5px;
    font-weight: bold;
    text-align: center;
    text-decoration: none;
    box-shadow: 0 6px 16px rgba(110, 79, 245, .26);
    transition: background-color .15s ease, transform .15s ease;
}

.ek-upgrade__btn:hover,
.ek-upgrade__btn:focus {
    background: #5a3ee0;
    color: #fff;
    text-decoration: none;
    transform: translateY(-1px);
}

.ek-upgrade__note {
    display: block;
    font-size: 11.5px;
    color: #837da3;
    line-height: 1.95;
    margin-top: 11px;
}

@media (max-width: 768px) {
    .ek-upgrade {
        padding: 14px 14px 16px;
    }

    /* The price and the button each take the full width: side by side on a
       phone the button loses to a 21px number beside it and stops looking
       like the thing to press. */
    .ek-upgrade__price,
    .ek-upgrade__btn {
        flex: 1 1 100%;
        min-width: 0;
    }

    .ek-upgrade__btn {
        padding: 12px 14px;
    }
}


/* --- factor page: which rung, and what is in it ---------------------------
   One control, not two boxes. The chips are the tabs and the panel under them
   is the selected chip spelled out — same fill, no divider between them, and
   no heading repeating the name the chip already carries. The two blocks it
   replaced were read as two separate things: a picker, and then a summary of
   something else.

   Inset from the card edge rather than run full-bleed, so it sits on the same
   28px rhythm as the price section and the form below it. A full-width slab
   between two padded sections reads as pasted in from somewhere else. */

.ek-factor-tier {
    margin: 20px 28px;
    padding: 15px 16px 16px;
    border: 1px solid #e4e0f4;
    border-radius: 14px;
    background: #fbfaff;
    text-align: right;
}

.ek-factor-tier__label {
    display: block;
    font-size: 11.5px;
    color: #8b95a8;
    margin-bottom: 9px;
}

.ek-factor-tier__row {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
}

/* A segmented control, not a second copy of the product page's radio cards.
   By the time somebody is on the factor page the decision is made and the
   question is narrow — "did I pick the right one?" — so the chips carry only
   the name and what it costs, and the panel below them keeps explaining the
   one that is selected. Anchors rather than inputs: the whole total reloads. */
.ek-factor-chip {
    flex: 1 1 auto;
    min-width: 120px;
    display: flex;
    flex-direction: column;
    gap: 3px;
    padding: 9px 12px;
    border: 1px solid #dfe4ec;
    border-radius: 9px;
    background: #fff;
    text-decoration: none;
    transition: border-color .15s ease, background-color .15s ease;
}

.ek-factor-chip:hover,
.ek-factor-chip:focus {
    border-color: #7d6ce0;
    text-decoration: none;
}

.ek-factor-chip__name {
    font-size: 12.5px;
    font-weight: bold;
    color: #3f4759;
    line-height: 1.7;
}

.ek-factor-chip__price {
    font-size: 11.5px;
    color: #8b95a8;
}

/* The selected rung is filled, not merely outlined: an outline alone reads as
   "hoverable" next to three other outlined chips. The fill is the same as the
   panel below, which is what ties the two into one control. */
.ek-factor-chip.is-current {
    border-color: #4c3fb5;
    background: #f1effe;
    cursor: default;
}

.ek-factor-chip.is-current .ek-factor-chip__name {
    color: #4c3fb5;
}

.ek-factor-chip.is-current .ek-factor-chip__price {
    color: #6558c9;
}

/* Already paid for. Deliberately flat and unclickable — offering it as a
   choice would invite a second purchase of the same thing. */
.ek-factor-chip.is-owned {
    background: #f4f6f9;
    border-style: dashed;
    cursor: default;
}

.ek-factor-chip.is-owned .ek-factor-chip__name {
    color: #9aa3b2;
}

.ek-factor-chip.is-owned .ek-factor-chip__price {
    color: #2f9e6f;
}

/* --- the panel: the selected chip, spelled out --------------------------- */

.ek-factor-tier__detail {
    margin-top: 10px;
    padding: 12px 14px;
    border-radius: 10px;
    border-right: 3px solid #6e4ff5;
    background: #f1effe;
}

/* The ladder is cumulative, and this line is where that is established. It used
   to establish it in words — «همهٔ موارد X، به‌علاوهٔ» — which the eye had to take
   on trust, because rung 1 drew four bullets and rung 2 drew four bullets and
   switching between them changed the sentence and not the shape. It now leads
   with the count, which is the only part of the claim that moves. */
.ek-factor-tier__carried {
    display: block;
    font-size: 11.5px;
    font-weight: bold;
    color: #5b52a8;
    line-height: 1.8;
}

.ek-factor-tier__carried b {
    font-size: 13.5px;
    color: #2f2a55;
}

/* The rungs below, folded. Four rows restating what the other chip already says,
   sitting between the buyer and the pay button, is a poor trade on a phone; the
   summary keeps the count, which is the part that argues. */
.ek-factor-tier__carried-over {
    margin-top: 8px;
}

.ek-factor-tier__carried-over > summary {
    display: flex;
    align-items: center;
    gap: 6px;
    padding: 6px 9px;
    border-radius: 8px;
    background: rgba(110, 79, 245, .07);
    font-size: 11.5px;
    color: #5b52a8;
    cursor: pointer;
    list-style: none;
}

.ek-factor-tier__carried-over > summary::-webkit-details-marker {
    display: none;
}

/* A tick, not a bullet: the row's claim is «you keep all of these», and a tick
   is the shape that says nothing is being given up for the higher price. */
.ek-factor-tier__carried-over > summary::before {
    content: "✓";
    flex: none;
    font-size: 10px;
    font-weight: bold;
    color: #40c185;
}

/* margin-right: auto in an RTL row parks this at the far left, the end of the
   line, where a disclosure chevron belongs. */
.ek-factor-tier__carried-over > summary::after {
    content: "";
    flex: none;
    margin-right: auto;
    margin-top: 3px;
    border: 4px solid transparent;
    border-top-color: #9a93bd;
    transition: transform .15s ease;
}

.ek-factor-tier__carried-over[open] > summary::after {
    transform: rotate(180deg);
    margin-top: -3px;
}

.ek-factor-tier__carried-over .ek-factor-tier__list {
    margin: 6px 3px 0;
}

/* Denser and greyer than the list below it. These lines are there to be counted
   and spot-checked, not read: they are the half of the offer the buyer has
   already decided they want. */
.ek-factor-tier__list.is-carried li {
    padding-right: 15px;
    font-size: 11.5px;
    line-height: 1.7;
    color: #7b7596;
}

.ek-factor-tier__list.is-carried li::before {
    content: "✓";
    top: 0;
    right: 1px;
    width: auto;
    height: auto;
    border-radius: 0;
    background: none;
    font-size: 9.5px;
    font-weight: bold;
    color: #aaa3cb;
}

/* The seam between what the buyer would get anyway and what they are paying the
   difference for. Everything below it answers «why the extra», which makes it
   the most persuasive line in the panel — and as a caption between two hairlines
   it was the quietest thing on the card. It is a label now, filled and carrying
   its own count, with the rule left to trail off behind it.

   In an RTL row the first child sits at the right, so the label leads and the
   line runs away to the left. */
.ek-factor-tier__only {
    display: flex;
    align-items: center;
    gap: 9px;
    margin: 13px 0 4px;
    font-size: 10.5px;
    font-weight: bold;
}

.ek-factor-tier__only b {
    flex: none;
    padding: 3px 11px 4px;
    border-radius: 99px;
    background: linear-gradient(135deg, #6e4ff5 0%, #5b3fe0 100%);
    color: #fff;
    box-shadow: 0 2px 8px rgba(110, 79, 245, .26);
}

.ek-factor-tier__only::after {
    content: "";
    flex: 1;
    height: 1px;
    background: linear-gradient(to left, #cfc4fa, transparent);
}

/* The lines the label is pointing at. A shade darker than an ordinary contents
   list and a slightly heavier mark: after a fold of ticked-off grey, these are
   the ones the buyer has not seen anywhere else on the page. */
.ek-factor-tier__list.is-exclusive li {
    color: #2f3646;
}

.ek-factor-tier__list.is-exclusive li::before {
    top: 9px;
    width: 7px;
    height: 7px;
    border-radius: 2.5px;
    box-shadow: 0 0 0 3px rgba(110, 79, 245, .13);
}

/* From 992px the panel has a column to itself and the rows cost nothing, so the
   carried list is open on arrival and the summary stops looking like a control.
   The `open` attribute itself is set in script — forcing a closed <details> to
   render its content from CSS alone is not reliable across browsers. */
@media (min-width: 992px) {
    .ek-factor-tier__carried-over > summary {
        cursor: default;
    }

    .ek-factor-tier__carried-over > summary::after {
        display: none;
    }
}

.ek-factor-tier__badge {
    display: inline-block;
    font-size: 11px;
    font-weight: bold;
    color: #b45309;
    background: #fff4e2;
    border-radius: 99px;
    padding: 3px 10px;
    margin-bottom: 8px;
}

.ek-factor-tier__list {
    list-style: none;
    margin: 7px 0 0;
    padding: 0;
}

.ek-factor-tier__list li {
    position: relative;
    padding-right: 17px;
    font-size: 12.5px;
    color: #3f4759;
    line-height: 1.95;
    text-wrap: pretty;
}

.ek-factor-tier__list li::before {
    content: "";
    position: absolute;
    top: 10px;
    right: 3px;
    width: 6px;
    height: 6px;
    border-radius: 2px;
    background: #6e4ff5;
}

/* The way up, offered from inside the panel rather than left to be inferred
   from a bigger number on a chip. It says the dearer option contains this one —
   the single fact two prices side by side cannot convey.

   It was a sentence under a dashed rule, and it read as a footnote to the list
   above it: the name, the count and the price ran together into one paragraph
   that wrapped wherever the box happened to end, leaving «۴ مورد دیگر» alone on
   its own line and the price underlined like a stray horizontal rule. It is an
   offer, so it now looks like one — a card on the panel's fill, the three facts
   in three fixed places. */
.ek-factor-tier__more {
    display: flex;
    align-items: center;
    gap: 10px;
    margin-top: 11px;
    padding: 9px 10px;
    border: 1px solid #d6cff5;
    border-radius: 10px;
    background: #fff;
    color: #4c3fb5;
    text-decoration: none;
    transition: border-color .15s, box-shadow .15s;
}

.ek-factor-tier__more:hover,
.ek-factor-tier__more:focus {
    color: #372b91;
    text-decoration: none;
    border-color: #6e4ff5;
    box-shadow: 0 2px 10px rgba(110, 79, 245, .13);
}

/* «+۴ بیشتر». The count is the whole argument — the one thing on this row that
   says how much more there is — so it goes in the mark rather than being spelled
   out mid-sentence where nothing makes it findable. On its own «+۴» was a number
   with no unit, and it borrowed its meaning from the line beside it; the word
   underneath means the mark reads without help. */
.ek-factor-tier__more-mark {
    flex: none;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    min-width: 34px;
    padding: 4px 5px 5px;
    border-radius: 8px;
    background: #6e4ff5;
    color: #fff;
    text-align: center;
}

.ek-factor-tier__more-mark b {
    font-size: 13px;
    font-weight: bold;
    line-height: 1.15;
}

.ek-factor-tier__more-mark small {
    font-size: 8.5px;
    line-height: 1.1;
    opacity: .8;
}

.ek-factor-tier__more-text {
    flex: 1;
    min-width: 0;
    line-height: 1.5;
}

.ek-factor-tier__more-name {
    display: block;
    font-size: 12.5px;
    font-weight: bold;
    color: #2f2a55;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* Not bold. The name above it is the bold thing on this row, and a second bold
   line in a two-line block leaves neither of them emphasised. It gets a tick and
   a darker grey instead: the claim is «you lose nothing», and a tick states that
   in a way a sentence in the same weight as everything else does not. */
.ek-factor-tier__more-note {
    display: block;
    position: relative;
    padding-right: 14px;
    font-size: 11px;
    color: #6a6486;
}

.ek-factor-tier__more-note::before {
    content: "✓";
    position: absolute;
    right: 0;
    top: 0;
    font-size: 10px;
    font-weight: bold;
    color: #40c185;
}

/* Never wraps and never shrinks: this is the number the buyer is deciding
   against, and a price that has moved to the next line is a price they have to
   go looking for.

   Stacked the same way the mark is, so the row reads as two figures with their
   units under them — «۴ مورد» on one end, «۳۱,۸۰۰ تومان بیشتر» on the other —
   rather than as a badge and a price in two different shapes. */
.ek-factor-tier__more-price {
    flex: none;
    display: flex;
    flex-direction: column;
    align-items: center;
    white-space: nowrap;
    line-height: 1.25;
    color: #372b91;
}

.ek-factor-tier__more-amount {
    display: flex;
    align-items: baseline;
    gap: 3px;
}

.ek-factor-tier__more-amount b {
    font-size: 14px;
    font-weight: bold;
}

.ek-factor-tier__more-amount small {
    font-size: 10.5px;
    opacity: .75;
}

/* Lighter than the caption under the mark, and deliberately so. «مورد» is a
   unit — it tells you what the 4 counts. «بیشتر» is not a unit of تومان; it is
   the qualifier that stops 31,800 being read as the price of the other version,
   which is the whole reason it is on the row. It has to be legible and it must
   not compete: the number is the information, this is the caveat attached to it.

   «تفاوت» would sit here more naturally as a noun, and it was the alternative.
   It also sounds like an accounting line. «بیشتر» is the word that makes 31,800
   feel like a top-up rather than a second purchase, so it stays and recedes
   instead. */
.ek-factor-tier__more-unit {
    margin-top: 1px;
    font-size: 9px;
    letter-spacing: .02em;
    color: #a8a2c4;
}

.ek-factor-tier__note {
    display: block;
    font-size: 11.5px;
    color: #7b7596;
    line-height: 1.9;
    margin-top: 9px;
}

/* While the server is answering a switch. The panel keeps its size and its
   words — swapping them for a spinner would make choosing a version look like
   loading a page, which is the thing being removed. */
.ek-factor-tier.is-switching {
    opacity: .5;
    pointer-events: none;
    transition: opacity .12s ease;
}

/* On a phone this is a box, inside a box, inside a card, and each frame takes
   about 25px off every line of text. The card is frame enough: here the picker
   gives up its own border, rounding and inset and separates with hairlines
   instead, the way the band above it does, and every horizontal padding on the
   way in gets smaller. What that frees goes to the words. */
@media (max-width: 768px) {
    .ek-factor-tier {
        margin: 0;
        padding: 13px 14px 15px;
        border: 0;
        border-top: 1px solid #eceef3;
        border-bottom: 1px solid #eceef3;
        border-radius: 0;
    }

    .ek-factor-chip {
        padding: 8px 10px;
    }

    /* The panel used to break out of the picker's padding and run edge to edge,
       bought with the rounding and the frame, because on a 390px screen fifty
       pixels of line width was the difference between a bullet on one line and
       a bullet on two.

       The page gutter outside the card has since dropped from 25px a side to
       12 (factor.blade.php), which hands back more width than the breakout was
       buying. So the panel takes its box back: it reads as the expansion of the
       chip above it — same fill, same rounding, sitting inside the picker
       rather than cutting across it — instead of as a third full-width band
       stacked under two others. */
    .ek-factor-tier__detail {
        margin: 11px 0 0;
        padding: 11px 12px 12px;
        border-radius: 11px;
        border: 1px solid #ddd4fb;
        border-right-width: 3px;
        border-right-color: #6e4ff5;
    }

    .ek-factor-tier__list li {
        padding-right: 15px;
    }
}

@media (max-width: 480px) {
    /* Two per row on a phone: three chips in one line truncate the names, and
       the name is the only thing distinguishing them. */
    .ek-factor-chip {
        flex: 1 1 calc(50% - 8px);
        min-width: 0;
    }
}


/* --- user panel: which rung, and the way up ------------------------------ */

.ek-panel-tier {
    display: inline-block;
    margin-right: 8px;
    padding: 2px 9px;
    border-radius: 99px;
    background: #f1effe;
    color: #4c3fb5;
    font-size: 11px;
    font-weight: bold;
    vertical-align: 2px;
}

/* Purple, like the offer on the download page and the ladder everywhere else.
   Green stays for the chip below it, which records an upgrade that already
   happened — one colour for a thing to do, another for a thing that is done. */
.ek-panel-upgrade {
    display: inline-flex;
    flex-direction: column;
    align-items: flex-start;
    gap: 1px;
    margin-right: 10px;
    padding: 6px 13px 7px;
    border-radius: 8px;
    border: 1px solid #6e4ff5;
    background: #f6f4ff;
    color: #4c3fb5;
    font-size: 12.5px;
    font-weight: bold;
    text-decoration: none;
}

.ek-panel-upgrade b {
    font-size: 11px;
    font-weight: normal;
    color: #6f6a8d;
}

.ek-panel-upgrade:hover,
.ek-panel-upgrade:focus {
    background: #6e4ff5;
    border-color: #6e4ff5;
    color: #fff;
    text-decoration: none;
}

.ek-panel-upgrade:hover b,
.ek-panel-upgrade:focus b {
    color: rgba(255, 255, 255, .85);
}

/* The green of the "way up" link, restated as a flat chip: on the transactions
   table an upgrade is a fact about a past payment, not something to click. */
.ek-panel-tier--upgrade {
    background: #e6f7ef;
    color: #2f9e6f;
}

/* The climb, under the product title. Deliberately quiet — most buyers never
   see it, and the ones who do are checking a charge, not browsing. */
.ek-panel-history {
    margin: 6px 0 0;
    padding-right: 26px;
}

.ek-panel-history__line {
    display: block;
    font-size: 11.5px;
    color: #8b95a8;
    line-height: 2;
}

/* --- proof strip: the buying reasons, above the price -------------------- */

/* One panel, four columns, hairlines between them.

   It shipped as a 2×2 grid of separately-bordered tiles, which cost ~165px —
   more than the whole gap between the product title and the rung cards on a
   phone, so the strip pushed the decision it was written to support below the
   fold. Four columns of one row say the same four facts in ~90px.

   Flex rather than a 4-column grid because the strip carries between one and
   four chips: `flex: 1` divides whatever there is, while fixed columns would
   leave a two-chip product with two empty cells. */
.ek-proof {
    list-style: none;
    display: flex;
    align-items: stretch;
    margin: 0 0 20px;
    padding: 0;
    border: 1px solid #e3e9f1;
    border-radius: 12px;
    background: #fff;
    box-shadow: 0 1px 2px rgba(22, 32, 52, .04);
    /* Clips the cell tint to the panel's own rounded corners; the cells carry
       no radius of their own, which is what makes the four read as one strip. */
    overflow: hidden;
}

.ek-proof__item {
    flex: 1 1 0;
    min-width: 0;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 4px;
    padding: 10px 4px 11px;
    text-align: center;
    background: linear-gradient(#fdfeff, #f6f9fc);
}

/* The divider is a border on the item, not a gap in the panel: a gap would let
   the page's white through and break the strip back into tiles. Logical side,
   because the page is RTL and the row therefore starts on the right. */
.ek-proof__item + .ek-proof__item {
    border-inline-start: 1px solid #e9edf4;
}

/* The evidence line. Fixed minimum height so a figure cell and a capability
   cell put their labels on the same baseline — otherwise the 26px green disc
   drops the tick's caption below the numbers' captions and the row reads
   ragged. */
.ek-proof__fact {
    display: flex;
    align-items: center;
    justify-content: center;
    min-height: 26px;
    max-width: 100%;
}

/* The one mark a chip can carry. A figure and a text value carry none — the
   number or the word IS the evidence — so this element exists only on a flag
   and a deny, where the mark is the entire answer. */
.ek-proof__mark {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: none;
    width: 26px;
    height: 26px;
    border-radius: 50%;
}

.ek-proof__item--flag .ek-proof__mark {
    background: #e6f7ef;
    color: #2f9e6f;
}

/* A denial is stated, not shouted. Grey rather than red: it is one honest line
   on a page trying to sell, and red beside a buy button reads as an error
   rather than as a specification. */
.ek-proof__item--deny .ek-proof__mark {
    background: #eef1f5;
    color: #8794a6;
}

.ek-proof__value {
    font-size: 17px;
    font-weight: bold;
    line-height: 1.25;
    color: #1f2a3c;
    /* Digits of equal width, so «۳» and «۱۵» in neighbouring cells sit on the
       same optical centre. */
    font-variant-numeric: tabular-nums;
    min-width: 0;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* A word is not a figure: at the numbers' size «PDF/Word» would not fit a 74px
   cell, and the ellipsis would trim the FRONT of it («…/Word») because an RTL
   cell trims the side the reader starts on. */
.ek-proof__item--text .ek-proof__value {
    font-size: 12.5px;
    line-height: 1.4;
    white-space: normal;
    overflow: hidden;
    text-overflow: clip;
    /* Last resort only, for a value longer than the cell. `anywhere` rather
       than `break-word` because only `anywhere` also shrinks the cell's
       min-content width, which is what keeps the four columns equal. */
    overflow-wrap: anywhere;
}

.ek-proof__label {
    font-size: 10.5px;
    line-height: 1.35;
    color: #6b7a90;
    /* Persian compounds joined by a ZWNJ («نمره‌گذاری») are longer than a 90px
       cell; break only when a word genuinely cannot fit. */
    overflow-wrap: break-word;
}

/* With no figure above it the label carries the whole claim, so it carries the
   weight too. */
.ek-proof__item--flag .ek-proof__label,
.ek-proof__item--deny .ek-proof__label {
    font-weight: bold;
    color: #33445c;
}

/* Said plainly, not sold. The caption is the claim either way, so it keeps the
   flag's weight; only the colour steps back. */
.ek-proof__item--deny .ek-proof__label {
    color: #75839a;
}

/* Small phones: the cells are ~75px there, so the padding goes before the type
   does. */
@media (max-width: 400px) {
    .ek-proof__item {
        padding: 9px 2px 10px;
    }

    .ek-proof__value {
        font-size: 16px;
    }

    /* A ~56px cell on a 320px phone is one step narrower than «PDF/Word» set at
       12.5px, and the overflow guard would then break it mid-word. */
    .ek-proof__item--text .ek-proof__value {
        font-size: 11.5px;
    }

    .ek-proof__label {
        font-size: 10px;
    }
}

/* --- an online test says its size in one line ---------------------------- */

/* «۵۸ سؤال · ۱۵ دقیقه», above the price, where a file product gets the proof
   strip.

   Not the strip, and not a smaller version of it: a test has exactly two
   figures worth printing before the button, and a bordered panel around two
   numbers — or, as it actually shipped, around ONE — makes a spec sheet out of
   a sentence. No border, no tint, no shadow: the price 20px below is the thing
   this card is built to show, and a boxed line above it competes for the same
   glance.

   Centred on the card, because the price and the button below it are, and a
   left-aligned line above two centred ones reads as a stray caption. */
.container.product-info aside .ek-testmeta {
    list-style: none;
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    justify-content: center;
    /* Wider than it looks like it needs: this line and the price are the only
       two things above the fold that carry figures, and at 16px they read as
       one block with the price's own second line. */
    margin: 0 0 22px;
    padding: 0;
}

.container.product-info aside .ek-testmeta li {
    display: inline-flex;
    align-items: baseline;
    gap: 4px;
    margin: 0;
    /* The sidebar's base list rule offsets every item by 15px and hangs an
       absolutely positioned marker outside it; both have to go, or the two
       facts sit off-centre with a purple square between them. */
    position: static;
    right: auto;
}

.container.product-info aside .ek-testmeta li::before {
    content: none;
}

/* A middot, not a hairline: with two items a divider rule would look like the
   start of a table. */
.container.product-info aside .ek-testmeta li + li::before {
    content: '·';
    margin: 0 8px;
    color: #ccd4e0;
    /* Undoes the base marker's absolute positioning, which would otherwise
       take the separator out of the line it separates. */
    position: static;
    width: auto;
    height: auto;
    background: none;
}

/* Emphasis inside the line, not against the price.

   It shipped at 16px bold in the price's own near-black, 16px above a 32px
   bold figure — near enough in weight and colour that the two read as one
   two-line price. The figures still have to lead their units, so the contrast
   stays; it is just spent inside this line rather than competing with the
   thing 22px below it. */
.ek-testmeta__value {
    font-size: 13px;
    font-weight: 600;
    line-height: 1.4;
    color: #55627a;
    /* Same as the proof strip: equal-width digits keep «۸» and «۵۸» on one
       optical centre. */
    font-variant-numeric: tabular-nums;
}

.ek-testmeta__unit {
    font-size: 12px;
    color: #8894a6;
}

/* --- the sample interpretation, under the buy button --------------------- */

/* The second choice on a test page, and the only honest answer to "what do I
   actually get?" — so it is a button, directly under the buy button, rather
   than the 14px grey underlined line it was, sitting below the reassurance
   chips where a page keeps its small print.

   Outline where the buy button is filled: the pair has to read as one primary
   action and one secondary, and two filled bars of the same width read as two
   equal ones. Its own hairline border rather than the brand blue at full
   strength for the same reason — the border only becomes blue on hover, when
   the visitor has already chosen to look at it. */
.container.product-info aside .btn-sample-interpretation {
    display: block;
    width: 100%;
    margin-top: 8px;
    padding: 12px 15px;
    border: 1px solid #dfe5f0;
    border-radius: 4px;
    background: #fff;
    color: #3a6cff;
    font-size: 13px;
    font-weight: 500;
    text-align: center;
    text-decoration: none;
    transition: background-color .15s ease, border-color .15s ease;
}

.container.product-info aside .btn-sample-interpretation:hover,
.container.product-info aside .btn-sample-interpretation:focus {
    border-color: #3a6cff;
    background: #f3f6ff;
    color: #3a6cff;
    text-decoration: none;
}

/* --- the ladder is cumulative, said out loud ----------------------------- */

.ek-tier__carried {
    display: block;
    font-size: 11.5px;
    font-weight: bold;
    color: #2f9e6f;
    line-height: 1.9;
    margin-top: 8px;
}

.ek-tier__carried + .ek-tier__includes {
    margin-top: 3px;
}

/* --- price block --------------------------------------------------------- */

/* The legacy rule (style.css:998) sets 30px/bold on the wrapper and lets it
   cascade into whatever markup price_html() emitted; the sizes below are
   explicit so nothing depends on that inheritance, and the paddings replace the
   ones that used to reserve room for an absolutely-positioned price. */
.container.product-info aside .price.ek-price {
    font-size: inherit;
    font-weight: normal;
    margin: 0 0 18px;
    padding: 0 0 18px;
    border-bottom: 1px solid #e8ecf2;
}

.ek-price__now {
    display: flex;
    align-items: baseline;
    gap: 6px;
    line-height: 1.3;
}

.ek-price__was {
    display: flex;
    align-items: center;
    gap: 8px;
    margin-top: 8px;
}

/* Centred only in the sidebar box. price_html() also renders inside the failed
   payment card, where the surrounding block is left-aligned. */
.container.product-info aside .ek-price__now,
.container.product-info aside .ek-price__was {
    justify-content: center;
}

.ek-price__amount {
    font-size: 32px;
    font-weight: bold;
    color: #24303f;
    letter-spacing: -.5px;
}

.ek-price--free .ek-price__amount {
    color: #0ac487;
}

/* «تومان» is a unit, not part of the figure, so it does not compete with it. */
.ek-price__currency {
    font-size: 14px;
    font-weight: normal;
    color: #6b7a90;
}

.ek-price__old {
    font-size: 13px;
    color: #98a3b3;
    text-decoration: line-through;
    text-decoration-color: #c9d1dc;
}

/* Red rather than the brand green: green is the buy button 20px below, and a
   discount that looks like the button reads as part of it. */
.ek-price__save {
    font-size: 11.5px;
    font-weight: bold;
    line-height: 1.7;
    color: #d94848;
    background: #fdecea;
    border-radius: 999px;
    padding: 3px 9px;
}

/* --- reassurance chips, below the buy button ----------------------------- */

/* Two equal columns rather than flex-wrap: the four are interchangeable
   reassurances of the same weight, and wrapping sized each one by its own text,
   which read as four different things. Grid rows stretch, so the pair on a row
   is the same height even when one of them wraps to two lines. */
.container.product-info aside .list-notic.list-notic--compact {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 5px;
    list-style: none;
    margin: 14px 0 0;
    padding: 0;
}

.container.product-info aside .list-notic.list-notic--compact li {
    display: flex;
    align-items: center;
    justify-content: center;
    text-align: center;
    margin: 0;
    /* Floor, not a fixed height: a label long enough to wrap keeps the tile it
       is in the same size as the other three rather than growing its row. */
    min-height: 30px;
    padding: 5px 7px;
    border: 0;
    border-radius: 7px;
    background: #f4f6fa;
    color: #6b7a90;
    font-size: 11px;
    font-weight: 500;
    line-height: 1.7;
    /* The base rule offsets each item by 15px and hangs its marker outside on
       `position:absolute`. Both have to be undone here, or the marker detaches
       from the chip and floats beside it. */
    position: static;
    right: auto;
}

/* No bullet. Centred text puts the marker wherever the label happens to end, so
   four labels of four different lengths gave four dots at four different
   positions — the one thing in a 2x2 grid that has to line up and did not.
   Aligning them to the start instead would fix the row but make a checklist out
   of what is deliberately the quietest block on the card, and the green tick it
   would borrow already means something more specific 200px above. `none`, not
   an empty string: the base rule (style.css:1005) hangs an absolutely
   positioned marker outside the item, and that one has to go too. */
.container.product-info aside .list-notic.list-notic--compact li::before {
    content: none;
}

/* --- only the chosen rung spells itself out ------------------------------
   Two rungs that both enumerate their contents make a column taller than the
   viewport, and the second card — the one the page recommends — lands below
   the fold. A visitor who never scrolls the sidebar never learns there is a
   second option at all, which is the same failure the proof strip had above.

   So a rung that is not selected keeps its name, its one-line promise and its
   price, and says how many items it carries instead of listing them. Choosing
   it expands it and collapses the other, so the column stays about one card
   taller than a single rung no matter how much a rung contains.

   Nothing is hidden that the page does not say elsewhere: the body copy
   carries the full side-by-side table, and the note under the cards still
   states that the cheaper rung is missing no file.

   Both conditions are needed. `.is-selected` is what the server renders and
   what the script toggles; `:has(input:checked)` covers the same state when
   the script has not run, so the control still works with JavaScript off. */
.ek-tier:not(.is-selected):not(:has(input:checked)) .ek-tier__carried,
.ek-tier:not(.is-selected):not(:has(input:checked)) .ek-tier__includes {
    display: none;
}

/* The count replaces the list, so it only appears when the list is gone. */
.ek-tier__count {
    display: none;
    font-size: 11.5px;
    color: #8b95a8;
    line-height: 1.9;
    margin-top: 6px;
}

.ek-tier:not(.is-selected):not(:has(input:checked)) .ek-tier__count {
    display: block;
}

/* --- the cards read as a block, not as a column of stranded words --------
   A Persian line ending in a Latin run («… قالب Word و PDF») breaks before the
   run and leaves one word alone on the next line, which is what made these
   cards look ragged rather than merely tall. `text-wrap: pretty` asks the
   browser to avoid exactly that; where it is not supported the text simply
   wraps as it does today.

   The leading these four lines carry is set with the rest of the card sizes
   above, so a change to how tight the picker is happens in one place. */
.ek-tier__tagline,
.ek-tier__includes li,
.ek-tier__carried,
.ek-tier__count {
    text-wrap: pretty;
}

/* Letting the name shrink is what keeps it on one line with the badge beside
   it; a 24px row spent on a 10px chip is the most expensive whitespace here. */
.ek-tier__name {
    min-width: 0;
}

.ek-tier__carried {
    line-height: 1.7;
    margin-top: 6px;
}

.ek-tier__count {
    line-height: 1.7;
    margin-top: 4px;
}

/* --- the side-by-side table, in the body copy ---------------------------
   The rung cards in the sidebar carry short labels so both fit on one screen;
   this is where the full wording lives, and where the two can be compared a
   row at a time instead of by scrolling between two boxes.

   Styled here rather than inline in `content_product` for two reasons: the
   audit flags inline colours outside the brand palette — correctly, even
   though these were lifted from the storefront — and a table built into 2,700
   product descriptions is a table nobody can restyle later. */
.ek-compare {
    width: 100%;
    border-collapse: collapse;
    margin: 14px 0 10px;
    font-size: 14px;
}

.ek-compare th,
.ek-compare td {
    padding: 9px 12px;
    border: 1px solid #e2e7ef;
    text-align: right;
    vertical-align: top;
}

.ek-compare thead th {
    background: #f4f6fa;
    font-weight: bold;
    color: #2b3245;
}

/* The recommended column is tinted for its whole height, so the eye can follow
   one column down the table without counting cells across. */
.ek-compare thead th.is-upper {
    background: #f3f0ff;
    color: #4c3fb5;
}

.ek-compare .ek-compare__price {
    display: block;
    font-weight: normal;
    color: #6d788c;
    font-size: 13px;
}

.ek-compare td.ek-compare__cell {
    text-align: center;
    width: 22%;
}

.ek-compare td.ek-compare__cell.is-upper {
    width: 26%;
}

.ek-compare__yes { color: #2f9e6f; font-weight: bold; }

/* A dash, not a cross: the row is absent from the cheaper rung, it is not
   broken there. Grey for the same reason the deny chip is grey. */
.ek-compare__no { color: #c2cad6; }

.ek-compare__note {
    font-size: 13px;
    color: #6d788c;
}
