@charset "UTF-8";
/* =============================================
   Tosefta with Variants — Clean Academic Theme
   ============================================= */

/* --- Base --- */
*,
*::before,
*::after {
    box-sizing: border-box;
}


body {
    font-family: 'Noto Serif Hebrew', serif;
    direction: rtl;
    line-height: 1.7;
    margin: 0;
    padding: 0;
    background-color: #faf8f5;
    color: #2c2c2c;
}

/* --- Header --- */
.site-header {
    background: #fff;
    border-bottom: 2px solid #d4c9b8;
    padding: 14px 20px;
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 16px;
    position: sticky;
    top: 0;
    z-index: 100;
}

.header-title {
    display: flex;
    align-items: center;
    gap: 10px;
}

.site-header h1 {
    font-family: 'Suez One', serif;
    font-weight: 400;
    font-size: 1.4em;
    margin: 0;
    color: #3a2e20;
    white-space: nowrap;
}

/* The header holds only its two menu handles (☰ and תצוגות), the title and the
   masechet selector. Its old .header-controls nav -- the אוצר link and the Word
   export -- moved into #sidebar under a divider, so those rules are gone with
   the markup. */

/* Push-button toggles for the apparatus panels. Their size and type come from
   whichever container currently holds them (.header-dropdown on desktop,
   .bottom-tabbar on a phone); this rule owns only the shape, the palette and the
   pressed state, so a button reads consistently wherever it has been relocated
   to.

   [hidden] needs stating explicitly: `display` here would otherwise beat the
   UA's `[hidden] { display: none }`, and every availability check in the JS
   sets exactly that attribute -- registry.onChange for the dock layers,
   updateDisplay for the synopsis. Without this the buttons for apparatus a
   tractate does not have stayed on screen and clickable, which is the whole of
   what a "dead button" was. */
.nav-toggle-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    padding: 3px 9px;
    border: 1px solid #6b5b47;
    border-radius: 4px;
    background: #fff;
    color: #6b5b47;
    cursor: pointer;
    line-height: 1;
    transition: background 0.15s, color 0.15s;
}

.nav-toggle-btn[hidden] {
    display: none;
}

.nav-toggle-btn:hover {
    background: #6b5b47;
    color: #fff;
}

.nav-toggle-btn.active {
    background: #6b5b47;
    color: #fff;
}

/* Word export. Its appearance is now .sidebar-action's (it is a labelled row in
   the settings panel, not a bare icon button in the navbar) plus the blue
   .nav-export-mark badge; what stays here is only the state this button has and
   the others do not -- the in-progress feedback while the docx is built. */
.nav-export-w {
    font-size: 1.05em;
}

.nav-export-arrow {
    font-size: 0.85em;
}

.nav-export.loading {
    opacity: 0.6;
    cursor: default;
}

.nav-export.loading .nav-export-arrow {
    animation: nav-export-bounce 0.8s ease-in-out infinite;
}

@keyframes nav-export-bounce {
    0%, 100% { transform: translateY(0); }
    50% { transform: translateY(2px); }
}

/* --- Page layout: TOC + content --- */
.page-layout {
    display: flex;
    min-height: calc(100vh - 60px);
}

/* --- Settings dropdown (the former sidebar column) --- */
/* Drops down from under the ☰ button instead of standing as a 280px column all
   session. The filters are set once and then read past, so a permanent column
   spent a fifth of the window on controls that are idle almost all of the time;
   as an overlay it reserves no width at all and the reading measure grows by
   that much.

   Anchored to the inline-START edge because that is where its button is, and to
   the measured header height (published by the ResizeObserver in index.html)
   because the header wraps to two or three rows on a narrow screen and a fixed
   3.5rem would leave the panel overlapping it or floating below it. */
.sidebar {
    position: fixed;
    inset-inline-start: 12px;
    top: calc(var(--site-header-height, 3.5rem) + 6px);
    /* Above .bottom-panels (500). A transient menu belongs over a standing
       panel, and at 460 the synopsis footer and manuscript dock cut off the
       bottom of this one -- taking the pinned .sidebar-actions with it, so the
       export and the אוצר link became unclickable whenever a dock was open. */
    z-index: 520;
    inline-size: 320px;
    max-inline-size: calc(100vw - 24px);
    /* Never taller than the room below the header, so the panel scrolls
       internally rather than running off the bottom of the window. */
    max-block-size: calc(100vh - var(--site-header-height, 3.5rem) - 24px);
    overflow-y: auto;
    overscroll-behavior: contain;
    background: #fff;
    border: 1px solid #d8ccb8;
    border-radius: 8px;
    box-shadow: 0 8px 28px rgba(0, 0, 0, 0.16);
    padding: 14px;
    /* Closed by default. visibility (not display) so the panel can transition,
       and so its scroll position survives being closed and reopened. */
    visibility: hidden;
    opacity: 0;
    transform: translateY(-6px);
    transition: opacity 0.15s ease, transform 0.15s ease, visibility 0.15s;
}

.sidebar.open {
    visibility: visible;
    opacity: 1;
    transform: translateY(0);
}

/* --- Apparatus dropdown (תצוגות) --- */
/* Which registers are showing. A dropdown rather than the rail down the page
   edge this used to be: opening a panel is an occasional gesture and each panel
   closes by its own ✕, so a permanent column was chrome bought for an
   intermittent need -- and it had to be dodged by .side-dock, which can now sit
   flush to the edge again.

   The wrapper is the positioning context for the panel, so the panel hangs off
   this button specifically rather than off the header. */
.header-menu {
    position: relative;
    display: flex;
    align-items: center;
}

/* Same trap as .nav-toggle-btn[hidden]: `display` above beats the UA rule, and
   this wrapper is hidden by attribute on a tractate with no registers at all. */
.header-menu[hidden] {
    display: none;
}

.header-menu-btn {
    font-family: inherit;
    font-size: 0.85em;
    font-weight: 600;
    line-height: 1;
    padding: 9px 12px;
    border: 1px solid #c5bdb1;
    border-radius: 5px;
    background: #fff;
    color: #3a2e20;
    cursor: pointer;
    white-space: nowrap;
    transition: background 0.2s, color 0.2s, border-color 0.2s;
}

.header-menu-btn:hover {
    background: #f0ece4;
}

/* Two distinct states, deliberately not one: .active means this dropdown is
   expanded (set by openPanel), .has-open means some register is showing (set
   from the registry). A reader needs to know a panel is open whether or not the
   menu happens to be. */
.header-menu-btn.has-open {
    border-color: #8b7d6b;
    background: #f3ede1;
    color: #3a2e20;
}

.header-menu-btn.active {
    background: #8b7d6b;
    border-color: #8b7d6b;
    color: #fff;
}

.header-dropdown {
    position: absolute;
    top: calc(100% + 8px);
    inset-inline-start: 0;
    z-index: 470;
    min-inline-size: 11rem;
    display: flex;
    flex-direction: column;
    gap: 3px;
    padding: 6px;
    background: #fff;
    border: 1px solid #d8ccb8;
    border-radius: 8px;
    box-shadow: 0 8px 28px rgba(0, 0, 0, 0.16);
    /* Closed by default; visibility rather than display so it can transition.
       Matches .sidebar's open/close language exactly -- they are the same kind
       of thing and should not animate differently. */
    visibility: hidden;
    opacity: 0;
    transform: translateY(-6px);
    transition: opacity 0.15s ease, transform 0.15s ease, visibility 0.15s;
}

.header-dropdown.open {
    visibility: visible;
    opacity: 1;
    transform: translateY(0);
}

/* Menu rows, not the centred pills of the old rail: a dropdown is read as a
   list, so the labels align at the reading edge and each row spans the width. */
.header-dropdown .nav-toggle-btn {
    justify-content: flex-start;
    width: 100%;
    padding: 8px 10px;
    font-family: inherit;
    font-size: 0.9em;
    font-weight: 500;
    text-align: start;
    white-space: nowrap;
    border-color: transparent;
    border-radius: 5px;
}

.header-dropdown .nav-toggle-btn:hover {
    background: #f2eee7;
    color: #2c2317;
}

/* An open register stays filled, so the menu is also the answer to "which of
   these am I looking at?" */
.header-dropdown .nav-toggle-btn.active,
.header-dropdown .nav-toggle-btn.active:hover {
    background: #6b5b47;
    border-color: #6b5b47;
    color: #fff;
}

.sidebar-toggle,
.toc-toggle {
    width: 38px;
    height: 38px;
    flex-shrink: 0;
    border-radius: 5px;
    border: 1px solid #c5bdb1;
    background: #fff;
    color: #3a2e20;
    font-size: 1.2em;
    line-height: 1;
    cursor: pointer;
    display: flex;
    align-items: center;
    justify-content: center;
    transition: background 0.2s;
}

/* Same reason as .nav-toggle-btn[hidden]: the `display` above would otherwise
   beat the UA rule, and #toc-toggle is hidden by attribute whenever the TOC is
   empty or we are above the mobile breakpoint (syncTocToggleVisibility). */
.sidebar-toggle[hidden],
.toc-toggle[hidden] {
    display: none;
}

.sidebar-toggle:hover,
.toc-toggle:hover {
    background: #f0ece4;
}

/* Filled while the dropdown is open, so the button reads as the panel's own
   handle. This used to mark the panel CLOSED (body.sidebar-collapsed), which
   was the right signal when the default state was a column standing open; with
   a dropdown, closed IS the default and needs no marking. */
.sidebar-toggle.active {
    background: #8b7d6b;
    border-color: #8b7d6b;
    color: #fff;
}

/* Click-anywhere-else-to-dismiss, at every width. Invisible on desktop: a
   dropdown that dimmed the page would read as a modal, which this is not. The
   mobile block below dims it, where the panel does cover most of the screen.

   BELOW .site-header (100), and that is the whole point rather than an
   accident. The header is `position: sticky; z-index: 100`, which makes it a
   stacking context: every z-index inside it -- including .header-dropdown's 470
   -- is resolved WITHIN that context and so cannot exceed 100 against the rest
   of the page. A backdrop above 100 therefore covered the header entirely, and
   with it every menu handle and every item of the apparatus dropdown. Raising
   the header instead is not an option: on mobile .bottom-panels (500)
   deliberately covers it as a full-height sheet.

   Leaving the header uncovered also means clicking a handle while its menu is
   open reaches the handle and toggles, instead of being swallowed by the
   backdrop; the header's own click-away listener in index.html handles the rest
   of the bar. */
.sidebar-overlay {
    display: none;
    position: fixed;
    inset: 0;
    z-index: 90;
    background: transparent;
}

.sidebar-overlay.visible {
    display: block;
}

/* --- TOC nav (perek/halakha navigation) --- */
.toc-nav {
    width: 54px;
    min-width: 54px;
    background: #fdfcfa;
    border-left: 1px solid #e8e3dc;
    padding: 10px 4px;
    overflow-y: auto;
    position: sticky;
    top: 60px;
    height: calc(100vh - 60px);
    font-size: 0.78em;
    text-align: center;
}

.toc-nav:empty {
    display: none;
}

.toc-perek {
    margin-bottom: 6px;
}

.toc-perek-label {
    display: block;
    font-weight: 700;
    color: #3a2e20;
    padding: 3px 2px;
    cursor: pointer;
    border-radius: 3px;
    text-decoration: none;
    transition: background 0.15s;
}

.toc-perek-label:hover {
    background: #ece7de;
}

.toc-halakhot {
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: 1px;
    padding: 2px 0;
}

.toc-h {
    display: inline-block;
    width: 20px;
    height: 20px;
    line-height: 20px;
    text-align: center;
    color: #6b5b47;
    text-decoration: none;
    border-radius: 3px;
    cursor: pointer;
    transition: background 0.15s;
}

.toc-h:hover {
    background: #ece7de;
}

.toc-h.active {
    background: #d4c9b8;
    color: #3a2e20;
    font-weight: 600;
}

/* --- Masechet selector (in the header) --- */
.masechet-selector {
    display: flex;
    align-items: center;
    gap: 8px;
}

.masechet-selector label {
    font-weight: 600;
    font-size: 0.92em;
    color: #3a2e20;
    white-space: nowrap;
}

.masechet-selector select {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.92em;
    padding: 6px 10px;
    border: 1px solid #c5bdb1;
    border-radius: 4px;
    background: #fff;
    color: #2c2c2c;
    cursor: pointer;
    max-width: 200px;
}

.masechet-selector button {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.9em;
    padding: 6px 16px;
    border: 1px solid #8b7d6b;
    border-radius: 4px;
    background: #8b7d6b;
    color: #fff;
    cursor: pointer;
    transition: background 0.2s;
}

.masechet-selector button:hover {
    background: #6b5b47;
}

/* Which base-text edition is currently loaded (Lieberman / in-house
   diplomatic / edBeeri-Zuckermandel / Sefaria Vilna fallback, etc.) --
   base text sourcing varies per tractate, so this needs to be visible. */
.edition-note {
    font-size: 0.78em;
    color: #8b7d6b;
    white-space: nowrap;
    padding: 3px 8px;
    background: #f7f4ef;
    border: 1px solid #e0dbd4;
    border-radius: 10px;
}

/* .filters-section label sets an unconditional display:flex (see that rule
   below), which otherwise overrides the browser's native
   `[hidden] { display: none }` -- author CSS always wins over that UA rule
   regardless of specificity, same issue .filters-section details:not([open])
   already documents above for a different element. */
.filters-section label[hidden] {
    display: none;
}

.chapter-header-alt {
    display: block;
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.5em;
    font-weight: 600;
    color: #4a6b7a;
    margin-top: 4px;
}

.edition-break-marker {
    display: inline-block;
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.72em;
    font-weight: 600;
    color: #4a6b7a;
    background: #eef3f4;
    border: 1px solid #c8d8db;
    border-radius: 8px;
    padding: 0 5px;
    margin: 0 2px;
    vertical-align: middle;
    white-space: nowrap;
}

/* --- Filter sections (using <details>) --- */
.filters-section details {
    background: #fff;
    border: 1px solid #e0dbd4;
    border-radius: 5px;
    margin-bottom: 8px;
    overflow: hidden;
}

/* Direct children set an unconditional `display` (flex, etc.) for their
   open-state layout, which otherwise overrides the browser's native
   `details:not([open]) > *:not(summary) { display: none }` collapse rule --
   author CSS always wins over that UA rule regardless of specificity. */
.filters-section details:not([open]) > *:not(summary) {
    display: none;
}

.filters-section summary {
    font-weight: 600;
    font-size: 0.88em;
    color: #3a2e20;
    padding: 8px 10px;
    cursor: pointer;
    background: #f7f4ef;
    border-bottom: 1px solid #e0dbd4;
    list-style: none;
    user-select: none;
}

.filters-section summary::-webkit-details-marker {
    display: none;
}

.filters-section summary::before {
    content: "◂ ";
    display: inline;
    font-size: 0.8em;
}

.filters-section details[open] > summary::before {
    content: "▾ ";
}

.filters-section .filter-body {
    padding: 8px 10px;
    display: flex;
    flex-direction: column;
    gap: 3px;
}

/* Top-level standalone toggles (show hidden, single witness) */
.filter-toggle {
    font-size: 0.85em;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 5px;
    padding: 5px 10px;
    border-bottom: 1px solid #ece8e1;
}

.filters-section label {
    font-size: 0.85em;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 5px;
    white-space: nowrap;
    padding: 2px 0;
}

.filters-section input[type="checkbox"] {
    width: 15px;
    height: 15px;
    cursor: pointer;
    accent-color: #8b7d6b;
    flex-shrink: 0;
}

/* Parent category label */
.filter-parent {
    font-weight: 600;
}

/* Flat first-level expandable filter row (no box, arrow at end) */
.filters-section details.filter-collapse {
    background: transparent;
    border: none;
    border-radius: 0;
    margin-bottom: 0;
    overflow: visible;
}

.filters-section details.filter-collapse > summary {
    background: transparent;
    border-bottom: none;
    padding: 2px 0;
    font-weight: 600;
    font-size: 0.85em;
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 8px;
}

.filters-section details.filter-collapse > summary::before {
    content: none;
}

.filters-section details.filter-collapse > summary::after {
    content: "◂";
    font-size: 0.8em;
    color: #8b7d6b;
}

.filters-section details.filter-collapse[open] > summary::after {
    content: "▾";
}

/* Body-text word replaced by the eclectic-text swap */
.eclectic-swap {
    color: #2d7a3e;
    font-weight: 600;
}

/* Sotah display panel */
.sotah-panel .panel-title {
    font-weight: 600;
    font-size: 0.9em;
    margin-bottom: 4px;
    color: #3a2e20;
}

.sotah-panel label {
    display: flex;
    align-items: center;
    gap: 6px;
    font-size: 0.85em;
    padding: 2px 0;
    cursor: pointer;
}

/* Sotah synoptic layout (two-col / marked): the aligned table stacks above
   the apparatus, which spans full width below it. */
.paragraph-pair.two-col-kiy {
    display: block;
}

.paragraph-pair.two-col-kiy > .variant-content,
.paragraph-pair.two-col-kiy > .hidden-variant-content {
    width: auto;
}

/* Synoptic table: one grid row per aligned segment so Vienna (right) and
   Erfurt (left) stay parallel line-to-line. */
.kiy-synoptic {
    margin-bottom: 10px;
    border: 1px solid #e0dbd4;
    border-radius: 4px;
    overflow: hidden;
}

.syn-row {
    display: grid;
    grid-template-columns: 1fr 1fr;
    column-gap: 24px;
    align-items: start;
    padding: 1px 10px;
}

.syn-row:nth-child(even) {
    background: #faf8f4;
}

/* Both columns share the Vienna body font/size for an exact match. */
.syn-v, .syn-e {
    font-family: 'Noto Serif Hebrew', serif;
    line-height: 1.7;
    color: #3a2e20;
}

.syn-e {
    border-right: 2px solid #e0dbd4;
    padding-right: 12px;
}

/* Marked coloring */
.syn-e.syn-match { color: #b8a890; }
.syn-e.syn-diff { color: #2d7a3e; font-weight: 600; }
.syn-v.syn-vonly { color: #2456a6; font-weight: 600; }

/* Notes mode: Erfurt-derived notes merged into the apparatus column */
.note-span.erfurt-note .variant {
    color: #2d7a3e;
    font-weight: 700;
}

/* Collapsed כי"ע block in default-mode apparatus */
.kiy-block {
    background: #f7f4ef;
    border: 1px solid #e0dbd4;
    border-radius: 4px;
    padding: 6px 10px;
    margin: 4px 0;
    font-size: 0.92em;
}

.kiy-block > summary {
    cursor: pointer;
    font-weight: 600;
    color: #3a2e20;
}

.kiy-block > div {
    padding-top: 6px;
    border-top: 1px solid #e0dbd4;
    margin-top: 6px;
}

/* --- Sidebar tabs ---
   Two settings pages in one sidebar: the variants filters and the parallels
   filters. Styled as a segmented strip rather than as document tabs, because
   the pane below them is a stack of bordered filter boxes and a second row of
   borders butting into it read as clutter. */
.sidebar-tabs {
    display: flex;
    gap: 4px;
    margin-bottom: 12px;
    padding: 3px;
    background: #f2eee7;
    border: 1px solid #e0dbd4;
    border-radius: 6px;
}

.sidebar-tab {
    flex: 1;
    padding: 6px 8px;
    font-family: inherit;
    font-size: 0.85em;
    font-weight: 600;
    color: #6b5b47;
    background: transparent;
    border: none;
    border-radius: 4px;
    cursor: pointer;
    transition: background 0.15s, color 0.15s;
}

.sidebar-tab:hover {
    background: #e7e1d7;
}

.sidebar-tab.active {
    background: #fff;
    color: #3a2e20;
    box-shadow: 0 1px 2px rgba(58, 46, 32, 0.12);
}

/* A single visible tab is not a choice -- it's a label with a border around
   it. Only shown once the tractate has parallels to filter. */
.sidebar-tabs:has(.sidebar-tab[hidden]) {
    display: none;
}

/* --- Panel actions (below the divider) --- */
/* Leaving the page and producing a file are not filters, so they sit apart from
   them: one rule, and rows that read as a menu rather than as more settings. */
.sidebar-actions {
    display: flex;
    flex-direction: column;
    gap: 2px;
    margin-top: 14px;
    padding-top: 10px;
    border-top: 1px solid #e0dbd4;
    /* Pinned to the foot of the panel rather than sitting at the end of the
       filter list, which on a long tractate is several screens down inside the
       scroll. Still visibly below the divider -- it just travels with the
       viewport instead of the content. The negative offset and matching padding
       cancel .sidebar's own bottom padding, so the strip reaches the panel's
       edge and nothing shows through beneath it. */
    position: sticky;
    bottom: -14px;
    margin-bottom: -14px;
    padding-bottom: 14px;
    background: #fff;
    /* So filters scrolling underneath read as passing behind an edge rather
       than being cut off mid-row. */
    box-shadow: 0 -6px 10px -6px rgba(58, 46, 32, 0.16);
}

.sidebar-action {
    display: flex;
    align-items: center;
    gap: 8px;
    width: 100%;
    padding: 7px 8px;
    font-family: inherit;
    font-size: 0.9em;
    text-align: start;
    color: #4a3f30;
    text-decoration: none;
    background: transparent;
    border: none;
    border-radius: 5px;
    cursor: pointer;
    transition: background 0.15s, color 0.15s;
}

.sidebar-action:hover {
    background: #f2eee7;
    color: #2c2317;
}

/* The Word mark keeps its own blue -- it names an external format rather than
   this site's palette -- but it is now a small leading badge on a labelled row
   instead of the whole button, so the row can say what it does in words. */
.sidebar-actions .nav-export {
    color: #4a3f30;
}

.sidebar-actions .nav-export:hover {
    background: #f2eee7;
    color: #2c2317;
}

.nav-export-mark {
    display: inline-flex;
    align-items: baseline;
    gap: 1px;
    flex-shrink: 0;
    padding: 2px 5px;
    border: 1px solid #2b579a;
    border-radius: 3px;
    color: #2b579a;
    font-family: 'Segoe UI', Arial, sans-serif;
    font-weight: 700;
    line-height: 1;
}

/* Parallels filter panel (sidebar, second tab) */
.parallels-panel-options .panel-title {
    font-weight: 600;
    font-size: 0.9em;
    margin-bottom: 4px;
    color: #3a2e20;
}

.parallels-panel-options {
    margin-bottom: 10px;
}

/* An option that does not apply in the current mode (the sub-unit split outside
   band mode) is dimmed in place rather than removed, so the pane doesn't change
   shape under the reader as they move between the three modes. */
.parallels-panel-options label:has(input:disabled) {
    opacity: 0.45;
    cursor: default;
}

/* Ties the sidebar row to the gutter bar it governs: same colour, same
   meaning. 4px is what a bar gets, so that's what the swatch gets. */
.parallel-filter-swatch {
    display: inline-block;
    width: 4px;
    height: 12px;
    border-radius: 1px;
    flex-shrink: 0;
}

.filters-section .filter-note {
    font-size: 0.76em;
    line-height: 1.4;
    color: #8b7d6b;
    margin-bottom: 4px;
    white-space: normal;
}

/* The filter rows carry work names and source names, which are longer than the
   sigla the variants panel deals in -- they wrap rather than overflow. */
.filters-section label[data-filter-row] {
    white-space: normal;
    align-items: flex-start;
    line-height: 1.35;
}

.filters-section label[data-filter-row] input[type="checkbox"] {
    margin-top: 2px;
}

.parallels-filter-reset {
    font-family: inherit;
    font-size: 0.8em;
    color: #6b5b47;
    background: #fff;
    border: 1px solid #d8d2c8;
    border-radius: 4px;
    padding: 4px 10px;
    cursor: pointer;
}

.parallels-filter-reset:hover {
    background: #f0ece4;
}

/* Witness-transcription panel (sidebar) */
.witness-panel .panel-title {
    font-weight: 600;
    font-size: 0.9em;
    margin-bottom: 4px;
    color: #3a2e20;
}

.witness-panel label {
    display: flex;
    align-items: center;
    gap: 6px;
    font-size: 0.85em;
    padding: 2px 0;
    cursor: pointer;
}

/* Alternate chapter/halakhah numbering overlay (Vilna / Lieberman-Zuckermandel)
   -- a distinct blue-grey rather than the warm brown/red used by the
   apparatus sup-note system, so the two overlays never read as the same
   kind of thing. Only the schemes that actually differ from our own
   chapter/halakhah grid in the loaded tractate get a visible checkbox. */
.numbering-panel .panel-title {
    font-weight: 600;
    font-size: 0.9em;
    margin-bottom: 4px;
    color: #3a2e20;
}

.numbering-panel label {
    display: flex;
    align-items: center;
    gap: 6px;
    font-size: 0.85em;
    padding: 2px 0;
    cursor: pointer;
    color: #4a6b7a;
}

/* Full witness-text strips shown below a halakha's apparatus */
.witness-strips {
    margin-top: 6px;
    border-top: 1px dashed #e0dbd4;
    padding-top: 6px;
}

.witness-strip {
    display: flex;
    align-items: baseline;
    gap: 8px;
    font-family: 'Noto Serif Hebrew', serif;
    line-height: 1.7;
    color: #3a2e20;
    padding: 1px 0;
}

.witness-strip-label {
    flex: none;
    font-weight: 700;
    color: #7a6a52;
    min-width: 1.2em;
    text-align: center;
}

.witness-word {
    color: inherit;
}

.witness-gap {
    color: #b8a890;
    font-style: italic;
}

/* "Plus" material: words a witness has with no base-text counterpart
   (offline-pipeline `additions`). Blue, not the diff-green, so it reads as
   "extra material" rather than "variant of an existing word". */
.witness-plus {
    color: #1d5c8f;
    font-weight: 600;
}

/* General multi-witness synopsis (non-Sotah tractates), built directly from
   Witnesses_<Tractate>.json's aligned words. A real <table>: one row per
   source (base text, then each witness), one column per word position, so
   word N sits at the same horizontal spot in every row (table columns
   auto-size to their widest cell across all rows) and the whole block
   scrolls horizontally as a word-by-word strip. The label column is sticky
   so it stays visible while the words scroll underneath it. */
.witness-synopsis-scroll {
    overflow-x: auto;
    margin-bottom: 16px;
    border: 1px solid #e0dbd4;
    border-radius: 4px;
}

.witness-synopsis {
    border-collapse: separate;
    border-spacing: 0;
    direction: rtl;
}

.syn-strip td {
    font-family: 'Noto Serif Hebrew', serif;
    line-height: 1.8;
    color: #3a2e20;
    white-space: nowrap;
    padding: 4px 8px;
    border-bottom: 1px dashed #ece6da;
}

.syn-strip:last-child td {
    border-bottom: none;
}

.syn-strip-base td {
    font-weight: 600;
    background: #f5f0e6;
}

.syn-strip-label {
    position: sticky;
    right: 0;
    z-index: 1;
    font-weight: 700;
    color: #7a6a52;
    text-align: center;
    background: #fffdf9;
    border-left: 1px solid #e0dbd4;
}

.syn-strip-base .syn-strip-label {
    background: #f5f0e6;
}

/* Which physical fragment the ג row is quoting here: the catalogue's codex
   siglum (G14, E5), hung off the witness siglum. Deliberately quiet -- it
   qualifies the siglum, it is not a second witness -- with the full shelfmark
   in the label's tooltip. */
.syn-frag-siglum {
    margin-right: 2px;
    font-size: 0.62em;
    font-weight: 600;
    letter-spacing: 0;
    color: #a08a63;
    cursor: help;
}

.synw-match {
    color: #b8a890;
}

/* Three tones over one hue, graded by classifyVariantPair's category (see
   synopsisDiffClasses): the eye should be able to skim a strip and land on the
   substantive readings without the habitual swaps competing for attention.
   `.synw-diff` alone keeps the old middle weight for any caller that has not
   picked a tone. */
.synw-diff {
    color: #2d7a3e;
    font-weight: 600;
}

/* Spelling and rabbi-name shapes: the same word, written differently. Barely
   louder than a match -- visible on inspection, invisible when skimming. */
.synw-diff-minor {
    color: #7d9b84;
    font-weight: 400;
}

/* Habitual swap, prefix, word order, inflection, citation scope. */
.synw-diff-routine {
    color: #4a8a5c;
    font-weight: 500;
}

/* A different word. */
.synw-diff-major {
    color: #1c6b2e;
    font-weight: 700;
}

.synw-gap {
    color: #b8a890;
    font-style: italic;
}

/* Multiword abbreviation ("fold"): the witness wrote one contracted word
   (רשב"ג, ע"ג, בד"א) where the base has several. The word sits in the anchor
   cell and the base positions it covers continue it -- so they must NOT show
   the ⟨ ⟩ that means "this witness lacks the word". A tinted box across the
   pair, with a leader line carrying the eye from the abbreviation to the base
   words it stands for. */
.witness-synopsis td.synw-fold,
.witness-synopsis td.synw-fold-cont {
    background: #f6f1e3;
    border-top: 1px solid #d3c393;
    border-bottom: 1px solid #d3c393;
}

.witness-synopsis td.synw-fold {
    border-right: 1px solid #d3c393;
}

.witness-synopsis td.synw-fold-last {
    border-left: 1px solid #d3c393;
}

.witness-synopsis td.synw-fold-cont {
    background-image: linear-gradient(to left, #b8a061 0 100%);
    background-size: 100% 1px;
    background-position: center;
    background-repeat: no-repeat;
}

/* Substitution: the witness replaces the base material at these positions
   (see substitutionsFor). Same blue as a plus -- it is unaligned witness
   material either way -- but boxed as one continuous span across the base
   columns it stands in for, because the word-to-column layout inside the run
   is presentational and must not read as a word-for-word pairing. */
.witness-synopsis td.synw-subst {
    color: #1d5c8f;
    font-weight: 600;
    background: #eef4fa;
    border-top: 1px solid #9fc0dd;
    border-bottom: 1px solid #9fc0dd;
}

.witness-synopsis td.synw-subst-first {
    border-right: 1px solid #9fc0dd;
}

.witness-synopsis td.synw-subst-last {
    border-left: 1px solid #9fc0dd;
}

/* Not extant: a fragmentary witness (ג) whose parchment does not cover this
   base position. Deliberately wordless -- a hatch, not a marker -- so it can
   never be misread as the ⟨ ⟩ that means "this witness lacks the word". */
.witness-synopsis td.synw-absent {
    background: repeating-linear-gradient(135deg,
        #f0ece4 0, #f0ece4 2px, #fffdf9 2px, #fffdf9 5px);
}

/* "Plus" column: a witness's extra words with no base-text counterpart
   (offline-pipeline `additions`), rendered as an inserted column after the
   base position they follow. Blue, not the diff-green used for variants of
   an existing base word, so plusses read as "extra material" instead. */
/* `.synw.` (repeating the base class) beats the `.syn-strip td` rule above
   on specificity, same trick `.synw.synw-active` already relies on. */
.synw.synw-plus {
    color: #1d5c8f;
    font-weight: 600;
    background: #eef4fa;
}

/* Same inserted column, for rows (including the base row) that have nothing
   there -- kept quiet so it doesn't compete with the plus cell beside it. */
.synw.synw-plusgap {
    background: #faf7f1;
}

/* Any cell that resolves to a base position is clickable (scrolls the running
   text, drives the manuscript viewer). Plus/addition cells now carry their
   anchor's base index too, so this affordance covers them; empty plusgap
   cells have no data-base-idx and stay non-interactive. */
.synw[data-base-idx] {
    cursor: pointer;
}
.synw[data-base-idx]:hover {
    outline: 1px solid #d8b96a;
    outline-offset: -1px;
}

/* Highlighted word ("column") synced from a clicked word/marker/apparatus note */
.synw.synw-active {
    background: #fdf1d8;
    outline: 2px solid #d8a94a;
    outline-offset: -2px;
}

/* "Ghost" cell: a witness word/plus that the offline pipeline aligned here
   (same base-word position as every other row) but which the manuscript
   actually places elsewhere (see `displaced` in Witnesses_<Tractate>.json).
   Hollow letters on pale pink -- the word is still legible enough to check,
   but visibly "not really here". Slightly larger + bolder than a normal
   synopsis cell since an outlined glyph reads thinner than a filled one at
   the synopsis's small font size. */
.witness-synopsis td.synw-ghost {
    background: #fdeef2;
    color: transparent;
    font-size: 1.05em;
    font-weight: 600;
    -webkit-text-stroke: 0.85px #a84a63;
    paint-order: stroke fill;
}

/* Browsers without text-stroke support (non-WebKit-family) would otherwise
   render fully invisible text -- fall back to plain (but still distinctly
   pink) solid-colored text. */
@supports not (-webkit-text-stroke: 1px black) {
    .witness-synopsis td.synw-ghost {
        color: #c2748a;
        background: #fdeef2;
    }
}

/* Persistent footer panels: synopsis + manuscript viewer, side by side.
   Each is a flex child with no width of its own -- flexbox alone gives a
   lone visible panel the full row and splits it 50/50 when both are open. */
.bottom-panels {
    position: fixed;
    bottom: 0;
    left: 0;
    right: 0;
    z-index: 500;
    display: flex;
    flex-direction: row;
}

.synopsis-footer,
.bottom-panels .dock-region {
    flex: 1 1 0;
    min-width: 0;
    max-height: 42vh;
    display: flex;
    flex-direction: column;
    background: #fffdf9;
    border-top: 2px solid #d8ccb8;
    box-shadow: 0 -4px 16px rgba(0, 0, 0, 0.12);
}

.synopsis-footer + .dock-region {
    border-inline-start: 1px solid #d8ccb8;
}

.synopsis-footer[hidden],
.dock-region[hidden] {
    display: none;
}

/* Dock chrome comes from midrash-viewer-core; only the palette is ours, so the
   shared header/tabs match the hand-rolled synopsis footer beside it. */
.dock-region.mvc-dock {
    --mvc-dock-bg: #fffdf9;
    --mvc-dock-border: #d8ccb8;
    --mvc-dock-header-bg: #f5f0e6;
    --mvc-dock-title-fg: #3a2e20;
    border: none;   /* the region already draws its own border/shadow */
}

/* A layer's own header contribution (which witness and chapter is showing). */
.dock-position-label {
    font-weight: 600;
    color: #3a2e20;
    font-size: 0.9em;
}

/* Commentary dock: full height under the header, tall rather than wide (see the
   note in index.html), and pinned to the inline-END edge -- the opposite side
   from the filters sidebar and the perek/halakhah nav, which are the
   .page-layout flex children occupying the inline-start edge. Putting it here
   leaves the reading column between the controls and the commentary instead of
   burying the sidebar underneath a fixed panel. */
.side-dock {
    position: fixed;
    inline-size: min(30rem, 38vw);
    inset-block: var(--site-header-height, 3.5rem) 0;
    inset-inline-end: 0;
    z-index: 480;
    display: flex;
    flex-direction: column;
    background: #fffdf9;
    border-inline-start: 2px solid #d8ccb8;
    box-shadow: -4px 0 16px rgba(0, 0, 0, 0.1);
}

body.side-dock-open .main-content {
    margin-inline-end: min(30rem, 38vw);
}

/* Pin toggle in the commentary dock header: stops the panel following the
   reader's scroll position. Dimmed when off, so "following" reads as the
   normal state and pinning as the deliberate exception. */
.dock-pin {
    font: inherit;
    font-size: 0.95em;
    line-height: 1;
    padding: 0.15rem 0.35rem;
    cursor: pointer;
    background: transparent;
    border: 1px solid transparent;
    border-radius: 3px;
    opacity: 0.45;
    filter: grayscale(1);
}

.dock-pin:hover {
    opacity: 0.8;
    background: rgba(0, 0, 0, 0.06);
}

.dock-pin.active {
    opacity: 1;
    filter: none;
    border-color: #c9bda4;
    background: #f0e6d2;
}

/* Commentary panels: the shared core panel, in this site's palette. */
#side-dock .mvc-comm {
    --mvc-comm-fg: #2e2a22;
    --mvc-comm-muted: #7a6a52;
    --mvc-comm-rule: #eae4d8;
    --mvc-comm-accent: #8a5a2b;
    --mvc-comm-dh: #6b4423;
    --mvc-comm-active-bg: #fdf6e3;
    font-family: 'Noto Serif Hebrew', serif;
}

@media (max-width: 900px) {
    /* The register toggles come out of the תצוגות dropdown and sit directly in
       .bottom-tabbar here (index.html reparents the actual elements), because a
       dropdown reached from a bar that is already one tap away would be a tap
       for nothing. So the trigger goes, and its emptied panel with it. */
    .header-menu {
        display: none;
    }

    /* --site-header-height defaults to a single-row desktop measurement
       (3.5rem); the mobile header wraps to two or three rows instead (see
       .site-header's flex-wrap rule), so anchoring the dock to that value
       left its top third hidden behind -- but painted OVER, since the dock's
       z-index is higher -- the header's lower rows. Ignoring the variable and
       covering the full height (like a mobile sheet) sidesteps needing to
       track the header's real, variable height at all. */
    .side-dock {
        inline-size: 100vw;
        inset-block: 0 var(--bottom-tabbar-h, 0px);
    }

    body.side-dock-open .main-content {
        margin-inline-end: 0;
    }

    /* Same full-height-sheet treatment for the bottom docks, and -- the
       actual ask -- an even split between them instead of each being capped
       at a fixed 42vh regardless of how much of the screen is free. Stacked
       vertically rather than side-by-side row: at phone widths two panels
       sharing a row leaves neither wide enough to read comfortably. */
    /* top:0 gives the container a definite height so its (up to two) open
       children can split it evenly -- but that also makes it a full-screen
       box regardless of whether anything is actually open, silently
       swallowing clicks to the page underneath. pointer-events:none on the
       (usually empty) container, re-enabled on the children that actually
       render, keeps the hit-testing scoped to real content. */
    .bottom-panels {
        top: 0;
        bottom: var(--bottom-tabbar-h, 0px);
        flex-direction: column;
        pointer-events: none;
    }

    .synopsis-footer,
    .bottom-panels .dock-region {
        max-height: none;
        min-height: 0;
        flex: 1 1 0;
        pointer-events: auto;
    }

    .synopsis-footer + .dock-region {
        border-inline-start: none;
        border-top: 2px solid #d8ccb8;
    }

}

/* --- Mobile bottom tab bar ---------------------------------------------
   Holds the panel-toggle buttons (filters, TOC, synopsis, manuscript,
   commentary) below the responsive breakpoint, flat rather than behind the
   תצוגות dropdown -- a bar this reachable does not need a menu in front of it.
   index.html moves the actual button elements in here (see the bottom-tabbar
   script) rather than duplicating them, so this only needs to lay out whatever
   it's handed. */
.bottom-tabbar {
    display: none;
}

.bottom-tabbar[hidden] {
    display: none;
}

@media (max-width: 900px) {
    .bottom-tabbar {
        display: flex;
        position: fixed;
        inset-inline: 0;
        bottom: 0;
        z-index: 600;
        background: #fff;
        border-top: 1px solid #d8ccb8;
        box-shadow: 0 -2px 10px rgba(0, 0, 0, 0.08);
        block-size: var(--bottom-tabbar-h, 54px);
        padding-inline: env(safe-area-inset-right, 0px) env(safe-area-inset-left, 0px);
        padding-block-end: env(safe-area-inset-bottom, 0px);
    }

    .bottom-tabbar[hidden] {
        display: none;
    }

    /* Bigger, evenly-split touch targets -- these are the same button elements
       as in the תצוגות dropdown, just relocated, so their own rules
       (.nav-toggle-btn, .sidebar-toggle, .toc-toggle) still set colour and
       active state; only the layout changes here. The dropdown's own sizing rules
       are scoped as descendants of .header-dropdown and so stop applying the
       moment a button is reparented into this bar. */
    .bottom-tabbar > * {
        flex: 1 1 0;
        min-width: 0;
        height: 100%;
        border-radius: 0;
        border: none;
        border-inline-start: 1px solid #eee2cf;
        margin: 0;
    }

    .bottom-tabbar > *:first-child {
        border-inline-start: none;
    }
}

.synopsis-footer-header {
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 6px 14px;
    border-bottom: 1px solid #e0dbd4;
    background: #f5f0e6;
    flex: none;
}

.synopsis-footer-header button {
    background: none;
    border: 1px solid #c9bda4;
    border-radius: 4px;
    cursor: pointer;
    padding: 2px 10px;
    font-size: 0.95em;
    color: #3a2e20;
}

.synopsis-footer-header button:hover {
    background: #e9e1d1;
}

/* Key to the cell states, sitting between the footer's controls and the
   strips. Quiet by design -- it has to survive being read past. */
.synopsis-legend {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 4px 12px;
    padding: 4px 14px;
    border-bottom: 1px solid #e0dbd4;
    background: #fffdf9;
    font-size: 0.72em;
    color: #7a6a52;
    flex: none;
}

.synopsis-legend span {
    display: inline-flex;
    align-items: center;
    gap: 4px;
    white-space: nowrap;
}

.synopsis-legend-swatch {
    display: inline-block;
    width: 1.5em;
    height: 1em;
    border: 1px solid #d7d0c4;
    font-style: normal;
    font-size: 0.85em;
    line-height: 1;
    text-align: center;
}

.synopsis-legend .legend-gap {
    border-color: transparent;
    color: #b8a890;
    width: auto;
}

.synopsis-legend .legend-absent {
    background: repeating-linear-gradient(135deg,
        #f0ece4 0, #f0ece4 2px, #fffdf9 2px, #fffdf9 5px);
}

.synopsis-legend .legend-subst {
    background: #eef4fa;
    border-color: #9fc0dd;
}

.synopsis-legend .legend-plus {
    background: #eef4fa;
}

.synopsis-legend .legend-fold {
    background: #f6f1e3;
    border-color: #d3c393;
}

.synopsis-legend .legend-ghost {
    background: #fdeef2;
    border-color: #e3bcc7;
}

.synopsis-legend-sep {
    width: 1px;
    height: 1em;
    background: #e0dbd4;
}

.synopsis-footer-label {
    font-weight: 600;
    color: #3a2e20;
    font-size: 0.9em;
}

.synopsis-footer-toggle {
    display: flex;
    align-items: center;
    gap: 4px;
    font-size: 0.85em;
    color: #3a2e20;
    cursor: pointer;
    margin-inline-start: auto;
}

.synopsis-footer-close {
    font-weight: 700;
}

.synopsis-footer-body {
    overflow: auto;
    padding: 8px 14px 14px;
}

/* Host for the shared midrash-viewer-core panel, which brings its own
   scrolling viewport, zoom/pan and fullscreen -- so this element must NOT
   scroll or pad, only give the panel a box to fill. */
#manuscript-dock .mvc-dock-body,
#manuscript-dock .mvc-dock-pane {
    overflow: hidden;
    min-height: 0;
}

#manuscript-dock .mvc-ms {
    --mvc-accent: #8a5a2b;
    --mvc-border: #ddcdb4;
    --mvc-bg: #fffdf9;
    --mvc-fg: #5a4632;
    --mvc-muted: #a89880;
    --mvc-box: #d1453a;
}

.synopsis-footer-body .witness-synopsis-scroll {
    margin-bottom: 16px;
}

.synopsis-footer-body .synopsis-footer-halakha-label {
    font-weight: 600;
    color: #7a6a52;
    font-size: 0.85em;
    margin: 8px 0 4px;
}

/* Movement-order table ("Lieberman-style" order table): shown above the
   synopsis whenever the displayed halakha belongs to a witness's
   `displaced` cluster. One column per source (base text, then witness
   groups sharing an identical reading order); each row is one position in
   that source's reading order of the cluster's halakhot. */
.movement-table-scroll {
    overflow-x: auto;
    margin-bottom: 10px;
    border: 1px solid #e6cdd6;
    border-radius: 4px;
    background: #fffaf9;
}

.movement-table {
    border-collapse: separate;
    border-spacing: 0;
    direction: rtl;
    width: 100%;
}

.movement-table th,
.movement-table td {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.82em;
    white-space: nowrap;
    padding: 4px 10px;
    text-align: center;
    border-bottom: 1px dashed #e6cdd6;
    border-left: 1px solid #f0e3e7;
}

.movement-table th:last-child,
.movement-table td:last-child {
    border-left: none;
}

.movement-table tr:last-child td {
    border-bottom: none;
}

.movement-table th {
    background: #f7e9ed;
    color: #7a3a4a;
    font-weight: 700;
}

.movement-table td {
    color: #4a3a30;
}

/* A halakha that sits in a different row-position here than in the base
   column -- i.e. it moved for this source -- gets bold red text so the eye
   catches it against the (unchanged) pastel background it shares with its
   position in every other column. */
.movement-table td.movement-moved {
    color: #c0202e;
    font-weight: 700;
}

/* Manuscript page image + percentage-positioned highlight box (positions are
   computed as fractions of the page's known Sefaria pixel dimensions, so
   they're correct immediately without waiting on <img> natural size). */
/* Leave room so the fixed footer row never permanently covers content */
body.synopsis-footer-open .main-content,
body.manuscript-dock-open .main-content {
    padding-bottom: 42vh;
}

/* On mobile an open panel is a full-height sheet rather than a 42vh strip
   (see the .bottom-panels mobile rules), so reserve the whole scrollable
   height instead of an amount that no longer matches what's covering the
   content. Must come after the unscoped rule above to win the tie -- same
   specificity, later wins. */
@media (max-width: 900px) {
    body.synopsis-footer-open .main-content,
    body.manuscript-dock-open .main-content {
        padding-bottom: calc(100vh - var(--bottom-tabbar-h, 0px));
    }
}

/* Shrink the sticky TOC column by the same amount, so its bottom edge never
   sits underneath the fixed footer row either. The settings panel is not listed:
   it is an overlay with its own max-block-size, not a column, and it is opened
   and dismissed rather than left standing beside the footer. */
@media (min-width: 901px) {
    body.synopsis-footer-open .toc-nav,
    body.manuscript-dock-open .toc-nav {
        height: calc(100vh - 60px - 42vh);
    }
}

/* Indented child filters */
.filter-children {
    padding-right: 22px;
    display: flex;
    flex-direction: column;
    gap: 2px;
    margin-bottom: 2px;
}

/* Like filter-children, but independent of the parent — not dimmed when
   the parent checkbox is checked. Use for orthogonal render options
   that live under the same expand arrow (e.g. line break on פתוח). */
.filter-extra {
    padding-right: 22px;
    display: flex;
    flex-direction: column;
    gap: 2px;
    margin-bottom: 2px;
}

/* Dim children when parent category is checked (all hidden anyway) */
.filter-children.disabled {
    opacity: 0.4;
    pointer-events: none;
}

/* Detail reason slots (injected dynamically) */
.detail-slot:empty {
    display: none;
}

.detail-slot {
    display: flex;
    flex-direction: column;
    gap: 2px;
    margin-top: 2px;
    padding-top: 3px;
    border-top: 1px dashed #e0dbd4;
}

.detail-slot label {
    font-size: 0.8em;
    color: #6b5b47;
}

.detail-count {
    color: #a89880;
    font-size: 0.9em;
}

/* Expandable detail groups */
.detail-group {
    margin-bottom: 1px;
}

.detail-group-header {
    display: flex;
    align-items: center;
    gap: 2px;
}

.detail-group-header label {
    flex: 1;
}

.detail-expand {
    cursor: pointer;
    font-size: 0.7em;
    color: #a89880;
    padding: 2px 4px;
    border-radius: 3px;
    user-select: none;
    transition: color 0.15s;
    line-height: 1;
}

.detail-expand:hover {
    color: #6b5b47;
    background: #ece7de;
}

.detail-group-children {
    display: none;
    flex-direction: column;
    gap: 1px;
    padding-right: 20px;
    margin-top: 1px;
}

.detail-group-children.open {
    display: flex;
}

/* --- Status bar --- */
.status-bar {
    font-size: 0.82em;
    color: #6b5b47;
    padding: 8px 0 4px;
    text-align: start;
}

/* --- Main content area --- */
/* The 1100px reading cap lives on the card inside this column (see #app), not on
   the column itself. It used to be here, which worked only while the filters
   held a 280px column and left no slack behind it: once that became a dropdown,
   a capped flex item stopped short and stranded the leftover width at the
   inline-end edge, dragging what then stood there off the edge. Letting the
   column fill the row and capping the card keeps the measure without the gap. */
.main-content {
    flex: 1;
    min-width: 0;
    padding: 20px 24px 60px;
}

/* --- Card (shared style for sections) --- */
.card {
    background: #fff;
    border: 1px solid #e0dbd4;
    border-radius: 6px;
    padding: 16px 20px;
    margin-bottom: 16px;
}

/* The reading surface holds the measure, and centres whatever width is left
   over. The 1100px cap used to sit on .main-content, where it worked only
   because the filters column left no slack behind it; see the note there. */
#app {
    max-width: 1100px;
    margin: 0 auto;
}

#content-container {
    display: flex;
    flex-direction: column;
}

.chapter-header {
    font-family: 'Suez One', serif;
    font-size: 1.35em;
    font-weight: 400;
    text-align: center;
    margin: 28px 0 14px;
    color: #3a2e20;
    border-bottom: 1px solid #e0dbd4;
    padding-bottom: 8px;
    scroll-margin-top: 68px;
}

.paragraph-pair {
    scroll-margin-top: 68px;
    position: relative;
    display: flex;
    /* Wraps so an apparatus band can take a full-width line under the columns
       without either of them being restructured: the band is just a flex child
       at 100%, and which register occupies the column above it is decided by
       whoever put it there. */
    flex-wrap: wrap;
    justify-content: space-between;
    padding-right: 36px;
    margin-bottom: 12px;
    gap: 20px;
}

/* The apparatus that is not holding the column beside the text. Same rule and
   the same label treatment whichever register it is, because the arrangement is
   the reader's choice and neither position is a demotion. */
.apparatus-band {
    width: 100%;
    margin-top: 10px;
    padding-top: 7px;
    border-top: 1px solid #ece5d8;
}

.apparatus-band-label {
    font-size: 0.72em;
    letter-spacing: 0.04em;
    color: #a2937c;
    margin-bottom: 4px;
}

.apparatus-band-variants .variant-content {
    width: 100%;
}

/* In the band the citations run as a wrapped row rather than a tall column:
   below the text there is width to spare and no reason to make the halakhah
   twice as tall as it needs to be. */
.apparatus-band-parallels .parallel-group {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: 4px 10px;
    margin-bottom: 4px;
}

.apparatus-band-parallels .parallel-group-title {
    margin: 0;
    flex: 0 0 auto;
}

.apparatus-band-parallels .parallel-row {
    flex: 0 1 auto;
}

/* An opened passage needs the whole width back. */
.apparatus-band-parallels .parallel-row.open {
    flex: 1 1 100%;
}

.paragraph-number {
    position: absolute;
    right: 0;
    top: 0;
    font-weight: bold;
    color: #a89880;
    font-size: 0.9em;
    min-width: 28px;
    text-align: center;
}

.text-content {
    width: 48%;
}

.variant-content,
.hidden-variant-content {
    width: 48%;
    font-size: 0.93em;
    color: #444;
}

.hidden-variant-content {
    display: none;
    width: 0;
}

/* When "show hidden" is on, go to 3-column */
.show-hidden .text-content {
    width: 34%;
}

.show-hidden .variant-content {
    width: 33%;
}

.show-hidden .hidden-variant-content {
    width: 33%;
}

/* --- Note rendering (compact inline) --- */
.note-sep {
    display: inline;
    color: #c5bdb1;
    margin: 0 1px;
}

.note-sv-echo {
    font-weight: bold;
    color: #999;
    font-size: 0.88em;
}

.note-affirming {
    font-size: 0.88em;
    color: #6b5b47;
}

.variant {
    font-family: Arial, sans-serif;
    font-weight: bold;
}

sup {
    color: #b84c3e;
    font-weight: 600;
}

/* --- Sup <-> note linking --- */
sup.note-ref {
    cursor: pointer;
    transition: background 0.15s;
    border-radius: 2px;
    padding: 0 1px;
}

sup.note-ref:hover,
sup.note-ref.highlight {
    background: #fce4b8;
}

.note-span {
    transition: background 0.15s;
    border-radius: 2px;
    padding: 0 1px;
}

.note-span.highlight {
    background: #fce4b8;
}

/* Dimmer highlight in the hidden column */
.hidden-variant-content .note-span.highlight {
    background: #f0e4cd;
}

/* Main-text word highlighted from clicking its column in the synopsis footer */
.body-word.highlight {
    background: #fce4b8;
    border-radius: 2px;
}

/* --- Responsive --- */
@media (max-width: 900px) {
    /* Height of the fixed bottom-tabbar (see far below); referenced by the
       docks so they leave room for it instead of sitting underneath it. Set
       on body rather than :root purely by convention with the other
       mobile-only state classes living on body in this file. */
    body {
        --bottom-tabbar-h: 54px;
    }

    /* Same dropdown, widened to the screen: at phone widths a 320px panel
       inset from one edge looks like a mistake, and there is nothing beside it
       worth leaving visible. The off-canvas drawer this used to be is gone --
       the dropdown behaves identically at every width now, which is what
       collapsed two open/close paths into one (see index.html). */
    .sidebar {
        inset-inline: 8px;
        inline-size: auto;
        max-inline-size: none;
        /* Clear of the bottom tab bar, which is above the panel and holds the
           controls for the docks. */
        max-block-size: calc(100vh - var(--site-header-height, 3.5rem)
                             - var(--bottom-tabbar-h, 0px) - 20px);
    }

    /* Dimmed here, unlike on desktop: the panel covers most of the screen, so
       the page behind it genuinely is out of use while it's open. */
    .sidebar-overlay {
        background: rgba(0, 0, 0, 0.3);
    }

    /* The perek/halakhah TOC has no room for its own sticky column on a
       phone, so it becomes an off-canvas drawer -- opened from the bottom tab
       bar (#toc-toggle), sliding in from the inline-end edge, the opposite one
       to the settings dropdown's anchor, so the two are never visually
       confused. JS toggles .open on only one of the two at a time; see
       closeDrawers/toggleSidebar/toggleTocNav in index.html. */
    .toc-nav {
        display: block;
        position: fixed;
        top: 0;
        left: 0;
        height: 100vh;
        width: 200px;
        z-index: 150;
        background: #fdfcfa;
        box-shadow: 4px 0 16px rgba(0,0,0,0.12);
        transform: translateX(-100%);
        transition: transform 0.3s ease;
        padding: 66px 6px 16px;
    }

    .toc-nav.open {
        transform: translateX(0);
    }

    .main-content {
        padding: 16px 12px 40px;
    }

    .site-header {
        flex-wrap: wrap;
    }

    .site-header h1 {
        font-size: 1.2em;
    }

    /* The selector row (label + <select> + button + edition-note) is wider
       than a phone screen as a single nowrap line -- wrap it, and let the
       edition-note pill wrap its own text instead of forcing width. Without
       this the row was overflowing the viewport by ~160px (see the pill's
       long edition names), dragging the whole page into horizontal scroll. */
    .masechet-selector {
        flex-wrap: wrap;
    }

    .masechet-selector select {
        max-width: 140px;
    }

    .edition-note {
        white-space: normal;
        max-width: 100%;
    }

    .paragraph-pair {
        flex-direction: column;
        padding-right: 30px;
        gap: 4px;
    }

    .text-content,
    .variant-content,
    .hidden-variant-content {
        width: 100% !important;
    }

    .show-hidden .text-content,
    .show-hidden .variant-content,
    .show-hidden .hidden-variant-content {
        width: 100% !important;
    }


}

/* =============================================
   DataTables Academic Theme Overrides
   (for otzarHaHilufim page)
   ============================================= */

/* RTL layout for DataTables wrapper */
.dataTables_wrapper {
    direction: rtl;
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.88em;
}

/* Search + length menu */
.dataTables_filter,
.dataTables_length {
    margin-bottom: 10px;
}

.dataTables_filter input,
.dataTables_length select {
    font-family: 'Noto Serif Hebrew', serif;
    border: 1px solid #c5bdb1;
    border-radius: 4px;
    padding: 4px 8px;
    background: #fff;
}

/* Table styling */
table.dataTable {
    border-collapse: collapse !important;
}

table.dataTable thead th {
    background: #f7f4ef;
    color: #3a2e20;
    font-weight: 600;
    border-bottom: 2px solid #d4c9b8;
    text-align: right;
    padding: 8px 10px;
}

table.dataTable tbody td {
    border-bottom: 1px solid #e8e3dc;
    padding: 7px 10px;
    text-align: right;
    vertical-align: top;
}

table.dataTable tbody tr:hover {
    background: #f7f4ef !important;
}

table.dataTable tbody tr.odd {
    background: #fff;
}

table.dataTable tbody tr.even {
    background: #fdfcfa;
}

/* Pagination */
.dataTables_paginate {
    margin-top: 12px;
}

.dataTables_paginate .paginate_button {
    border: 1px solid #e0dbd4 !important;
    border-radius: 3px;
    margin: 0 2px;
    background: #fff !important;
    color: #6b5b47 !important;
}

.dataTables_paginate .paginate_button.current {
    background: #8b7d6b !important;
    color: #fff !important;
    border-color: #8b7d6b !important;
}

.dataTables_paginate .paginate_button:hover {
    background: #f7f4ef !important;
    color: #3a2e20 !important;
}

/* Info text */
.dataTables_info {
    color: #6b5b47;
    font-size: 0.9em;
    padding-top: 8px;
}

/* Sorting arrows */
table.dataTable thead .sorting::after,
table.dataTable thead .sorting_asc::after,
table.dataTable thead .sorting_desc::after {
    opacity: 0.5;
}

/* --- Filter mode toggle --- */
.filter-mode-toggle {
    display: flex;
    gap: 4px;
    padding: 8px 10px;
    border-bottom: 1px solid #e0dbd4;
    margin-bottom: 6px;
}

.filter-mode-toggle .mode-label {
    font-size: 0.82em;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 4px;
    color: #6b5b47;
    padding: 3px 6px;
    border-radius: 4px;
    transition: background 0.15s;
}

.filter-mode-toggle .mode-label:has(input:checked) {
    background: #ece7de;
    color: #3a2e20;
    font-weight: 600;
}

.filter-mode-toggle input[type="radio"] {
    width: 14px;
    height: 14px;
    accent-color: #8b7d6b;
}

/* --- Row detail section --- */
#row-detail-section {
    font-size: 0.92em;
}

#row-detail-section h3 {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 1.1em;
    color: #3a2e20;
    margin: 0 0 10px;
    padding-bottom: 8px;
    border-bottom: 1px solid #e0dbd4;
}

/* --- Witness columns in otzar table --- */
.witness-col {
    min-width: 32px;
    max-width: 48px;
    font-size: 0.85em;
    text-align: center !important;
}

table.dataTable thead th.witness-col {
    padding: 8px 4px;
    text-align: center;
}

/* --- Column search bar --- */
.search-bar-section {
    padding: 12px 16px !important;
    margin-bottom: 12px;
}

.column-search-row {
    display: flex;
    gap: 16px;
    flex-wrap: wrap;
}

.search-field {
    flex: 1;
    min-width: 150px;
    display: flex;
    flex-direction: column;
    gap: 4px;
}

.search-field label {
    font-size: 0.82em;
    font-weight: 600;
    color: #3a2e20;
}

.search-field input {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.9em;
    padding: 6px 10px;
    border: 1px solid #c5bdb1;
    border-radius: 4px;
    background: #fff;
    color: #2c2c2c;
    transition: border-color 0.2s;
}

.search-field input[type="text"]:focus {
    outline: none;
    border-color: #8b7d6b;
    box-shadow: 0 0 0 2px rgba(139, 125, 107, 0.15);
}

.search-field-narrow {
    flex: 0.7;
}

.search-field-toggle {
    flex: 0 0 auto;
    min-width: auto;
    justify-content: flex-end;
}

.search-option {
    font-size: 0.82em;
    color: #6b5b47;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 4px;
    white-space: nowrap;
    padding-top: 20px;
}

.search-option input[type="checkbox"] {
    accent-color: #8b7d6b;
}

/* --- Context modal --- */
.modal-overlay {
    display: none;
    position: fixed;
    inset: 0;
    background: rgba(0, 0, 0, 0.45);
    z-index: 500;
    justify-content: center;
    align-items: flex-start;
    padding-top: 60px;
    overflow-y: auto;
}

.modal-overlay.visible {
    display: flex;
}

.modal-content {
    background: #fff;
    border-radius: 8px;
    max-width: 720px;
    width: 90%;
    max-height: calc(100vh - 100px);
    overflow-y: auto;
    padding: 24px 28px;
    position: relative;
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.2);
    direction: rtl;
    font-family: 'Noto Serif Hebrew', serif;
    margin-bottom: 40px;
}

.modal-close {
    position: absolute;
    top: 12px;
    left: 16px;
    background: none;
    border: none;
    font-size: 1.6em;
    cursor: pointer;
    color: #6b5b47;
    line-height: 1;
    padding: 4px 8px;
    border-radius: 4px;
    transition: background 0.15s;
}

.modal-close:hover {
    background: #ece7de;
}

.modal-content h3 {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 1.15em;
    color: #3a2e20;
    margin: 0 0 12px;
    padding-bottom: 10px;
    border-bottom: 1px solid #e0dbd4;
}

.modal-summary {
    font-size: 0.88em;
    color: #6b5b47;
    margin-bottom: 8px;
}

.modal-reasons {
    font-size: 0.85em;
    color: #444;
    margin-bottom: 16px;
    padding-bottom: 12px;
    border-bottom: 1px solid #e8e3dc;
}

.modal-loading {
    text-align: center;
    padding: 24px;
    color: #a89880;
    font-size: 0.92em;
}

.modal-context-item {
    margin-bottom: 16px;
    padding-bottom: 14px;
    border-bottom: 1px dashed #e8e3dc;
}

.modal-context-item:last-child {
    border-bottom: none;
}

.modal-context-ref {
    font-weight: 600;
    color: #3a2e20;
    font-size: 0.9em;
    margin-bottom: 6px;
}

.modal-context-text {
    font-size: 0.92em;
    line-height: 1.7;
    color: #2c2c2c;
    margin-bottom: 6px;
}

.modal-context-text mark {
    background: #fce4b8;
    padding: 1px 3px;
    border-radius: 2px;
}

.modal-context-variants {
    margin-top: 6px;
    padding: 6px 10px;
    background: #faf8f5;
    border-radius: 4px;
    border: 1px solid #e8e3dc;
}

.modal-variant-note {
    font-size: 0.85em;
    margin-bottom: 3px;
    color: #444;
}

.modal-sv {
    font-weight: 600;
    color: #3a2e20;
}

.modal-var {
    color: #b84c3e;
    font-weight: 600;
}

.modal-wit {
    color: #6b5b47;
    font-size: 0.9em;
}

.modal-more {
    text-align: center;
    color: #a89880;
    font-size: 0.85em;
    padding-top: 8px;
}

/* --- Full ref listing in modal --- */
.modal-all-refs {
    margin-top: 16px;
    padding-top: 12px;
    border-top: 1px solid #e0dbd4;
}

.modal-all-refs-header {
    font-weight: 600;
    font-size: 0.9em;
    color: #3a2e20;
    margin-bottom: 8px;
}

.modal-all-refs-list {
    display: flex;
    flex-wrap: wrap;
    gap: 6px 16px;
    font-size: 0.84em;
    color: #444;
    line-height: 1.6;
}

.modal-ref-group {
    white-space: nowrap;
}

/* --- Witness cell clickable hint --- */
td.witness-col {
    transition: background 0.1s;
}

td.witness-col:hover {
    background: #ece7de !important;
}

/* --- Parallels layer -------------------------------------------------------
   Two halves, styled together: the extent bars in a gutter down the inline-end
   edge of the reading column, and the citation panel in the side dock. */

/* The gutter lives inside .text-content's own inline-end padding rather than in
   the gap between the text and apparatus columns: the gap is 20px and a chapter
   can want five lanes, and stealing it would let the bars collide with the
   apparatus text. Reserving padding instead means the column narrows by exactly
   what the bars need, and only while the layer is on. */
.text-content {
    position: relative;
}

body.parallel-extents-on .text-content {
    padding-inline-end: calc(6px + var(--parallel-lanes, 1) * 7px);
}

.parallel-gutter {
    position: absolute;
    inset-block: 0;
    inset-inline-end: 0;
    inline-size: calc(var(--parallel-lanes, 1) * 7px);
    pointer-events: none;
}

.parallel-bar {
    position: absolute;
    inset-inline-end: calc(var(--parallel-lane, 0) * 7px);
    inline-size: 4px;
    padding: 0;
    border: 0;
    border-radius: 2px;
    background: var(--parallel-color, #8a7a63);
    opacity: 0.5;
    cursor: pointer;
    pointer-events: auto;
    transition: opacity 0.12s, inline-size 0.12s;
}

.parallel-bar:hover,
.parallel-bar.focused,
.parallel-bar.open {
    opacity: 1;
    inline-size: 6px;
}

/* A bar clipped at a paragraph boundary loses its cap on that side, so a
   parallel running through three halakhot reads as one extent interrupted by the
   layout rather than as three separate parallels. */
.parallel-bar.continues-above {
    border-start-start-radius: 0;
    border-start-end-radius: 0;
}

.parallel-bar.continues-below {
    border-end-start-radius: 0;
    border-end-end-radius: 0;
}

/* Covered words get no styling of their own -- with a dozen overlapping
   parallels the text would be unreadable. Only the FOCUSED parallel's words are
   marked, and then only faintly. */
.body-word.parallel-focus {
    background: #eef3ea;
    box-shadow: 0 1px 0 #7c9a6a;
}

/* Subunit division: alternating tint plus a break mark, so the articulation the
   parallels imply is visible without renumbering anything. */
.parallel-subunit-break {
    display: inline-block;
    inline-size: 0.75em;
    color: #b5a68c;
    font-size: 0.8em;
    vertical-align: 0.15em;
}

.parallel-subunit-break::before {
    content: '❙';
}

.body-word[data-parallel-subunit="1"] {
    background: rgba(160, 140, 100, 0.07);
}

/* --- the dock panel --- */
.parallels-panel {
    display: flex;
    flex-direction: column;
    gap: 10px;
    padding: 10px 12px;
    overflow-y: auto;
}

.parallels-heading {
    font-family: 'Suez One', serif;
    font-size: 0.95em;
    color: #6b5b45;
    border-bottom: 1px solid #e0dbd4;
    padding-bottom: 6px;
}

.parallels-empty {
    color: #8a7a63;
    font-size: 0.9em;
    margin: 0;
}

/* What this panel is not showing, and where it went. */
.parallels-note {
    margin: 0;
    font-size: 0.8em;
    color: #9a8a70;
}

.parallel-group {
    display: flex;
    flex-direction: column;
    gap: 4px;
}

.parallel-group-title {
    margin: 6px 0 2px;
    font-size: 0.85em;
    font-weight: 600;
    color: var(--parallel-color, #6b5b45);
    border-inline-start: 3px solid var(--parallel-color, #6b5b45);
    padding-inline-start: 7px;
}

.parallel-row {
    border: 1px solid #e6e0d6;
    border-radius: 4px;
    background: #fffefb;
}

.parallel-row.focused {
    border-color: var(--parallel-color, #b5a68c);
    box-shadow: 0 0 0 2px rgba(120, 100, 70, 0.08);
}

.parallel-row-header {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 8px;
    inline-size: 100%;
    padding: 6px 9px;
    border: 0;
    background: none;
    cursor: pointer;
    text-align: start;
    font: inherit;
    color: #3a2e20;
}

.parallel-row-header:hover {
    background: #f7f3ea;
}

.parallel-ref {
    font-size: 0.95em;
}

.parallel-row-meta {
    display: flex;
    align-items: baseline;
    gap: 7px;
    flex: none;
}

.parallel-strength {
    color: #a89880;
    font-size: 0.6em;
    letter-spacing: 1px;
}

/* ועיין: what the edition called a comparison rather than a parallel. Named in
   the edition's own word, and quiet -- it qualifies the reference, it is not a
   warning about it. */
.parallel-compare {
    font-size: 0.72em;
    color: #8a7a62;
    white-space: nowrap;
    border: 1px solid #ded3c0;
    border-radius: 3px;
    padding: 0 3px;
}

/* Precision is shown only when it is WORSE than a measured span -- the absence
   of this label is what "we located the extent" looks like. */
.parallel-precision {
    font-size: 0.72em;
    color: #9a8a70;
    white-space: nowrap;
}

.parallel-row-body {
    padding: 2px 9px 8px;
    border-top: 1px solid #f0ebe1;
}

.parallel-dh {
    font-weight: 600;
    font-size: 0.9em;
    color: #6b5b45;
    margin-bottom: 4px;
}

.parallel-passage {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.95em;
    line-height: 1.75;
    color: #3a2e20;
    max-block-size: 22em;
    overflow-y: auto;
}

/* --- note mode: the apparatus as printed ---------------------------------
   Set as running prose, not as a list of rows: the note is a sentence, and the
   references are words in it. Everything below is about keeping that true while
   still letting four kinds of reference be told apart at a glance. */
.apparatus-note {
    border-bottom: 1px solid #f2ede4;
    padding: 7px 9px;
}
.apparatus-note:last-child { border-bottom: none; }

.apparatus-note-line {
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.92em;
    line-height: 1.85;
    color: #3a2e20;
    margin: 0;
}

.apparatus-note-lemma {
    font-weight: 700;
    color: #6b4c2a;
}

/* A reference the reader can act on. Deliberately not a button-looking button:
   it sits inside a sentence, so it is marked the way a citation is marked in
   print -- a coloured underline -- and grows a background only under the
   pointer. */
.apparatus-ref {
    font: inherit;
    color: inherit;
    padding: 0 1px;
    border: none;
    background: none;
}

.apparatus-ref-live,
.apparatus-ref-link {
    cursor: pointer;
    color: #1f4f78;
    text-decoration: underline;
    text-decoration-color: #a8c4dc;
    text-underline-offset: 2px;
    border-radius: 3px;
}
.apparatus-ref-live:hover,
.apparatus-ref-link:hover,
.apparatus-ref-live.focused {
    background: #e8f0f7;
    text-decoration-color: #1f4f78;
}
.apparatus-ref-live.open {
    background: #dce8f3;
    font-weight: 600;
}

/* A ועיין reference inside a note: still live, still opens the passage, but the
   underline is dashed, so a pointer to compare does not read on the page as an
   asserted parallel. */
.apparatus-ref-compare {
    text-decoration-style: dashed;
}

/* Recognised, unplaceable: the midrashic works, which the parser can name but
   not address. Dotted rather than solid, and inert -- the reader should see
   that Lieberman cited it and that we cannot take them there. */
.apparatus-ref-unplaceable {
    color: #7a6a52;
    text-decoration: underline dotted;
    text-decoration-color: #c4b49a;
    text-underline-offset: 2px;
    cursor: help;
}

/* Filtered out, and only visible at all because "הצג ציונים מסוננים" is on. */
.apparatus-ref-filtered {
    color: #a4998a;
    text-decoration: line-through;
    text-decoration-color: #cbbfae;
}

.apparatus-note-body {
    margin-top: 6px;
    border-top: 1px solid #f0ebe1;
    padding: 6px 0 0;
}

/* The aligned stretch against its context: the surrounding words are kept and
   dimmed rather than cut, because seeing what sits around the match is how a
   reader judges whether the alignment found the right passage. */
.parallel-aligned {
    background: #eef3ea;
    box-shadow: 0 1px 0 #7c9a6a;
}

.parallel-context {
    color: #9a8f80;
}

.parallel-passage-missing {
    font-family: inherit;
    font-size: 0.85em;
    color: #9a8a70;
    font-style: italic;
}

.parallel-row-footer {
    display: flex;
    justify-content: space-between;
    gap: 10px;
    margin-top: 7px;
    font-size: 0.8em;
    color: #7a6a52;
}

.parallel-cited {
    font-family: 'Noto Serif Hebrew', serif;
}

.parallel-sefaria-link {
    color: #2a5b8c;
    white-space: nowrap;
}

.parallel-sources {
    margin-top: 3px;
    font-size: 0.74em;
    color: #a89880;
    line-height: 1.5;
}

/* Narrow screens: the reading column has no room to give up, so the bars sit in
   the margin between the text and the screen edge instead of inside it. */
@media (max-width: 900px) {
    body.parallel-extents-on .text-content {
        padding-inline-end: 10px;
    }

    .parallel-gutter {
        inline-size: 8px;
    }

    .parallel-bar {
        inset-inline-end: calc(var(--parallel-lane, 0) * 3px);
        inline-size: 2px;
    }
}

/* --- Parallels beside the text ---------------------------------------------
   The reading mode the parallels apparatus actually wants: the citations take
   the column the variant apparatus normally holds, and each subunit of the
   halakhah sits level with the parallels claimed for it. The variants keep their
   place in the document -- they move to a collapsed block under the halakhah,
   not out of it. */

body.parallels-beside .paragraph-pair {
    display: block;
    padding-inline-end: 36px;
}

body.parallels-beside .text-content,
body.parallels-beside .variant-content {
    width: auto;
}

/* One grid row per subparagraph, so a citation -- and the passage it opens into --
   sits level with the words it belongs to. The list column is always there, since
   a subparagraph's citations are the first thing to read about it; what it does
   not always get is ROOM, and the widths below are the compromise: a narrow strip
   for closed citations, a real second column once a passage is open. Reserving
   half the measure for closed citations everywhere cost the whole chapter its
   readability -- four or five words to a line. */
.parallel-split {
    display: grid;
    grid-template-columns: 1fr minmax(7rem, 20%);
    column-gap: 16px;
    align-items: start;
}

.parallel-split:not(.has-cites) {
    grid-template-columns: 1fr;
}

/* Deliberately not transitioned: opening a passage scrolls it to its aligned
   words, and that measurement has to happen at the settled width. An animated
   grid-template-columns would have it measuring mid-flight. */
.parallel-split.has-open {
    grid-template-columns: 1fr minmax(15rem, 42%);
}

.parallel-split-row {
    display: grid;
    grid-column: 1 / -1;
    grid-template-columns: subgrid;
}

/* A subparagraph break is a paragraph break, so it is spaced like one rather than
   ruled like a table row. The breaks now land on the text's own punctuation (see
   snapToPause), which is what makes plain spacing legible: each block starts at a
   sentence or a clause, so the eye needs no line to be told where it began. */
.parallel-split-row + .parallel-split-row {
    margin-top: 0.5em;
}

.parallel-split-text {
    position: relative;
    font-family: 'Noto Serif Hebrew', serif;
    padding-inline-end: calc(var(--parallel-lanes, 0) * 7px);
}

.parallel-split-refs {
    display: flex;
    flex-direction: column;
    align-items: stretch;
    gap: 3px;
    min-width: 0;
    padding-top: 0.15em;
}

/* Covered words carry no permanent decoration: the bars in the gutter mark the
   extents, and underlining the runs as well left most of the chapter underlined at
   three weights, which reads as texture. They stay clickable, and say so on
   hover -- and light up when their citation is hovered or opened. */
.body-word.parallel-span {
    cursor: pointer;
}

.body-word.parallel-span:hover {
    background: #f3efe4;
}

/* --- the citation list in the near margin --- */
.parallel-cite-item {
    border-inline-start: 2px solid transparent;
    padding-inline-start: 5px;
    min-width: 0;
}

.parallel-cite-item.focused,
.parallel-cite-item.open {
    border-inline-start-color: var(--parallel-color, #8a7a63);
}

.parallel-cite {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 5px;
    inline-size: 100%;
    border: 0;
    background: none;
    padding: 1px 0;
    text-align: start;
    font-family: inherit;
    font-size: 0.78em;
    line-height: 1.35;
    color: var(--parallel-color, #6b5b45);
    cursor: pointer;
}

.parallel-cite:hover .parallel-cite-ref,
.parallel-cite-item.focused .parallel-cite-ref {
    text-decoration: underline;
}

.parallel-cite-ref {
    min-width: 0;
    overflow-wrap: break-word;
}

.parallel-cite-item.open .parallel-cite-ref {
    font-weight: 600;
}

.parallel-cite .parallel-strength {
    flex: none;
    font-size: 0.55em;
    letter-spacing: 0.5px;
    color: #b8ab95;
    opacity: 0.9;
}

/* An open passage sits under its own citation, indented to it, so a column with
   three open passages still reads as three citations and not as three texts. */
.parallel-cite-item > .parallel-open {
    margin-top: 3px;
}

/* Words whose parallel is currently open, so the text says which passage the
   column beside it belongs to. */
.body-word.parallel-open-word {
    background: #eef3ea;
}

/* The parallel passage, opened next to the words it parallels. */
.parallel-open {
    border: 1px solid #e6e0d6;
    border-inline-start: 3px solid var(--parallel-color, #8a7a63);
    border-radius: 3px;
    background: #fffdf8;
    padding: 4px 7px 6px;
    margin-bottom: 5px;
}

.parallel-open.focused {
    border-color: var(--parallel-color, #8a7a63);
    box-shadow: 0 0 0 2px rgba(120, 100, 70, 0.08);
}

.parallel-open-head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 6px;
    margin-bottom: 3px;
}

.parallel-open-ref {
    font-size: 0.8em;
    color: var(--parallel-color, #6b5b45);
    text-decoration: none;
    font-weight: 600;
}

.parallel-open-ref:hover {
    text-decoration: underline;
}

.parallel-open-close {
    flex: none;
    border: 0;
    background: none;
    padding: 0 2px;
    font-size: 0.75em;
    color: #b5a68c;
    cursor: pointer;
    line-height: 1;
}

.parallel-open-close:hover {
    color: #6b5b45;
}

/* position: relative so the aligned span's offsetTop is measured against this
   box, which is what openParallelPassages scrolls. */
.parallel-open-text {
    position: relative;
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.88em;
    line-height: 1.7;
    color: #3a2e20;
    max-block-size: 13em;
    overflow-y: auto;
}

.parallel-open-note {
    font-size: 0.7em;
    color: #a89880;
    margin-top: 2px;
}

/* Beside-mode reserves its gutter per subparagraph, not once for the halakhah:
   the bars have to stop at the subparagraph they belong to. So the halakhah-wide
   reservation is released here, and .parallel-split-text makes its own. */
body.parallels-beside.parallel-extents-on .text-content {
    padding-inline-end: 0;
}

@media (max-width: 900px) {
    /* No room for two columns: the citations go under their subparagraph instead
       of beside it, which keeps the pairing even though it loses the alignment. */
    .parallel-split,
    .parallel-split-row {
        display: block;
    }

    .parallel-split-refs {
        display: flex;
        flex-direction: row;
        flex-wrap: wrap;
        gap: 2px 10px;
        margin-block: 3px 8px;
    }

    .parallel-split-refs .parallel-cite-item {
        flex: 1 1 8rem;
    }
}

/* Which of our words a citation covers, under the ref. Present because several
   rows can otherwise be the same ref at different places in one halakhah. */
.parallel-anchor-text {
    display: block;
    font-family: 'Noto Serif Hebrew', serif;
    font-size: 0.8em;
    color: #9a8a70;
    margin-top: 1px;
}

/* Related occurrences of the focused passage elsewhere in the chapter -- the same
   Mishnah answering a second clause. Fainter than the focused extent because it is
   a weaker statement: related, not the thing pointed at. */
.body-word.parallel-focus-related {
    background: #f6f2e8;
}

/* Attribution for the apparatus, which is CC-BY: a licence condition, so it is
   part of the panel rather than a footnote someone has to remember. */
.parallels-credit {
    margin: 8px 9px 4px;
    padding-top: 6px;
    border-top: 1px solid #f0ebe1;
    font-size: 0.72em;
    color: #9a8a70;
    line-height: 1.5;
}
