/* Copyright 2026 by John A Kline.  See LICENSE for your rights.
   The Seismograph tab, in the panel grammar the celestial pages settled on
   and the forecast tabs, Highs/Lows, Graphs and the imagery tabs have
   carried since.  There was a second tab, Earthquakes; 11.2 folded it into
   this one, and the drum's markers are the only route to event information
   now.

   TOKENS.  This file uses css/liveseasons.css's --ls-* set DIRECTLY, light
   and dark, rather than restating it under a prefix of its own the way
   css/radar.css had to.  The only new tokens here are the ones this page
   family actually invents: the plates, the transport bar, and two data
   hues.  That is the direction radar.css's own header says the site is
   heading, and this is the first family to take it.

   THE PLATE, AGAIN.  Same argument as the imagery tabs, same conclusion.
   The heliograph is a WHITE raster the Raspberry Shake draws and we do not,
   and it prints its own vertical scale ("Each Vertical Division = 333.33
   microvolts") along the bottom of every plate.  It may not be recolored,
   so it sits on .plate--lit, which stays pale under .theme-dark: a lit
   panel inside a dark instrument.  (The dark counterpart lived here for
   the Earthquakes page's near-black event screenshots and went with it;
   the satellite pages have their own in css/radar.css.)

   ONE HUE PER CHART.  Every chart here draws a single series, so nothing is
   encoded in color that is not also encoded in position or size, and there
   is no categorical palette to get wrong.

   NO NUMBER ON A NOISE AXIS.  The ink measure behind the gutter and the two
   noise charts is uncalibrated -- ruling of 2026-09-05 -- so its value is
   never drawn.  Those axes carry ratios: multiples of the day's quietest
   quarter hour, percent of the pre-2020 weekday level, percent of the
   busiest day.  If you find yourself adding a unit here, that is the bug. */

:root {
    /* the plates */
    --sq-plate-lit:#ffffff;
    --sq-plate-line:#c2c8ce;
    /* the archive stepper */
    /* the two data hues: --sq-quake is an arrival and a quake, --sq-noise
       is the ground.  Neither is a categorical slot; see the note above. */
    /* 4.59 on white; #4b7fa8 read 4.29, and .quiets .v prints the
       quiet-time percentage in it at 13px bold, which is small text. */
    --sq-noise:#467aa3;
    --sq-grid:#e2e6ea;
    /* A QUAKE IS RED.  A terra cotta stood here, then a brick red, and
       neither read as red beside what the marker points at: a trace drawn
       in pure red.  The plate is a lit panel in both themes, so the red
       is the same in both.  Its ink is WHITE, and the red is a shade
       under the traces' #ff0000 because every text pair has to clear
       WCAG 2 4.5 AND APCA Lc 60 (tests: TestQuakeAndAirCardContrast;
       tools/contrast.py):
         white on #ff0000   4.00  Lc 69.6   under the WCAG bar
         dark on #ff0000    5.03  Lc 39.5   unreadable on an iPhone
         white on #e60000   4.81  Lc 75.8   this */
    --sq-quake:#e60000;
    --sq-on-mark:#ffffff;
    /* An annotation's words in the red, where no tag is under them: 4.81 /
       Lc 70.3 on white.  Its own token because the dark plate cannot use
       the marker red for type -- see .theme-dark. */
    --sq-annt:#e60000;
    /* felt shaking, the S wave's hue: 5.3 on white */
    --sq-felt:#a6561a;
}

.theme-dark {
    /* Deliberately NOT dark: the heliograph is a lit panel.  See the plate
       note at the top of this file. */
    --sq-plate-lit:#dfe4ea;
    --sq-plate-line:#2a3358;
    --sq-noise:#8fc0e6;
    --sq-grid:#1d2547;
    --sq-felt:#e8a458;
    /* The same red lifted, hue held, for type on the dark card: #e60000
       reads Lc 29.9 there.  Tags and markers keep --sq-quake. */
    --sq-annt:#ff9d85;
}

/* THE [hidden] GUARD, and it is not optional.  The browser hides [hidden]
   with a UA rule of specificity (0,1,0), which any class rule setting
   display beats -- css/radar.css records what that cost on the imagery
   pages.  Several things here are shown and hidden from javascript. */
.sq [hidden]{display:none !important}

/* ---- the panel ------------------------------------------------------ */
.sq{padding:1.625rem 1.25rem 2.125rem;margin-top:1.125rem;font-size:min(calc(1rem + var(--ls-step)), max(1rem, var(--ls-cap)));color:var(--ls-ink);
    text-align:left;font-family:'Open Sans',arial,sans-serif}
.sq .sqwrap{max-width:77.5rem;margin:0 auto;display:flex;flex-direction:column;gap:1.625rem}
.sq section{background:var(--ls-surface);border:.0625rem solid var(--ls-line);
            padding:1.125rem 1.25rem 1rem}
.sq .eyebrow{color:var(--ls-accent);font-weight:600;font-size:.8em;letter-spacing:.08em;
             text-transform:uppercase;margin:0 0 .75rem;border:0;padding:0}
.sq .caption{color:var(--ls-muted);font-size:.85em;margin:.875rem 0 0;max-width:86ch;
             line-height:1.55}
.sq .caption b{color:var(--ls-ink-3)}
.sq .cfoot{color:var(--ls-muted);font-size:.82em;border-top:.0625rem solid var(--ls-rule);
           padding-top:.625rem;margin-top:1rem}
.sq a{color:var(--ls-link);text-decoration:none}
.sq a:hover{text-decoration:underline}
/* The frame column is given a DEFINITE width, not `auto`.  The heliograph
   is 1,570 px of intrinsic width and the image inside it is width:100%, so
   an auto column sizes itself to the raster: the page went 1,279 px wide at
   a 1,124 px viewport and the rail was crushed into a column of vertical
   text one word wide.  The phone query overrides this to a single column. */
.sq .withrail{display:grid;grid-template-columns:45rem minmax(0,1fr);gap:1.625rem;
              align-items:start;margin-top:1.125rem}
.sq .rail{min-width:0}
.sq .railh{color:var(--ls-accent);font-weight:600;font-size:.8em;letter-spacing:.08em;
           text-transform:uppercase;margin:1.375rem 0 .5rem}
.sq .railh:first-child{margin-top:0}
.sq .railh--pill{display:flex;align-items:center;gap:.625rem;
                 justify-content:space-between;flex-wrap:wrap;white-space:nowrap}
.sq .pill--inst{font-size:.92em;font-weight:600;padding:.125rem .5625rem;border-radius:.625rem;
          border:.0625rem solid;white-space:nowrap;text-transform:none}
.sq .pill--inst.pill--ok{color:var(--ls-ok);border-color:var(--ls-ok);background:var(--ls-tint)}
.sq .rail p{margin:0 0 .625rem;font-size:.88em;line-height:1.6;color:var(--ls-ink-2)}
.sq .meta{margin:0;display:grid;grid-template-columns:auto 1fr;gap:.375rem .875rem;font-size:.86em}
.sq .meta dt{color:var(--ls-muted);font-size:.92em;letter-spacing:.04em;
             text-transform:uppercase;white-space:nowrap}
.sq .meta dd{margin:0;color:var(--ls-ink-2);font-variant-numeric:tabular-nums}

.sq .plate{border:.0625rem solid var(--sq-plate-line);display:grid;place-items:center;
           padding:.625rem;border-radius:.1875rem}
.sq .plate img{display:block;max-width:100%;height:auto}
.sq .plate--lit{background:var(--sq-plate-lit)}

/* ---- the archive stepper -------------------------------------------- */
.sq .transport{display:flex;align-items:center;gap:.625rem;margin-top:.75rem;flex-wrap:wrap}
/* the page head sits above the card now, so nothing in it to clear */
.sq section > .transport:first-child{margin-top:0}
/* ONE CONTROL VOCABULARY, not two.  11.2 wrote --sq-btn-* for this
   transport rather than adopting the picker the report pages already
   had; the two differed only in radius, height, fill and ink, which
   reads as carelessness rather than as a system.  --ls-control-* is the
   single definition now, sized as the reports picker -- the larger
   target for a finger.  The four --sq-btn-* tokens they replace
   are deleted with them, light and dark. */
.sq .tbtn{background:var(--ls-control-face);
          border:.0625rem solid var(--ls-control-line);
          color:var(--ls-control-ink);height:var(--ls-control-h);min-width:2.375rem;
          display:grid;place-items:center;cursor:pointer;padding:0 .6875rem;
          border-radius:var(--ls-control-r);
          font:600 .78em/1 'Open Sans',arial,sans-serif;letter-spacing:.05em}
.sq .tbtn svg{width:.8125rem;height:.8125rem;fill:currentColor}
.sq .tbtn:hover:not(:disabled){border-color:var(--ls-control-on);
                               color:var(--ls-control-on)}
/* A DISABLED CONTROL FADES, as it did in 13.2.  WCAG 1.4.3 exempts
   inactive controls from the contrast bar, and the fade is what says
   the control does nothing; ink_runner.py excuses text inside a
   disabled control by the same rule. */
.sq .tbtn:disabled{opacity:.42;cursor:default}
.sq .tbtn[aria-pressed="true"],
.sq .tbtn[aria-checked="true"]{background:var(--ls-control-on);
                               border-color:var(--ls-control-on);
                               color:var(--ls-control-on-ink)}

/* THE HALF-DAY CHOICE, as one control.  Two hairline boxes with a gap
   between them read as two unrelated buttons; this is one question with
   two answers, so the pair share an edge and the group draws the box.
   The selected half fills with the accent, which is the same thing the
   month grid does for the chosen month. */
.sq .tseg{display:inline-flex;border:.0625rem solid var(--ls-control-line);
          border-radius:var(--ls-control-r);overflow:hidden}
.sq .tseg .tbtn{border:0;border-radius:0;min-width:6rem}
.sq .tseg .tbtn + .tbtn{border-left:.0625rem solid var(--ls-control-line)}
.sq .tseg .tbtn:hover:not(:disabled){background:var(--ls-control-hover)}
.sq .tseg .tbtn[aria-checked="true"]:hover{background:var(--ls-control-on)}

/* The unit, said once for the whole control -- the day and the half are
   both UTC, so it belongs to the group rather than to either field. */
.sq .tunit{font:700 .68em/1 'Open Sans',arial,sans-serif;letter-spacing:.1em;
           color:var(--ls-faint);margin-right:-.125rem}

/* Latest: the same quiet shortcut the report pages use, not a sixth box
   in the row.  One word, one job, one treatment. */
/* LATEST IS THE REPORTS' LATEST.  The transport buttons above were
   unified to --ls-control-* and sized as the reports picker; this button
   was left on its own .78em and padding:0, so the one control the two
   pages share still did not match -- the fix had been applied to the
   instance and not to the class.  These five values ARE
   graph_date.css's .gdp-latest, and TestPickersAgree holds them there:
   the seismograph page does not load graph_date.css (it wants none of
   the popup), so the rule is restated rather than shared. */
.sq .tlatest{background:none;border:0;color:var(--ls-control-on);
             font-weight:600;font-size:min(calc(1rem + var(--ls-step)), max(1rem, var(--ls-cap)));font-family:'Open Sans',arial,sans-serif;
             cursor:pointer;padding:.5625rem .25rem;margin-left:.375rem}
.sq .tlatest:hover:not(:disabled){text-decoration:underline}
.sq .tlatest:disabled{color:var(--ls-faint);opacity:.55;cursor:default}
.sq .tdate{height:var(--ls-control-h);border:.0625rem solid var(--ls-control-line);
           background:var(--ls-control-face);
           color:var(--ls-ink);border-radius:var(--ls-control-r);padding:0 .625rem;
           font:.86em/1 'Open Sans',arial,sans-serif}
.sq .stamp{margin-left:auto;font-size:.86em;color:var(--ls-ink-2);
           font-variant-numeric:tabular-nums;white-space:nowrap}
.sq .gdp-error{color:var(--ls-bad);font-size:.85em;min-height:1.2em;margin-top:.25rem}

/* =====================================================================
   THE DRUM.  Two columns that must stay in vertical register: a gutter we
   draw and a heliograph we do not.  Everything in the gutter and every
   arrival marker is positioned by PERCENTAGE of the image box, from the one
   calibration this page family has -- 48 traces, baseline i at
   y = 65 + 30i of 1534; minute m at x = 50 + 96m of 1570 -- so both survive
   the image being scaled to any width and nothing measures pixels at
   runtime.

   The plate around the heliograph carries a border and NO mat.  That source
   is itself a white plate, so a mat would add nothing; and it would push
   the image down inside the frame and take the gutter out of register with
   the traces, which is the whole point of the column.
   ===================================================================== */
.sq .drum{display:grid;grid-template-columns:6.5rem 1fr;align-items:stretch;
          margin-top:1.375rem}
.sq .dgut{position:relative}
.sq .dgutcap{position:absolute;top:-.125rem;right:.5rem;font-size:min(calc(.59375rem + var(--ls-step)), max(.59375rem, var(--ls-cap)));letter-spacing:.07em;
             text-transform:uppercase;color:var(--ls-faint);
             transform:translateY(-100%);text-align:right}
.sq .dgrow{position:absolute;right:.5rem;left:0;transform:translateY(-50%);
           display:flex;align-items:center;justify-content:flex-end;gap:.375rem;height:.75rem}
.sq .dgrow .lab{font-size:min(calc(.625rem + var(--ls-step)), max(.625rem, var(--ls-cap)));color:var(--ls-faint);font-variant-numeric:tabular-nums;
                white-space:nowrap;width:3.25rem;text-align:right}
.sq .dgrow .bar{height:.3125rem;border-radius:.125rem 0 0 .125rem;background:var(--sq-noise);
                opacity:.85;width:0}
.sq .dgrow.hr .lab{color:var(--ls-muted);font-weight:600}
/* brighter in dark, where --ls-faint and --ls-muted sit low on the navy */
.theme-dark .sq .dgrow .lab{color:var(--ls-muted)}
.theme-dark .sq .dgrow.hr .lab{color:var(--ls-ink-2)}
.sq .dgrow.hr .bar{opacity:1}
.sq .dplate{padding:0}
.sq .dframe{position:relative;line-height:0}
.sq .dframe img{width:100%;height:auto;display:block}
.sq .marks{position:absolute;inset:0;pointer-events:none}
/* The sensor, in the row above the plate.  Measured: the instrument's own
   "R24AE EHZ AM 00" is ~14px in a 1570px raster, which is 5.5px once the
   plate is drawn at 614, and the picker is 400px below the fold at a 1124
   viewport.  NOT over the plate: the header band above the first trace is
   only 50 raster rows -- about 20 on screen -- and a badge big enough to
   read reaches twice that, onto the trace.  The record is never covered. */
/* CENTERED over the plate, not tucked into a corner: it reads as the
   picture's title, which is what it is, and it is the most findable of the
   three positions tried -- findability being the whole complaint.  Left
   would sit 8px from the gutter's own caption, two labels of different
   scope with nothing to separate them. */
/* ALL THREE, AND THEY SWITCH.  This row held one chip naming the chosen
   sensor; it holds the three sensors now and any of them changes the
   plate.  It keeps the chip's place exactly -- the
   plate's column, centered above it, clear of the gutter's own caption --
   because the three positions that were tried before it are written up
   just above and none of the reasons changed.

   THE CHOSEN ONE IS A SOLID ACCENT RECTANGLE -- the whole chip fills
   with the accent, not a badge inside it.  A first pass marked it
   the way the picker below marks its tiles -- the code in a filled badge,
   the axis word in accent -- on the argument that one vocabulary is
   easier to learn than two.  It is the wrong argument for these two
   objects: the picker's mark sits on a 200px thumbnail where a filled
   badge is a detail on a large thing, and up here the button IS the
   detail, so a badge inside it marks a small thing inside a small thing.
   Filling the whole chip reads at a glance, which is what a row above the
   plate is for.

   The ink is --ls-on-accent on --ls-accent, the site's own pair: 4.84 in
   light and 8.43 in dark, so the axis word clears AA at its 0.82em and
   the pair is one this skin already measures elsewhere. */
/* THREE EQUAL BUTTONS, one width for all three.  The axis words are not
   the same length -- vertical, north-south, east-west -- so left to their
   content the three chips were 169, 207 and 178 css px and the row read
   as three unrelated objects rather than one control.  `repeat(3, 1fr)`
   on a grid that is still centered in the plate's column sizes every
   column to the widest of them and no wider: the row grows to fit its own
   contents, it does not stretch to the plate.  A flex row with flex:1
   would have stretched them across the whole column instead, which is a
   different look and not the one asked for. */
.sq .chtop{grid-column:2;justify-self:center;margin-bottom:.4375rem;
           display:grid;grid-template-columns:repeat(3,1fr);gap:.5rem;
           justify-content:center}
.sq .chtb{background:var(--ls-tint);border:.0625rem solid var(--ls-line);
          border-radius:.25rem;padding:.1875rem .5625rem;cursor:pointer;
          text-align:center;
          font:700 min(calc(.9375rem + var(--ls-step)), max(.9375rem, var(--ls-cap)))/1.25 'Open Sans',arial,sans-serif;letter-spacing:.04em;
          color:var(--ls-ink)}
.sq .chtb .ax{font-weight:400;font-size:.82em;color:var(--ls-ink-2);
              margin-left:.4375rem;letter-spacing:.02em}
/* An empty axis word must not leave a 7px gap in front of nothing: the
   picker is what supplies the wording, and a page without it falls back
   to the bare channel name. */
.sq .chtb .ax:empty{display:none}
.sq .chtb:hover{border-color:var(--ls-accent)}
.sq .chtb[aria-pressed="true"]{background:var(--ls-accent);
          border-color:var(--ls-accent);color:var(--ls-on-accent)}
/* Both spans, explicitly: .ax carries its own --ls-ink-2 and would keep
   it on the filled chip, where it is 1.6 against the accent. */
.sq .chtb[aria-pressed="true"] .cno,
.sq .chtb[aria-pressed="true"] .ax{color:var(--ls-on-accent)}
/* ONLY THE VISIBLE MARKER IS CLICKABLE.  The cap is pulled up out of its
   own flow space (translateY below), so the button's box is 43px tall --
   the cap's height of empty air, then the stem -- while the trace pitch at
   the width a plate is drawn is under twelve.  With the box itself
   hit-testable, that is a large invisible target over the plate, and where
   two of them overlap the later marker in the DOM answers for a click
   aimed at the earlier one's stem.  So the button takes no pointer events
   and its two visible pieces take them back; the click still bubbles to
   the button's handler. */
/* A MARKER IS A POINT: zero wide at its `left`, with the stem and the label
   each centered on it.  It used to be centered on itself with a transform,
   and a transform makes every marker its own stacking layer -- so no label
   could ever sit above another marker's stem.  Ordering whole markers by
   lift traded one crossing for another (a lifted M2.8's label under an
   M3.8's stem, Feb 2 2026).  With no transform here, every label is above
   every stem, whatever crosses what. */
.sq .mk{position:absolute;width:0;pointer-events:none;
        background:none;border:0;padding:0;cursor:pointer;line-height:1}
.sq .mk .cap,.sq .mk .stem{pointer-events:auto}
.sq .mk .stem{display:block;width:.1875rem;height:1.625rem;background:var(--sq-quake);
              position:relative;z-index:1;transform:translateX(-50%)}
.sq .mk .cap{display:block;font:700 min(calc(.75rem + var(--ls-step)), max(.75rem, var(--ls-cap)))/1.5 'Open Sans',arial,sans-serif;
             color:var(--sq-on-mark);background:var(--sq-quake);border-radius:.1875rem;
             padding:.0625rem .3125rem;white-space:nowrap;
             position:absolute;bottom:100%;left:0;transform:translateX(-50%);z-index:2}
/* THE LABEL HANGS ABOVE THE STEM, OUT OF THE BUTTON'S FLOW.  Lifted with
   translateY(-100%) it still took its full height in flow, so the stem
   began one label-height below it and ended that far past the trace it
   points at -- 17px on the desktop, 18px on a phone, with nothing joining
   label to stem.  Out of flow, the button is the stem:
   drawMarks and spreadMarks put its top a stem's length above the trace,
   so the tip lands on the arrival and the label sits on the stem's top.
   tests/seismic_runner.py holds both ends to a pixel. */
/* pointer-events BACK ON.  .marks is none so the overlay does not block the
   plate and .mk turns it back on for the buttons -- but the popover is
   appended into .marks too, and inherited none, so its two links could not
   be clicked at all.  What sat under the link at its own center was the
   heliograph. */
.sq .mkpop{pointer-events:auto;position:absolute;z-index:5;width:24rem;
           background:var(--ls-surface);color:var(--ls-ink-2);
           border:.0625rem solid var(--ls-line);border-radius:.75rem;
           font-size:.9em;line-height:1.45;
           box-shadow:0 .75rem 2rem rgba(20,30,50,.24),0 .125rem .375rem rgba(20,30,50,.12);
           animation:sq-card-in .18s ease-out}
.theme-dark .sq .mkpop{box-shadow:0 .75rem 2rem rgba(0,0,0,.55)}
/* the pointer, on the marker: the popup sets --mk-arrow to wherever the
   marker is, since the card is kept inside the plate and may not be */
.sq .mkpop::before{content:"";position:absolute;top:-.4375rem;left:var(--mk-arrow,1.75rem);
           width:.875rem;height:.875rem;margin-left:-.4375rem;transform:rotate(45deg);
           background:var(--sq-quake);border-radius:.125rem 0 0 0}
.sq .mkpop.quiet,.sq .mkscrim.quiet{animation:none}
/* and the wave line does not grow in again when an open card is rebuilt */
.sq .mkpop.quiet .mpline{animation:none}
.sq .mphead{position:relative;border-radius:.6875rem .6875rem 0 0;padding:.875em 2.75em .8125em 1em;
           background:var(--sq-quake);color:var(--sq-on-mark)}
.sq .mpclose{position:absolute;top:.625em;right:.625em;width:1.875em;height:1.875em;border-radius:50%;
           border:0;padding:0;background:rgba(0,0,0,.14);color:inherit;cursor:pointer;
           font:700 1.1em/1 'Open Sans',arial,sans-serif}
.sq .mptop{display:flex;align-items:flex-end;gap:.85em}
.sq .mpmag{font:800 3.1em/.9 'Open Sans',arial,sans-serif;letter-spacing:-.03em;white-space:nowrap}
/* full ink, no opacity, on anything laid on the red: white at .85 was 3.67
   and Lc 56.3, and at .92 4.17 (TestQuakeAndAirCardContrast) */
.sq .mpmag small{font-size:.29em;font-weight:700;letter-spacing:.02em;margin-left:.15em}
.sq .mpwhere{font:700 1.05em/1.25 'Open Sans',arial,sans-serif}
.sq .mpwhen{font-size:.86em;margin-top:.15em}
.sq .mpchips{display:flex;flex-wrap:wrap;gap:.45em;margin-top:.7em}
.sq .mpchips span{font:700 .76em/1.6 'Open Sans',arial,sans-serif;padding:0 .65em;border-radius:1em;
           background:rgba(0,0,0,.28)}
/* Darkened, under white ink: 8.04 and Lc 90.0 on the #e60000 header, where
   the header's own white is 4.81 and 75.8 (TestQuakeAndAirCardContrast). */
.sq .mpbody{padding:.875em 1em 1em}
.sq .mpfacts{display:grid;grid-auto-flow:column;grid-auto-columns:1fr;gap:.5em;margin-bottom:.9em}
.sq .mpfact{background:var(--ls-tint);border:.0625rem solid var(--ls-hair-2);border-radius:.5em;padding:.45em .6em}
.sq .mpfact b{display:block;font:800 1.1em/1.2 'Open Sans',arial,sans-serif;color:var(--ls-ink);
           font-variant-numeric:tabular-nums;white-space:nowrap}
.sq .mpfact span{font-size:.7em;color:var(--ls-muted);letter-spacing:.05em;text-transform:uppercase}
.sq .mplabel{font-size:.72em;color:var(--ls-faint);letter-spacing:.05em;text-transform:uppercase}
.sq .mprace{margin-bottom:.9em}
.sq .mptrack{position:relative;height:2.85em;margin-top:.35em}
.sq .mpline{position:absolute;left:0;right:0;top:2.35em;height:.25em;border-radius:.2em;
           background:linear-gradient(90deg,var(--sq-quake),var(--sq-noise),var(--sq-felt));
           transform-origin:left;animation:sq-grow 1.2s ease-out both}
.sq .mptick{position:absolute;top:0;font-size:.7em;line-height:1.25;color:var(--ls-muted);white-space:nowrap}
.sq .mptick b{display:block;color:var(--ls-ink);font-weight:700;font-variant-numeric:tabular-nums}
.sq .mptick::after{content:"";position:absolute;top:3.07em;left:0;width:.9em;height:.9em;border-radius:50%;
           background:var(--ls-surface);border:.2em solid var(--sq-quake);box-sizing:border-box}
.sq .mptick.t0{left:0}
.sq .mptick.tp{transform:translateX(-50%);text-align:center}
.sq .mptick.tp::after{left:50%;margin-left:-.45em;border-color:var(--sq-noise)}
.sq .mptick.tend{right:0;left:auto;transform:none;text-align:right}
.sq .mptick.tend::after{left:auto;right:0;margin-left:0}
.sq .mptick.ts::after{border-color:var(--sq-felt)}
.sq .mpbtns{display:flex;flex-wrap:wrap;gap:.5em}
.sq .mpbtn{display:inline-block;font:700 .84em/1.3 'Open Sans',arial,sans-serif;padding:.5em .85em;
           border-radius:.45em;border:.0625rem solid var(--ls-line);background:var(--ls-tint);
           color:var(--ls-accent);text-decoration:none}
.sq .mpbtn.prime{background:var(--ls-accent);border-color:var(--ls-accent);color:var(--ls-on-accent)}
/* The one-event locator.  Angle is the bearing from this house, radius is
   log10 of the distance, so Los Altos Hills and Kamchatka sit on the same
   dial.  It says what "23 mi, bearing 354 degrees" says, in the form the
   question is actually asked, and three rings spread from the epicenter. */
.sq .locwrap{display:flex;align-items:center;gap:.8em;margin-bottom:.9em}
.sq .loc{width:6.5em;height:6.5em;flex:none;overflow:visible}
.sq .loc .ring{fill:none;stroke:var(--sq-grid);stroke-width:1}
.sq .loc .spoke{stroke:var(--sq-grid);stroke-width:1}
.sq .loc .ray{stroke:var(--sq-quake);stroke-width:1.25;stroke-dasharray:3 3}
/* the rings keep a thin stroke as they spread: vector-effect is set on
   the circles themselves (seismic.js locator), where it is valid SVG */
.sq .loc .wave{fill:none;stroke:var(--sq-quake);stroke-width:1.25;
           transform-box:fill-box;transform-origin:center;
           animation:sq-ripple 2.4s ease-out infinite}
/* each ring's delay is set where it is drawn (seismic.js ripples), from the
   clock, so a rebuilt card's rings carry on rather than restart; the 2.4s
   above is RIPPLE_S there */
.sq .loc .you{fill:var(--ls-accent)}
.sq .loc .dot{fill:var(--sq-quake);stroke:var(--ls-surface);stroke-width:1.5}
.sq .lockey{font-size:.86em;line-height:1.45;color:var(--ls-ink-2)}
.sq .lockey b{font-size:1.15em;color:var(--ls-ink)}
.sq .lockey span{font-size:.86em;color:var(--ls-faint)}
@keyframes sq-card-in{from{opacity:0;transform:translateY(-.375rem)}}
@keyframes sq-grow{from{transform:scaleX(0)}}
@keyframes sq-ripple{0%{transform:scale(1);opacity:.8}100%{transform:scale(5.5);opacity:0}}
@keyframes sq-sheet-in{from{transform:translateY(100%)}}
@keyframes sq-fade-in{from{opacity:0}}
/* ON A PHONE, A SHEET FROM THE BOTTOM of the screen (seismic.js popMark
   says why), over a scrim a tap on which closes it.  Nothing between
   #drum_marks and the page is transformed or clipped, so fixed means the
   viewport here. */
.sq .mkscrim{pointer-events:auto;position:fixed;inset:0;z-index:40;background:rgba(10,15,34,.35);
           animation:sq-fade-in .2s ease-out}
.sq .mkpop.mksheet{position:fixed;left:0;right:0;bottom:0;top:auto;width:auto;z-index:41;
           max-height:85vh;overflow:auto;font-size:1em;border-radius:1.25rem 1.25rem 0 0;
           border-bottom:0;animation:sq-sheet-in .24s ease-out}
.sq .mkpop.mksheet::before{display:none}
.sq .mkpop.mksheet .mphead{border-radius:1.1875rem 1.1875rem 0 0;padding-top:1.4em}
.sq .mkpop.mksheet .mphead::before{content:"";position:absolute;top:.5em;left:50%;width:2.6em;height:.28em;
           margin-left:-1.3em;border-radius:.2em;background:rgba(255,255,255,.45)}
@media (prefers-reduced-motion: reduce){
  .sq .mkpop,.sq .mkscrim,.sq .mpline,.sq .loc .wave{animation:none}
  .sq .loc .wave{display:none}
}

/* the three channels, as the Sat. Bands contact sheet does it */
/* align-items:start -- A BUTTON CENTERS ITS OWN CONTENT.  Stretched to the
   row, a thumbnail whose label wraps to one line fewer than its neighbors'
   carried its image down by half the difference: on the phone the EHZ
   thumbnail dropped 5.5px whenever EHN or EHE was selected, because only
   the selected label's bold weight wrapped it to a second line.  Sized to
   its own content and pinned to the top of the row, every image starts on
   the same line whatever its label does. */
.sq .chans{display:grid;grid-template-columns:repeat(3,1fr);gap:.875rem;margin-top:1rem;
           align-items:start}
.sq .chan{background:none;border:0;padding:0;font:inherit;text-align:left;
          cursor:pointer;color:var(--ls-ink-2)}
.sq .chan .cimg{background:var(--sq-plate-lit);border:.0625rem solid var(--sq-plate-line);
                display:block;width:100%;height:auto;border-radius:.125rem}
.sq .chan .clab{display:block;font-size:.78em;margin-top:.375rem;color:var(--ls-ink-2)}
.sq .chan .cno{color:var(--ls-muted);margin-right:.4em}
.sq .chan[aria-pressed="true"] .cimg{border-color:var(--ls-accent);
                                     outline:.18em solid var(--ls-accent);
                                     outline-offset:.05em}
.sq .chan[aria-pressed="true"] .clab{color:var(--ls-accent);font-weight:700}
.sq .chan[aria-pressed="true"] .cno{background:var(--ls-accent);color:var(--ls-on-accent);
                                    border-radius:.125rem;padding:.05em .35em;margin-right:.35em}
.sq .chan:active .cimg{border-color:var(--ls-accent)}

/* what the catalog says arrived on the plate being shown */
.sq .ondrum{display:flex;flex-wrap:wrap;gap:.5rem;margin-top:.875rem}
.sq .oq{display:flex;align-items:baseline;gap:.4375rem;border:.0625rem solid var(--ls-hair);
        border-left:.1875rem solid var(--sq-quake);background:var(--ls-tint);padding:.3125rem .625rem;
        font-size:.8em;border-radius:.125rem}
.sq .oq.nope{border-left-color:var(--ls-line);color:var(--ls-muted)}
.sq .oq b{font-size:1.15em;color:var(--ls-ink)}
.sq .oq .n{display:inline-grid;place-items:center;width:.9375rem;height:.9375rem;
           border-radius:50%;background:var(--sq-quake);color:var(--sq-on-mark);
           font:700 min(calc(.5625rem + var(--ls-step)), max(.5625rem, var(--ls-cap)))/1 'Open Sans',arial,sans-serif}
.sq .oq .quiet{color:var(--ls-muted)}

/* ---- charts we draw ourselves --------------------------------------- */
.sq .chart{width:100%;height:auto;display:block;overflow:visible}
.sq .chart .grid{stroke:var(--sq-grid);stroke-width:1}
.sq .chart .axis{stroke:var(--ls-rule);stroke-width:1}
.sq .chart .tick{fill:var(--ls-faint);font-size:min(calc(10px + var(--ls-svg-step)), max(10px, var(--ls-svg-cap)));font-family:'Open Sans',arial,sans-serif}
.sq .chart .ylab{fill:var(--ls-faint);font-size:min(calc(10px + var(--ls-svg-step)), max(10px, var(--ls-svg-cap)));font-family:'Open Sans',arial,sans-serif}
.sq .chart .lbl{fill:var(--ls-ink-3);font-size:min(calc(11px + var(--ls-svg-step)), max(11px, var(--ls-svg-cap)));font-family:'Open Sans',arial,sans-serif}
.sq .chart .bar{fill:var(--sq-noise)}
.sq .chart .line{fill:none;stroke:var(--sq-noise);stroke-width:2;stroke-linejoin:round}
.sq .chart .dot{fill:var(--sq-quake);fill-opacity:.62;stroke:var(--ls-surface);stroke-width:1}
.sq .chart .dot.faint{fill:var(--sq-noise);fill-opacity:.28;stroke:none}
.sq .chart .ann{stroke:var(--sq-quake);stroke-width:1.5;stroke-dasharray:4 3}
.sq .chart .annt{fill:var(--sq-annt);font-size:min(calc(11px + var(--ls-svg-step)), max(11px, var(--ls-svg-cap)));font-weight:700;
                 font-family:'Open Sans',arial,sans-serif}
/* a quake's label is white on a red tag once seismic.js has sized the tag
   (drawHalfDay says why); until then, red type on no tag */
.sq .chart .anntag{fill:var(--sq-quake)}
.sq .chart .annt.tagged{fill:var(--sq-on-mark)}
/* filtering hides marks; it never repaints the survivors */

.sq .figrow{display:grid;grid-template-columns:1fr 1fr;gap:1.625rem;margin-top:1rem;
            align-items:start}
.sq .fig h3{margin:0 0 .25rem;font-size:.8em;letter-spacing:.08em;text-transform:uppercase;
            color:var(--ls-accent);font-weight:600}
.sq .fig .fsub{margin:0 0 .625rem;font-size:.8em;color:var(--ls-muted)}
.sq .hero{display:flex;gap:1.625rem;flex-wrap:wrap;margin:.875rem 0 0}
.sq .hero div{min-width:7.5rem}
.sq .hero .n{font-size:2.1em;font-weight:700;color:var(--ls-ink);line-height:1.1;
             font-variant-numeric:tabular-nums}
.sq .hero .k{font-size:.76em;letter-spacing:.07em;text-transform:uppercase;
             color:var(--ls-muted);margin-top:.125rem}
.sq .quiets{margin:0;padding:0;list-style:none;font-size:.84em}
.sq .quiets li{display:grid;grid-template-columns:auto 1fr auto;gap:.625rem;
               align-items:baseline;padding:.3125rem 0;border-bottom:.0625rem solid var(--ls-hair-2)}
.sq .quiets .d{font-variant-numeric:tabular-nums;color:var(--ls-ink-2);white-space:nowrap}
.sq .quiets .w{color:var(--ls-muted)}
.sq .quiets .v{font-variant-numeric:tabular-nums;color:var(--sq-noise);font-weight:700}

/* ---- the phone layout ----------------------------------------------
   Under the width query, and NOT a narrow layout: the phone keeps the same
   1124-px frame as a wider screen (the root rule in css/liveseasons.css
   scales it) and sets the type larger.  One override does the family. */
@media (max-width: 600px){.sq{font-size:min(calc(1.875rem + var(--ls-step)), max(1.875rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq .sqwrap{gap:2.125rem}}
@media (max-width: 600px){.sq section{padding:1.5rem 1.625rem 1.375rem}}
@media (max-width: 600px){.sq .withrail{grid-template-columns:1fr}}
@media (max-width: 600px){.sq .figrow{grid-template-columns:1fr}}
@media (max-width: 600px){.sq .drum{grid-template-columns:9.375rem 1fr}}
@media (max-width: 600px){.sq .dgrow .lab{font-size:min(calc(1.3125rem + var(--ls-step)), max(1.3125rem, var(--ls-cap)));width:5.75rem}}
@media (max-width: 600px){.sq .dgrow{height:1.25rem}}
@media (max-width: 600px){.sq .dgutcap{font-size:min(calc(.9375rem + var(--ls-step)), max(.9375rem, var(--ls-cap)))}}
/* The strip that replaced the single .plab chip; the phone layout scales
   every chrome element up and this is one, so it keeps the chip's size
   and gains the gap the three buttons need at that scale. */
@media (max-width: 600px){.sq .chtb{font-size:min(calc(1.5rem + var(--ls-step)), max(1.5rem, var(--ls-cap)));padding:.3125rem .8125rem}}
@media (max-width: 600px){.sq .chtop{gap:.75rem}}
@media (max-width: 600px){.sq .mk .cap{font-size:min(calc(1.875rem + var(--ls-step)), max(1.875rem, var(--ls-cap)));padding:.1875rem .625rem}}
@media (max-width: 600px){.sq .mk .stem{width:.25rem;height:2.5rem}}
@media (max-width: 600px){.sq .tbtn{height:3.5rem;min-width:4rem;padding:0 1rem}}
@media (max-width: 600px){.sq .tbtn svg{width:1.5rem;height:1.5rem}}
@media (max-width: 600px){.sq .tdate{height:3.5rem;font-size:.8em}}
/* THE PHONE'S LATEST, sized like the reports picker's -- 32px on 12/22,
   which is what the phone .gdp.gdp .gdp-latest uses.  This needs its own rule
   because the desktop value stopped being relative: .tlatest was
   `.78em`, and the phone .sq sets a 30px base, so the one declaration was
   12.5px on the desktop and 23.4 here.  Pinning the desktop to the
   reports picker's 16px silently shrank the phone's to 16 with it. */
@media (max-width: 600px){.sq .tlatest{font-size:min(calc(2rem + var(--ls-step)), max(2rem, var(--ls-cap)));padding:.75rem 1.375rem}}
/* THE STAMP TAKES ITS OWN LINE HERE, deliberately.  At the phone's type
   scale the transport needs 1289px of a 990px row, so the stamp wraps --
   and it was wrapping by ACCIDENT: margin-left:auto right-aligns it when
   it fits, so a shorter date ("Sep 9" rather than "Wed, Sep 9, 2026")
   would pull it back up beside Latest and the row would change shape
   with the calendar.  flex-basis:100% makes the second line the design
   at every date.  Nothing moves today; what stops is the jumping.
   There is no version of this that fits on one line: deleting the whole
   Latest button AND the UTC label still leaves it 81px short, and the
   only remaining lever is type size, which is the phone layout's point. */
@media (max-width: 600px){.sq .stamp{flex:0 0 100%;margin-left:0}}
@media (max-width: 600px){.sq .stamp{margin-left:0;white-space:normal}}
@media (max-width: 600px){.sq .chart .tick,.sq .chart .ylab{font-size:19px}}
@media (max-width: 600px){.sq .chart .lbl,.sq .chart .annt{font-size:20px}}

/* PHONE TEXT SIZES MEASURED ON AN IPHONE.  Under the old 1124 pin, iOS
   Safari enlarged this family's small text on its own; these are the
   sizes it showed (screen px at 402 wide, as rem of the scaled frame),
   so the device-width page reads the same.  Rules Safari left alone are
   not restated. */
@media (max-width: 600px){.sq.sq .rail p{font-size:min(calc(2.291rem + var(--ls-step)), max(2.291rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .caption{font-size:min(calc(2.296rem + var(--ls-step)), max(2.296rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .railh{font-size:min(calc(1.828rem + var(--ls-step)), max(1.828rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .eyebrow{font-size:min(calc(1.828rem + var(--ls-step)), max(1.828rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .cfoot{font-size:min(calc(2.19rem + var(--ls-step)), max(2.19rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .fig h3{font-size:min(calc(1.844rem + var(--ls-step)), max(1.844rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .oq{font-size:min(calc(1.763rem + var(--ls-step)), max(1.763rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .fig .fsub{font-size:min(calc(1.779rem + var(--ls-step)), max(1.779rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .quiets .w{font-size:min(calc(1.716rem + var(--ls-step)), max(1.716rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .meta dd{font-size:min(calc(1.79rem + var(--ls-step)), max(1.79rem, var(--ls-cap)))}}
@media (max-width: 600px){.sq.sq .railh--pill{font-size:min(calc(1.499rem + var(--ls-step)), max(1.499rem, var(--ls-cap)))}}
