/**
 * Contextual reports — the "Reports" control on a record page.
 *
 * ⛔ THIS COMPONENT SHIPPED WITH NO STYLES AT ALL, ON ELEVEN ROUTES.
 *
 * `context-report-button.js` has always emitted `ctx-reports`, `ctx-reports-toggle`,
 * `ctx-reports-menu`, `ctx-reports-item`, `ctx-reports-desc` and `ctx-reports-state` — and not
 * one of those class names appeared in any stylesheet in this repository, or as an inline style,
 * or in an injected <style>. So the menu rendered as bare bordered boxes pinned to the top-left
 * of the document, overlapping the page header, with each template's NAME and DESCRIPTION run
 * together into one unbroken sentence: "Risk registerThe full risk register with inherent...".
 *
 * It was found by photographing it. The feature works — the registry carries eleven route keys,
 * its deploy gate passes, and the menu opens with the right templates — so nothing failed and no
 * test noticed. An unstyled control is invisible to every check except looking at it, which is
 * precisely what the article's screenshot pass is for.
 *
 * ⛔ LOADED GLOBALLY, NOT PER ROUTE. `registry.js` declares stylesheets per route, and this
 * component mounts on eleven of them. Adding it eleven times would leave the twelfth route that
 * mounts the button silently unstyled again — the same defect, reintroduced by someone doing
 * exactly what the pattern told them to. It sits with the other globally-mounted components in
 * app/index.html instead.
 *
 * Everything below is design-system tokens from base.css. No component hex values: the module
 * palette is generated and a literal here would drift from it the moment a colour moved.
 */

/**
 * THE MENU OPENS BELOW THE ROW, NOT BELOW THE BUTTON.
 *
 * ⛔ WHY THE DIFFERENCE MATTERS, MEASURED. The panel is anchored with `top: calc(100% + 6px)`,
 * and 100% is the height of THIS element. As an inline-block wrapping only the toggle, that is
 * the toggle's own height — so in an actions row containing a taller neighbour the panel opens
 * ABOVE that neighbour's bottom edge and lands on it. On the Risk Register the primary
 * "+ New Risk" wraps to two lines and is the tallest control in the row: the panel began at
 * y≈174 while that button ran to y≈194, so its second line was covered in the article's own
 * screenshot of the feature. An independent review caught it; the earlier fix that moved this
 * control INTO the actions row is what created the collision.
 *
 * Stretching the wrapper to the row makes 100% the row's height, so the panel clears every
 * control beside it however tall they are, and no page has to know the button's size.
 */
/* The host is the element the mount inserts into the page's own actions row, so IT is the flex
   item — stretching the inner wrapper alone would have done nothing, because its parent is this
   div and not the row. Unstyled until now, which is why the collision existed at all. */
.ctx-reports-host {
    align-self: stretch;
    display: flex;
    align-items: center;
}

.ctx-reports {
    position: relative;
    display: inline-flex;
    align-items: center;
    align-self: stretch;
    /* Harmless where the host is not a flex item (the created row, a bare header): the
       wrapper simply keeps its natural height and 100% resolves to the toggle as before. */
    min-height: 100%;
}

/* The toggle is a normal secondary button; only the disclosure caret is added here. */
.ctx-reports-toggle::after {
    content: '';
    display: inline-block;
    margin-left: 8px;
    border-left: 4px solid transparent;
    border-right: 4px solid transparent;
    border-top: 4px solid currentColor;
    vertical-align: middle;
    transition: transform 120ms ease;
}

.ctx-reports[data-open="true"] .ctx-reports-toggle::after {
    transform: rotate(180deg);
}

/**
 * ANCHORED TO THE TOGGLE. Without `position: absolute` against the relative parent the menu
 * laid out in normal flow at the top of the document — which is what put it over the header.
 */
.ctx-reports-menu {
    position: absolute;
    top: calc(100% + 6px);
    /**
     * ⛔ OPENS RIGHTWARD. The first version used `right: 0`, which anchors the panel's RIGHT edge
     * to the toggle — correct for a control near the right of the viewport, and wrong for this
     * one. The toggle mounts at the LEFT edge of the content area, so a 320px panel extended
     * leftward UNDER THE SIDEBAR and every line of template text was clipped mid-word. Caught by
     * re-capturing after the first fix: the styles were right and the direction was not.
     *
     * ⛔ AND THEN IT CLIPPED ON THE OTHER EDGE. Once the host moved into the page's actions row
     * (so the menu stops covering the page title), the toggle sits at the RIGHT end of the
     * toolbar and a left-aligned panel ran off the right of the frame — the mirror image of the
     * first defect, from the mirror-image constant. `left: 0` is therefore the PREFERENCE, not
     * the rule: `chooseMenuSide()` measures the room and adds the modifier below when a
     * left-aligned panel would not fit.
     */
    left: 0;
    right: auto;
    z-index: 60;
    min-width: 320px;
    /* Never wider than the space actually left beside the nav, so it cannot overflow the page. */
    max-width: min(420px, calc(100vw - 380px));
    max-height: 60vh;
    overflow-y: auto;
    padding: 6px;
    background: var(--bg-primary);
    border: 1px solid var(--border-color);
    border-radius: var(--radius-lg, 10px);
    box-shadow: 0 8px 24px rgba(0, 0, 0, 0.12);
}

/* Set by chooseMenuSide() when a left-aligned panel would run past the right edge. */
.ctx-reports-menu--right {
    left: auto;
    right: 0;
}

/**
 * ⛔ THE THREE REPORTS MUST LOOK AS CLICKABLE AS THE LINK UNDER THEM.
 *
 * These are real <button role="menuitem"> elements and they have always worked. But they were
 * rendered in `--text-primary` at weight 600 with a description beneath, and the only affordance
 * distinguishing them from a heading was a hover background — which a static reader never sees.
 * The result, filed by an independent reviewer against the article's own screenshot: the menu
 * reads as three paragraphs of prose with one link at the bottom, so the single most obviously
 * clickable thing in a menu of contextual reports is "Browse all reports →", the escape hatch.
 *
 * The name therefore takes the link colour, which the description below overrides for itself —
 * so the name reads as the action and the sentence under it stays secondary text.
 *
 * `--primary-text-strong`, NOT `--accent-primary`: base.css:1174 sets links to the former on
 * purpose, because the accent measures 4.49:1 light / 3.98:1 dark on the page wash and misses
 * the AA floor. Reaching for the accent here would have re-introduced the contrast bug that
 * comment exists to prevent.
 */
.ctx-reports-item {
    display: block;
    width: 100%;
    padding: 10px 12px;
    background: transparent;
    border: none;
    border-radius: var(--radius-md, 6px);
    text-align: left;
    font-size: 0.875rem;
    font-weight: 600;
    color: var(--primary-text-strong);
    cursor: pointer;
}

.ctx-reports-item:hover,
.ctx-reports-item:focus-visible {
    background: var(--bg-secondary);
}

/**
 * THE DESCRIPTION IS ITS OWN LINE. It is a sibling <span> inside the button, so without
 * `display: block` it sat immediately after the name with no space at all and the two read as
 * one run-on sentence — the single most obviously broken thing in the captured shot.
 */
.ctx-reports-desc {
    display: block;
    margin-top: 2px;
    font-size: 0.8125rem;
    font-weight: 400;
    line-height: 1.35;
    color: var(--text-secondary);
}

/**
 * THE ESCAPE HATCH SITS ON THE SAME LEFT EDGE AS THE REPORTS ABOVE IT.
 *
 * This class had no rule at all, so the anchor took base.css's link styling and none of the
 * menu's padding: its text began 12px to the left of every item name, and the menu's four
 * actionable rows formed two different left edges. Separated by a hairline, because it is a
 * different KIND of action — leaving this menu for the full library — and that distinction was
 * previously carried entirely by the fact that it was the only thing that looked like a link.
 */
.ctx-reports-all {
    display: block;
    margin-top: 4px;
    padding: 10px 12px;
    border-top: 1px solid var(--border-color);
    font-size: 0.875rem;
    font-weight: 600;
}

/* Loading, error and empty states share the menu's padding so they do not sit flush. */
.ctx-reports-state {
    margin: 0;
    padding: 10px 12px;
    font-size: 0.8125rem;
    color: var(--text-muted, var(--text-secondary));
}

.ctx-reports-error {
    color: var(--danger-text-strong, var(--text-primary));
}

/**
 * THE REVERSE SECTION — reports already written about this record.
 *
 * A separate GROUP, hairlined off the generate list above it, because it answers a different
 * question: everything above is what you can produce, this is what exists. Without the rule the
 * anchors would take base.css's link styling and none of the menu's padding — the same defect
 * `.ctx-reports-all` was written to fix, which is why it borrows that class's left edge exactly
 * rather than inventing a second one.
 */
.ctx-reports-about {
    margin-top: 4px;
    border-top: 1px solid var(--border-color);
}

/**
 * A LABEL, NOT AN ITEM. It must not read as something to click, so it takes the muted
 * treatment of the state lines rather than the item's weight — a heading styled like a row is
 * how a menu grows an entry that does nothing when pressed.
 */
.ctx-reports-about-head {
    margin: 0;
    padding: 10px 12px 4px;
    font-size: 0.75rem;
    font-weight: 600;
    letter-spacing: 0.02em;
    text-transform: uppercase;
    color: var(--text-muted, var(--text-secondary));
}

/*
 * Anchors, where the generate rows are buttons — so they need the item padding restated. The
 * hover/focus treatment is inherited from `.ctx-reports-item`, which they also carry, so the
 * two kinds of row feel the same to a pointer and to a keyboard.
 */
.ctx-reports-about-item {
    display: block;
    text-decoration: none;
    color: var(--text-primary);
    font-weight: 500;
}

/**
 * THE REVERSE SECTION'S OWN RECOVERY AND OVERFLOW ROWS.
 *
 * `.ctx-reports-retry` exists because the section previously ended at its error message while
 * the generate list twenty lines above offered a way forward. A `role="menu"` makes the gap
 * worse than an ordinary panel would: Tab DISMISSES the menu, so a control that is not a
 * `menuitem` cannot be reached by keyboard at all, and the only recovery left is the mouse.
 *
 * Styled as a row rather than a button so it shares the item left edge — the same reason
 * `.ctx-reports-all` and `.ctx-reports-about-item` restate that padding instead of inventing
 * their own. It sits under a message that is already coloured, so it does not repeat the colour.
 *
 * ⛔ THE COLOUR IS `--primary-text-strong`, WHICH THIS FILE ALREADY USES, BECAUSE I FIRST WROTE
 * `var(--link-color, …)` AND `--link-color` DOES NOT EXIST.
 *
 * A token you invent reads perfectly, survives review, and renders correctly — the fallback in
 * `var(--invented, --real)` silently supplies the real value, so there is nothing to see on
 * screen and nothing to catch by looking. The only thing that notices is
 * `validate-no-phantom-tokens-universal`, and it reported `count: 2` (this file and its admin
 * mirror) against a shrink-only threshold of 0, reddening the land gate.
 *
 * Worse, the batch runner could not attribute it: the check reports a COUNT rather than a file
 * map, so it announced "failing checks name no file it changed" and went off to gate master
 * alone to find out whose break it was. A count-shaped check is invisible to file-based blame —
 * so when a gate reds on one, run it yourself and read its offenders list rather than waiting to
 * be told it is not yours. Checklist §AB.
 */
.ctx-reports-retry {
    display: block;
    width: 100%;
    padding: 4px 12px 10px;
    border: 0;
    background: none;
    font: inherit;
    font-size: 0.8125rem;
    font-weight: 600;
    text-align: left;
    color: var(--primary-text-strong);
    cursor: pointer;
}

/**
 * The cap disclosure. A quieter row than a report, because it is a statement about the list
 * rather than another entry in it — but still a `menuitem` and still an anchor, since it is the
 * only route to the reports the cap left out.
 */
.ctx-reports-about-more {
    display: block;
    padding: 4px 12px 10px;
    font-size: 0.75rem;
    font-weight: 600;
    text-decoration: none;
    color: var(--text-muted, var(--text-secondary));
}

.ctx-reports-retry:hover,
.ctx-reports-retry:focus-visible,
.ctx-reports-about-more:hover,
.ctx-reports-about-more:focus-visible {
    color: var(--text-primary);
    text-decoration: underline;
}
