/* Magik website design system.
 *
 * Ported from the design lab, cell 188 of 600:
 *   style    18  goffrr  "Ocean fill · frosted · round"
 *   palette   7          "Aqua pop"
 *
 * The button is a window onto moving water. Surfaces are translucent
 * and actually blur what is behind them. Corners are round.
 */

/* Pantone 16-1546 Living Coral, on the concrete and the pool.
 *
 * Three materials off the reference: the warm concrete deck is the
 * ground, the pool is the water, and the coral is the one thing you
 * press. Blue never appears on a flat surface, so the two never fight.
 *
 * ONE RULE, and it is not negotiable. Living Coral is a fill, never
 * type. It runs 2.73:1 against white and 2.26:1 as text on the deck,
 * so white labels on it and coral body copy both fail WCAG outright.
 * Anything coral that has to be READ uses --su-text instead.
 */
:root{
  --bg:#EFE9E1;      /* the concrete, sunlit */
  --surface:#F9F5EF; /* the same, one stop up */
  --ink:#241E1B;     /* the shadow on the concrete, warm not neutral */
  --muted:#736760;   /* 4.54:1 on the ground. The quietest legal type. */

  /* NOT A TEXT COLOUR. 2.23:1 on the ground and 2.47:1 on a card, so
     anything set in it fails WCAG outright — and it was carrying "fuel
     and fee inside", which is the whole proposition, in the least
     legible colour on the site. There is no room under --muted for a
     third legal tone on a ground this light, so this one stopped being
     type: it is for hairlines, dormant map dots, struck-through prices
     and disabled dates. Quiet text is --muted, one size smaller. */
  --faint:#A79C93;
  --line:#DED5C9;

  --su:#FF6F61;      /* Living Coral 16-1546 TPX. FILL ONLY */
  --ac:#FF8A72;      /* the lit edge of it, for the gradient */
  --su-text:#AE4433; /* what coral looks like when it has to be read */
  --onacc:#241E1B;   /* dark on coral: 6.03:1 */

  --se:#4FC8CE;      /* the pool */
  --hi:#F0913F;      /* the spritz */
  --wa:#E2A33C;
  --da:#C03A28;

  /* ---- Aperol -------------------------------------------------------
     The coral wash (--tint) is mixed for a WHITE card. On the sand it
     has nothing to push against: #FBDDD6 against #EFE9E1 is a 1.06:1
     separation, so a row of chips reads as pale pink smudges rather
     than as anything placed. Sand is a warm ground and it wants a warm,
     saturated answer, not a desaturated one — so anything tinted that
     sits directly on the page ground takes Aperol instead of coral.
     Coral keeps the cards and the buttons; this is only for the ground. */
  --ap:#F4661B;      /* Aperol. FILL — the orange that survives sand */
  --ap-text:#9E3D05;  /* the same, when it has to be read: 6.8:1 on --ap-wash */
  --ap-wash:#F8DFC6; /* Aperol over the sand, 1.9:1 against it */
  --ap-line:#E8B98C; /* the edge of the wash, so a chip has a boundary */

  --tint:#FBDDD6;    /* coral wash — for cards, NOT for the ground */
  --tint2:#D6EDEE;   /* pool wash */
  --tint3:#E9E2D7;   /* sand wash */

  /* Where the water runs out, the page is beach. Two sands, wet and
     dry, so the field under the page has somewhere to go. */
  --sand:#E4D8C2;    /* dry sand */
  --sand2:#D8C9AF;   /* the darker band the tide left */

  /* The sea has its own pair now. It is the pool, not the brand
     colour, so the water stays turquoise while the interface is coral. */
  --sea-a:#5FD3D8;   /* the caustic highlight */
  --sea-b:#1E7F8C;   /* the depth between */

  /* ---- THE INSTRUMENT RAMP -------------------------------------------
     Teal -> green -> yellow -> orange -> red. Not sand and coral, and
     deliberately not: this is the one thing on the site where colour is
     a reading rather than a mood, every marina on earth already reads
     this ramp, and a two-metre swell painted in the brand's coral is a
     dial that matches the furniture and tells you nothing.

     It lived in forecast.css, which is loaded by one page. The sea panel
     in the header is on EVERY page and was therefore painting the same
     three verdicts out of the brand palette instead — a "green flag" day
     drawn in teal, because teal was what it had. Two palettes for one
     scale is how the header and the forecast page come to disagree about
     what a good day looks like, so there is one, and it is here.

     The five steps are the five bands in MAGIK.WAVE_BANDS / WIND_BANDS,
     sampled at each band's midpoint. Recompute them if the ramp moves. */
  --s0:#4FA8C7;  --s0-wash:#DCEEF4;  --s0-ink:#2E6173;   /* glassy / calm   */
  --s1:#6FC262;  --s1-wash:#E2F3E0;  --s1-ink:#407139;   /* easy / light    */
  --s2:#E9C13F;  --s2-wash:#FBF3D9;  --s2-ink:#877025;   /* lumpy / fresh   */
  --s3:#DC613B;  --s3-wash:#F8DFD8;  --s3-ink:#803822;   /* rough / strong  */
  --s4:#A23329;  --s4-wash:#ECD6D4;  --s4-ink:#5E1E18;   /* big / hard      */
  --sna:#A79C93; --sna-wash:#EAE4DC; --sna-ink:#736760;  /* nothing read    */

  /* ---- THE SEPARATOR ------------------------------------------------
     A section break was a flat 1px of --line all the way across, which is
     the same rule every website on earth draws. This one is the two
     halves of the brand meeting: Living Coral coming up out of nothing on
     the left, the caustic blue of the water in the middle, coral again
     and then nothing. It is the wash of a wave crossing sand, at one
     pixel.

     KEPT ALMOST INVISIBLE ON PURPOSE. The strongest stop is 42% of a
     colour that is already light, and both ends fade out completely, so
     at arm's length this is a hairline and only at reading distance is
     it a hairline with colour in it. A separator that announces itself
     has stopped separating and started decorating — and there are four
     of these on a boat page. Fine first, brand second.

     Used as a background rather than a border, because a border cannot
     hold a gradient without border-image and border-image cannot fade to
     transparent at the ends without also eating the corners. */
  --hairline:linear-gradient(90deg,
    transparent 0%,
    color-mix(in srgb, var(--su) 42%, transparent) 16%,
    color-mix(in srgb, var(--sea-a) 52%, transparent) 50%,
    color-mix(in srgb, var(--su) 34%, transparent) 84%,
    transparent 100%);

  --sh:36,30,27;     /* warm shadow, as an rgb triplet */

  /* style goffrr · geometry */
  --r-card:22px; --r-btn:999px; --r-chip:999px; --r-img:15px;

  /* style goffrr · surfaces (frosted, not solid)
     The fill was 55%, which over sand landed about 4% away from the ground
     it sat on: the cards stopped being objects and the page went one
     colour. A card has to be a step up from its ground before it can be
     anything else, so the fill is 80% and the edge and the shadow do
     their share too. Over the water bands it is still translucent. */
  --cardbg:color-mix(in srgb, var(--surface) 80%, transparent);
  --cardbd:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  --blur:blur(13px) saturate(150%);
  --elev:0 1px 2px -1px rgba(var(--sh),.16), 0 16px 28px -18px rgba(var(--sh),.6);

  /* The control is flat Living Coral. It used to be a window onto moving
     water — two radial passes plus a turbulence tooth — but the gradient
     made the same button read as two different corals depending on where
     it sat on the page. One fill, one colour, no drift. */
  --btnbg:var(--su);
  --btnfg:var(--onacc);
  --btnsh:0 8px 18px -12px color-mix(in srgb, var(--su) 62%, #000);
  --btn-tex-o:0;

  /* moving-water tooth that drifts across the button fill */
  --wtex:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='220' height='220'%3E%3Cfilter id='w'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.012 .05' numOctaves='4'/%3E%3CfeColorMatrix type='saturate' values='0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23w)' opacity='.7'/%3E%3C/svg%3E");
  --paper:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='200' height='200'%3E%3Cfilter id='g'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.045' numOctaves='5'/%3E%3CfeColorMatrix type='saturate' values='0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23g)' opacity='.3'/%3E%3C/svg%3E");

  /* web-scale rhythm */
  --maxw:1180px;
  --gut:clamp(20px, 5vw, 40px);
  --sec:clamp(72px, 10vw, 132px);

  /* How far the water has to run up to reach the top of the page. The
     header floats over it, so this is the header's own height and not a
     number of its own; site.js keeps it measured. The value here is only
     what it measures to before the account chip has been painted in. */
  --header-h:96px;
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%; scroll-behavior:smooth}
@media (prefers-reduced-motion:reduce){
  html{scroll-behavior:auto}
  *,*::before,*::after{animation-duration:.001ms !important; animation-iteration-count:1 !important; transition-duration:.001ms !important}
}

body{
  margin:0; background:var(--bg); color:var(--ink);
  font-family:"Lexend", system-ui, -apple-system, sans-serif;
  font-size:17px; line-height:1.62; font-weight:350;
  -webkit-font-smoothing:antialiased; text-rendering:optimizeLegibility;
  overflow-x:hidden; position:relative;
}

/* A frosted panel is only frosted if there is something behind it to
   blur. Below the hero the page would otherwise be flat, so soft fields
   pool across it — enough for the blur to have work to do, never enough
   to compete with the text.
   These fields are SAND, not coral. Past the edge of the water you are
   on the beach, and coral belongs on the things you press, not on the
   ground you are standing on. */
body::before{
  content:""; position:fixed; inset:0; z-index:-1; pointer-events:none;
  background:
    radial-gradient(58% 42% at 12% 18%,  color-mix(in srgb, var(--sand2) 70%, transparent), transparent 70%),
    radial-gradient(52% 40% at 92% 40%,  color-mix(in srgb, var(--sand) 66%, transparent), transparent 72%),
    radial-gradient(60% 46% at 30% 78%,  color-mix(in srgb, var(--sand2) 55%, transparent), transparent 70%),
    radial-gradient(46% 38% at 82% 96%,  color-mix(in srgb, var(--hi) 7%, transparent), transparent 70%);
}
img{max-width:100%; display:block}
a{color:inherit}
::selection{background:var(--tint); color:var(--ink)}

/* typography */
h1,h2,h3,h4{
  margin:0; font-family:"Bricolage Grotesque", system-ui, sans-serif;
  font-variation-settings:"wdth" 86; font-weight:700;
  line-height:1.06; letter-spacing:-.015em; color:var(--ink);
}
h1{font-size:clamp(42px, 7.2vw, 82px); line-height:1.02; letter-spacing:-.028em}
h2{font-size:clamp(30px, 4.4vw, 50px); letter-spacing:-.022em}
h3{font-size:clamp(19px, 2vw, 23px); letter-spacing:-.012em}
h4{font-size:16px; font-weight:700; letter-spacing:-.005em}
p{margin:0}
em{font-style:normal; opacity:.45}

.eyebrow{
  font-size:11px; letter-spacing:.17em; text-transform:uppercase;
  color:var(--muted); font-weight:600; margin:0 0 14px;
}
.lede{font-size:clamp(17px, 1.55vw, 20px); color:var(--muted); line-height:1.6; max-width:60ch}
.sub{color:var(--muted); font-size:15px}
.fine{font-size:13px; color:var(--muted); line-height:1.55}
.ok{color:var(--su-text)}
.num{font-variant-numeric:tabular-nums}

/* layout */
/* The gutter is the bigger of the design's own and whatever the hardware
   is taking. `viewport-fit=cover` in the head puts the page under the
   notch, which is right for the water behind it and wrong for a line of
   type: turned sideways, an iPhone's notch stands in the left gutter and
   the first character of every paragraph goes behind it. In portrait, and
   on everything that is not a phone, both insets are 0 and this is
   `var(--gut)` unchanged. */
.wrap{
  width:100%; max-width:var(--maxw); margin-inline:auto;
  padding-left:max(var(--gut), env(safe-area-inset-left));
  padding-right:max(var(--gut), env(safe-area-inset-right));
}
.section{padding-block:var(--sec)}
/* Two sections in a row used to stack a full --sec on both sides of the
   seam, so adjacent blocks sat a quarter of a screen apart and the page
   read as empty rather than as generous. One section owns the gap. */
.section + .section{padding-block-start:0}
/* unless the section paints its own ground, where some of the padding is
   what the water fades in through */
.section + .section.band-sea{padding-block-start:calc(var(--sec) * .74)}
.section-head{max-width:70ch; margin-bottom:clamp(34px,4.5vw,58px)}
.section-head p{margin-top:16px}

/* A section that stands in the water.
   The frosted card system only works when there is something behind it
   worth blurring, and below the hero there was nothing — so the cards
   went flat and the whole page went one colour. This band puts the sea
   back under the middle of the page, which is both the brand and the
   contrast the cards need. */
.band-sea{position:relative; isolation:isolate}
.band-water{
  position:absolute; inset:0; z-index:-1; pointer-events:none; overflow:hidden;
  opacity:.92;
  -webkit-mask-image:linear-gradient(transparent 0%, #000 16%, #000 78%, transparent 100%);
  mask-image:linear-gradient(transparent 0%, #000 16%, #000 78%, transparent 100%);
}
.band-water canvas{width:100%; height:100%; display:block}
.band-head{
  display:flex; align-items:flex-end; justify-content:space-between;
  gap:24px; flex-wrap:wrap; margin-bottom:clamp(28px,3.6vw,46px);
}
.band-head h2{max-width:18ch}
/* --muted is tuned for sand. On turquoise it goes to mush, so type that
   stands in the water is ink held back rather than grey. */
.band-head .eyebrow{margin-bottom:10px; color:color-mix(in srgb, var(--ink) 68%, transparent)}
.band-sea .ppl p{color:color-mix(in srgb, var(--ink) 76%, transparent)}

/* The button is flat Living Coral. One fill, no texture, no gradient —
   the only thing that moves is the button itself, on hover. */
.btn{
  position:relative; overflow:hidden; isolation:isolate;
  display:inline-flex; align-items:center; justify-content:center; gap:9px;
  border:none; border-radius:var(--r-btn);
  background:var(--btnbg); color:var(--btnfg);
  font-family:"Lexend", sans-serif; font-weight:600; font-size:16px;
  padding:15px 30px; box-shadow:var(--btnsh); cursor:pointer;
  text-align:center; text-decoration:none; white-space:nowrap;
  transition:transform .18s ease, box-shadow .18s ease, background-color .18s ease;
}
@keyframes btndrift{0%{background-position:0% 40%} 100%{background-position:100% 60%}}
.btn:hover{
  transform:translateY(-2px);
  background-color:var(--ac);
  box-shadow:0 14px 28px -14px color-mix(in srgb, var(--su) 72%, #000);
}
.btn:active{transform:translateY(0)}
.btn:focus-visible{outline:2.5px solid var(--ink); outline-offset:3px}
.btn.sm{font-size:14px; padding:11px 21px}
.btn.lg{font-size:17px; padding:18px 38px}

/* the quiet companion: outline, no fill, ocean edge on hover */
.btn-ghost{
  display:inline-flex; align-items:center; justify-content:center; gap:9px;
  border:1.5px solid color-mix(in srgb, var(--ink) 14%, transparent);
  border-radius:var(--r-btn); background:color-mix(in srgb, var(--surface) 60%, transparent);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  color:var(--ink); font-family:"Lexend",sans-serif; font-weight:550; font-size:16px;
  padding:14px 28px; cursor:pointer; text-decoration:none; white-space:nowrap;
  transition:border-color .18s, color .18s, transform .18s;
}
.btn-ghost:hover{border-color:var(--ac); color:var(--ac); transform:translateY(-2px)}
.btn-ghost:focus-visible{outline:2.5px solid var(--ink); outline-offset:3px}
.btn-ghost.sm{font-size:14px; padding:10px 20px}

.btn-row{display:flex; flex-wrap:wrap; gap:13px; align-items:center}

/* Frosted surfaces: 55% surface plus a real 13px backdrop blur, so
   these panels blur the water, the photographs and the page behind. */
.card{
  background:var(--cardbg); border:var(--cardbd); border-radius:var(--r-card);
  box-shadow:var(--elev);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  padding:26px 26px 28px; position:relative;
}
.card.flush{padding:0; overflow:hidden}
.card.tight{padding:20px}

/* chips & pills */
/* Chips sit on the page ground, so they are Aperol rather than coral —
   see the note by --ap. The hairline is what stops seven of them in a row
   from reading as one continuous smear of colour. */
.chip{
  background:var(--ap-wash); color:var(--ap-text); border-radius:var(--r-chip);
  border:1px solid var(--ap-line);
  padding:6px 14px; font-size:13px; display:inline-block; white-space:nowrap;
}
/* On a card the ground is already light, so the chip goes back to coral. */
.card .chip, .cap-card .chip{
  background:var(--tint); color:var(--su-text); border-color:transparent;
}
.chips{display:flex; flex-wrap:wrap; gap:7px}
.pill{
  border-radius:var(--r-chip); padding:4px 12px; font-size:11.5px; font-weight:600;
  background:var(--tint2); color:var(--ac); white-space:nowrap;
  display:inline-flex; align-items:center; gap:5px; letter-spacing:.01em;
}
.pill.ok{background:var(--tint); color:var(--su-text)}
.pill.new{background:var(--ac); color:#fff}
.pill.warn{background:color-mix(in srgb, var(--wa) 22%, var(--bg)); color:#9A6B00}
.pill.live{background:color-mix(in srgb, var(--da) 14%, var(--bg)); color:var(--da)}
.pill.live::before{
  content:""; width:6px; height:6px; border-radius:50%; background:var(--da);
  animation:blip 1.9s ease-in-out infinite;
}
@keyframes blip{0%,100%{opacity:1} 50%{opacity:.25}}

/* site header
   The header is a floating bar, and it is deliberately the opposite
   material to the search bar below it. That bar is light, frosted and
   full width; if the header were the same it would read as a second
   copy of the same object stacked above the first. So the header is
   DEEP WATER: dark glass, and only as wide as the things inside it.
   Light-and-wide is the page. Dark-and-narrow is the site.
   Scrolling tightens it — the rail pulls in, the glass firms up, the
   wordmark shrinks — so the page reads as sliding underneath a fixed
   object rather than the header changing costume. */
.site-header{
  position:sticky; top:0; z-index:60;
  padding-block:16px;
  background:transparent; border:none;
  transition:padding-block .4s cubic-bezier(.2,.9,.3,1);
}
.site-header.stuck{padding-block:9px}

/* The scrim.
   A floating header has no ground, so everything in it was being read
   against whatever happened to be sliding underneath — a bright sky, a
   dark hull, a photograph edge — and its legibility swung with the
   scroll. This lays the page's own colour back down behind the header
   and fades it out below, so content dissolves into sand before it ever
   reaches the bar. It is the page passing under the header rather than
   colliding with it.
   It stays off while the header is over the sea at the top of a page,
   where the water is the ground and there is nothing to fix. */
.site-header::before{
  content:""; position:absolute; z-index:-1; pointer-events:none;
  inset:0 0 -44px 0;
  /* Solid sand for the whole height of the bar and a little past it, then
     a soft tail. Translucency here bought nothing — whatever showed
     through was noise behind type — while the tail is what keeps this
     from being a hard-edged band across the page. */
  background:linear-gradient(to bottom,
    var(--bg) 0%,
    var(--bg) 72%,
    color-mix(in srgb, var(--bg) 58%, transparent) 88%,
    transparent 100%);
  backdrop-filter:blur(6px); -webkit-backdrop-filter:blur(6px);
  -webkit-mask-image:linear-gradient(#000 74%, transparent 100%);
  mask-image:linear-gradient(#000 74%, transparent 100%);
  opacity:0; transition:opacity .4s ease;
}
.site-header.past-water::before{opacity:1}
/* The mark on the left standing on the page, the controls on the right
   floating in their own pill. Two objects, not one bar. */
.site-header .wrap{
  position:relative; display:flex; align-items:center;
  gap:clamp(16px,3vw,40px);
}

/* THE BAR IS NOT A BAR ANY MORE.
   It was a dark glass slab floating on the right of every page, and it
   was built for six items — three links, the sea, a chip and a button.
   Those are all in the drawer now, so what was left was a black brick
   holding one pill and two glyphs, sitting beside a wordmark that stands
   on the page with nothing behind it and above a cream search bar that
   does the same. It was the only heavy object on a site made of light
   ones, and it read exactly as heavy as it was.
   So the slab goes and its contents stand on the page like everything
   else. Each of the three is its own light object in the same material
   as the search bar underneath — one family of four across the header,
   rather than three things inside a fourth. */
.header-bar{
  position:relative; isolation:isolate;
  width:fit-content; max-width:100%; margin-left:auto;
  display:flex; flex-wrap:nowrap; align-items:center; gap:8px;
  padding:0; background:none; border:0; box-shadow:none;
  backdrop-filter:none; -webkit-backdrop-filter:none;
  animation:bar-in .7s cubic-bezier(.2,.9,.3,1) both;
}
@keyframes bar-in{from{opacity:0; transform:translateY(-16px)} to{opacity:1; transform:none}}
/* The sea inside the pill went with the pill. It was caustics on dark
   glass, seen from underneath, and there is no dark glass left for them
   to be seen through — over the page they would be a second ocean laid
   on top of the one already running behind the header. */
.header-water{display:none}
.header-bar > :not(.header-water){position:relative; z-index:1}

/* The wordmark. One flat value against its ground — ink on the light
   page, shell on the dark header — and nothing else. It is the one
   fixed point on a site where everything else is moving water, so it
   carries no colour of its own, no sweep and no glow. The PNG is used
   as a mask rather than drawn directly, which is what lets that one
   value be set at all. */
.wordmark{
  display:block; width:132px; height:33px; flex:none;
  background:url("../img/magik-wordmark.png") left center/contain no-repeat;
  transform-origin:left center;
  transition:width .4s cubic-bezier(.2,.9,.3,1), height .4s cubic-bezier(.2,.9,.3,1),
             transform .35s cubic-bezier(.2,.9,.3,1);
}
@supports ((-webkit-mask-image:url("../img/magik-wordmark.png")) or (mask-image:url("../img/magik-wordmark.png"))){
  .wordmark{
    background:var(--ink);
    -webkit-mask:url("../img/magik-wordmark.png") left center/contain no-repeat;
            mask:url("../img/magik-wordmark.png") left center/contain no-repeat;
  }
}

/* ---------------------------------------------------------- the lockup
   The word is two pieces cut from one image: the M, and AGIK. They are
   placed rather than flowed, so scrolling can slide AGIK away to the left
   and leave the M standing exactly where it was — same size, same place,
   same ink — while the disc arrives behind it. Nothing cross-fades and
   nothing morphs, which is the whole point: the M is one element that is
   never touched, so there is no seam to hide.

   Every measurement is derived from the geometry of the source PNG, which
   is 436 x 109 with the M occupying the first 98 columns and AGIK
   starting at column 100. That file is tracked additive -31: every gap
   loses the same 31 columns, which leaves the M/A pair at 2px against
   15-19px elsewhere. At 40px cap height that join still holds by a single
   column; at the phone's 29px it closes and the two letters touch. The
   untracked master is kept at
   mockups/tracking/_source-wordmark.png — re-track from that, never from
   this one, or the tightening compounds. */
.wm-lockup{
  --wm-w:250px;      /* the whole word, as displayed */
  --wm-h:62.5px;
  --wm-m-w:56.7px;   /* the M alone, rounded up so nothing clips */
  --wm-agik-x:57.3px;/* where AGIK begins inside the word */
  --wm-agik-w:193px;
  --disc:94px;       /* 1.5x the cap height: enough to hold the M with air */
  --inset:calc((var(--disc) - var(--wm-m-w)) / 2);
  --wm-close:.55s cubic-bezier(.2,.9,.3,1);

  position:relative; display:block; flex:none;
  height:var(--disc);
  width:calc(var(--inset) + var(--wm-w));
  transition:width .55s cubic-bezier(.2,.9,.3,1);

  /* The clip is here to swallow AGIK on its way out — it retracts its own
     width, so it finishes about 98px off the left edge and would
     otherwise be seen sliding across whatever is beside the mark.
     `hidden` alone cannot do that job any more: the box ends where the
     word's ink ends, near enough to the pixel, and the water now moves
     that ink by up to 13px. Clipped at the box, the K's right edge is
     shaved flat every time a lens crosses it — a straight vertical cut
     in the middle of a wave, which is the one artefact that gives the
     whole effect away as a filter. `clip` with a margin keeps the same
     clip a finger's width further out, which is past the deepest the
     displacement goes and nowhere near the 98px AGIK travels. `hidden`
     stays first for anything that has not got overflow:clip. */
  overflow:hidden;
  overflow:clip; overflow-clip-margin:16px;
}
/* shut down to the disc, which is all that is left once AGIK has gone */
.wm-shut .wm-lockup,
.page-gps .wm-lockup{width:var(--disc)}

/* THE BADGE DOES NOT GROW WITH THE WORD.
   The open word is 20% larger than the badge was drawn for. The badge is
   the size it has always been — it is a fixed object, the same thing the
   favicon is, and a mark you look at all day is not improved by being
   larger. So docking does not merely close the word, it steps the whole
   geometry back down to the set below, which is the size every one of
   these numbers was before the word grew.

   This costs something and it is worth saying where. The lockup was
   built on the promise that the M is never touched — same size, same
   place, same ink, the disc simply arriving behind it — because a
   resizing M is a seam and hiding that seam was the entire design. That
   promise cannot survive a word that is bigger than its own badge: one
   of the two has to move, and the instruction is that the badge holds.
   So the M does resize now, over the same .55s and the same curve as the
   width, and the read changes from `AGIK leaves, the disc arrives` to
   `the word settles into the badge`. It is a good enough move — it is
   smooth, it is one continuous gesture, and the ink never changes — but
   it is a different move, and if the old one is ever wanted back, the
   two var sets have to agree again and the word goes back to 208. */
.wm-shut .wm-lockup,
.page-gps .wm-lockup{
  --wm-w:208px; --wm-h:52px; --wm-m-w:47.2px;
  --wm-agik-x:47.7px; --wm-agik-w:161px; --disc:78px;
}

/* Every one of these is derived from a var that changes on dock, so every
   one of them has to be transitioned or the step-down is a single-frame
   snap in the middle of a half-second move. Custom properties do not
   interpolate; the lengths they feed do. */
.wm-m,.wm-agik{
  position:absolute; top:calc((var(--disc) - var(--wm-h)) / 2); height:var(--wm-h);
  background:url("../img/magik-wordmark.png") no-repeat;
  background-size:var(--wm-w) var(--wm-h);
  transition:top var(--wm-close), left var(--wm-close), width var(--wm-close),
             height var(--wm-close), background-size var(--wm-close),
             -webkit-mask-size var(--wm-close), mask-size var(--wm-close);
}
.wm-m   {left:var(--inset); width:var(--wm-m-w); background-position:0 0}
.wm-agik{
  left:calc(var(--inset) + var(--wm-agik-x)); width:var(--wm-agik-w);
  background-position:calc(-1 * var(--wm-agik-x)) 0;
  /* the same list, plus the two that only AGIK does */
  transition:top var(--wm-close), left var(--wm-close), width var(--wm-close),
             height var(--wm-close), background-size var(--wm-close),
             -webkit-mask-size var(--wm-close), mask-size var(--wm-close),
             transform var(--wm-close), opacity .32s ease .04s;
}
@supports ((-webkit-mask-image:url("../img/magik-wordmark.png")) or (mask-image:url("../img/magik-wordmark.png"))){
  .wm-m,.wm-agik{
    background:var(--ink);
    -webkit-mask-image:url("../img/magik-wordmark.png");
            mask-image:url("../img/magik-wordmark.png");
    -webkit-mask-repeat:no-repeat; mask-repeat:no-repeat;
    -webkit-mask-size:var(--wm-w) var(--wm-h); mask-size:var(--wm-w) var(--wm-h);
  }
  .wm-m{-webkit-mask-position:0 0; mask-position:0 0}
  .wm-agik{
    -webkit-mask-position:calc(-1 * var(--wm-agik-x)) 0;
            mask-position:calc(-1 * var(--wm-agik-x)) 0;
  }
}
/* AGIK retracts into the M. It travels its own width, so it is gone before
   the lockup finishes closing, and it passes UNDER the disc and the M —
   they are later in the DOM, so they paint over it — which is what makes
   it read as going into the M rather than merely leaving. */
.wm-shut .wm-agik,
.page-gps .wm-agik{transform:translateX(calc(-1 * var(--wm-agik-w))); opacity:0}

/* The disc is the badge with its own M healed out, so the M you see in it
   is the wordmark's, in ink. It arrives a beat late and overshoots. */
.wm-disc{
  position:absolute; left:0; top:0; width:var(--disc); height:var(--disc);
  border-radius:50%;
  background:url("../img/magik-disc.png") center/contain no-repeat;
  /* No ring and no shadow: the disc sits straight on the scrim, which is
     already the page's own sand, so anything drawn around it is a seam. */
  transform:scale(.2); opacity:0;
  transition:transform .5s cubic-bezier(.34,1.5,.5,1), opacity .28s ease;
}
.wm-shut .wm-disc,
.page-gps .wm-disc{transform:none; opacity:1; transition-delay:.12s, .12s}

/* ------------------------------------------------- the mark, refracted
   The whole site is water, and the one thing standing still in it was the
   word. It is under the surface now.

   The bending itself is an SVG filter — #wm-refract, in the icon sprite,
   where the reasoning for it is written out. All that is decided here is
   which element it is hung on and when it comes off.

   It is hung on .wm-lockup, so the M, AGIK and the disc are all bent by
   one continuous field of water rather than three of their own. Three
   would be three separate surfaces meeting at the seams between the
   pieces, and the seams between those pieces are the one thing this
   lockup was built to hide.

   `filter` composites the element off-screen and back, and the browser
   does that every frame while the turbulence is running. At 160x40 CSS
   pixels that is cheap; do not move this to anything page-sized. */
.wm-lockup{filter:url(#wm-refract)}

/* Docked, the filter comes off.
   Docking is the one moment the lockup is doing something exact — AGIK
   retracting its own width, the disc arriving behind an M that must not
   appear to move by a single pixel — and a displacement map is, by
   definition, the mark not being where it is. The two cannot both be
   true. The water is for the mark at rest.
   It is a transition rather than a switch so the surface flattens over
   the same half-second the word takes to close. */
.wm-lockup{transition:filter .45s ease}
.wm-shut .wm-lockup,
.page-gps .wm-lockup{filter:none}

/* ...and then the badge goes back under.
   Flat was right for the half-second of the move and wrong for the hour
   after it. Once the word has shut into the disc, the disc is the mark
   at rest — the only mark on the page — and the one thing on the site
   that was not in the water was the thing you look at most.

   So the filter comes back, on a delay long enough to clear the whole
   choreography: .55s of the lockup closing plus the .12s the disc waits
   before it arrives. It is a zero-length animation rather than a
   transition because filter:none -> url() has nothing to interpolate;
   what is wanted is a switch that happens late, and `forwards` on a
   delayed animation is exactly that. Undocking drops .docked, the
   animation goes with it, and the lockup falls back to the word's own
   water on the line above.

   THE CIRCLE IS NOT IN THE WATER. ONLY THE M IS.
   Hung on the lockup, the filter takes the disc with it, and a displaced
   circle is just a circle that has stopped being round — there is no
   information in a rim except its roundness, so bending it reads as a
   drawing error rather than as water. The disc is the ground here, the
   same as the page is the ground for the open word: it holds still and
   the ink on it moves. So the filter goes on .wm-m alone, which is the
   one element in the lockup that is a letter, and the badge becomes an
   M seen through water on a solid disc.

   That also means the water can go back to being the word's own water.
   Docked, .wm-m is 47.2px of the same letterform at the same size it has
   always been, so #wm-badge is cut for a letter and not for a rim. */
.wm-shut .wm-m,
.page-gps .wm-m{animation:wm-badge-under .01s linear .74s forwards}
@keyframes wm-badge-under{to{filter:url(#wm-badge)}}

/* Type that will not hold still is type somebody cannot read. Anyone who
   has asked for less movement gets the mark flat, which is also what the
   printed version of it is. The animation has to be named as well as the
   filter: a filled animation beats a plain declaration in the cascade,
   so switching this off is the only way `filter:none` here can win. */
@media (prefers-reduced-motion:reduce){
  .wm-lockup{filter:none}
  .wm-shut .wm-m,
  .page-gps .wm-m{animation:none; filter:none}
}

.brand{display:flex; align-items:center; text-decoration:none; flex:none}

/* ---------------------------------------------------------------- dock
   Past the hero the header stops being a header and becomes the search.
   The word closes into its own initial, the search bar lands beside it,
   and the navigation pill shuts into one button on the right.

   TWO FLAGS, because they are two questions. `.docked` is the search
   bar being in the header, and only five pages have one. `.wm-shut` is
   the word having closed into the badge, which every page does. They
   are set together where there is a bar and separately where there is
   not; site.js does both. Anything about the MARK keys off .wm-shut --
   and, since Live fleet, off `.page-gps` beside it: that page is a
   chart edge to edge with nothing to scroll, so the word never closes
   on its own and the badge would otherwise be the one mark on the site
   that is a different size and still moving. The mark rules name both
   selectors; the ones about the BAR (the sea chip, the padding) name
   only .wm-shut, because that page is not docked, it is simply short.
   Anything about the MARK keys off .wm-shut,
   anything about the layout off .docked. */
.header-dock{display:flex; align-items:center; min-width:0; flex:0 1 auto}
.docked .header-dock{flex:1 1 auto}
.docked .header-bar{margin-left:0}

/* The bar in the hero leaves a hole the exact size of itself behind, so
   docking cannot move the page under its own trigger. */
.sb-placeholder{height:0}
.brand:hover .wm-lockup{transform:scale(1.03)}
.wm-lockup{transform-origin:left center;
  transition:width var(--wm-close), height var(--wm-close),
  transform .35s cubic-bezier(.2,.9,.3,1)}
/* The mark used to carry the city under it as a footnote. It does not any
   more: the word is bigger now and the two were reading as a pair rather
   than a mark and its caption. Cartagena is still said in the footer and
   in the copy of every page that is about a place, which is where a fact
   belongs. Nothing else in the header wears a caption, so there is no
   .brand small rule left here. */

/* ---------------------------------------------------------- the drawer
   The navigation is a drawer at every width, not only once the page has
   scrolled or once the window is narrow.

   It was a row of words across the top of every page — Aboard, Live,
   People, and however many more the account had earned — and a row of
   words is a thing to be read before anything can be done with it. Two
   of the three rules underneath this file's header existed only to stop
   that row overflowing: the bar gave up its padding, then the role under
   your name, then your name. None of that is a layout, it is a queue of
   apologies for one.
   So the row goes where it already went on a phone and once docked. The
   header keeps what somebody might have arrived to do, and one button
   for everywhere they might go.

   Hung off the button rather than stretched across the row: the button is
   on the right, so the panel opens down and to the left of it.

   AND IT IS SHELL, NOT INK. The panel was a black slab, and it was the
   only black object on a site whose whole ground is warm sand: it landed
   on the page like a hole cut in it, and everything inside had to be
   re-coloured for a dark ground — which is how "Register your boat" ended
   up near-white type on a near-white pill and read as an empty box.
   The header already has a material, and there are four things in it: the
   sea chip, the account glyph, the button this hangs from, and the search
   bar under them. The drawer is the fifth. Same shell, same hairline, same
   warm shadow — it now reads as the button opening rather than as a
   separate piece of interface arriving from somewhere else, and every
   colour rule on the site (coral is a fill, --muted is the quiet type)
   applies in here unchanged. */
.nav{display:flex; flex-direction:column; align-items:stretch; gap:2px}
.header-bar > .nav{
  position:absolute; top:calc(100% + 12px); right:0; left:auto; margin:0;
  /* WIDER THAN IT WAS, because it holds more than it did. At 248px
     this was a column of one-word links; it is now a glyph, a label and
     sometimes a third column -- the count on Saved, the setting on the
     preferences row -- and "English · USD" was drawn off the right edge
     of the panel. 300px is what the widest of those rows needs without
     the label wrapping. */
  width:max(300px, 21vw); max-width:calc(100vw - 2 * var(--gut));
  background:var(--surface);
  border:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  border-radius:22px; padding:8px; display:none;
  box-shadow:0 2px 6px -2px rgba(var(--sh),.2), 0 30px 56px -28px rgba(var(--sh),.75);
}
.header-bar > .nav.open{display:flex; animation:nav-drop .3s cubic-bezier(.2,.9,.3,1) both}
/* The foot of the drawer. `display:contents` because its children are
   rows in the same column as the links above them — the span is only
   somewhere for session.js to insert the earned links in FRONT of, and a
   place to hang the rule that separates the two halves. */
.nav-tail{display:contents}
/* Places above, the thing to do and who you are below. A real <hr>, not a
   border on whichever row happens to come first: which row that is
   depends on the account (an owner is not offered the register button)
   and on whether anybody is signed in at all. */
.nav-rule{
  height:1px; border:0; background:var(--hairline);
  margin:9px 3px 8px;
}

/* Nav links are pills, not underlines: the ground slides in under the
   word on hover and stays under the page you are on. */
/* The links an account has earned arrive together in one span. Left as a
   span it is a single flex item whose own contents line-break when the
   bar runs short of room -- and a second line of links makes the bar
   taller. Its children are the bar's children, like the fixed links. */
.nav .nav-role{display:contents}

/* Sea state in the header. On dark glass it is lit rather than tinted:
   the readings glow amber out of the dark the way an instrument does at
   night, which is also what keeps it from reading as another nav item. */
/* ---- what the bay is doing ----
   Out of the drawer and into the bar. It was a wave glyph and a number in
   a pill, which is a number in a pill: nothing about it said sea and less
   said forecast. So it carries the word.

   AND IT IS THE SAME WHITE PILL AS THE TWO GLYPHS BESIDE IT. The first
   go at this tinted the whole chip with the verdict, which read beautifully
   against sand and vanished against the water it was reporting on — teal
   type on a teal sea, at the top of every page, which is where this thing
   spends most of its life. The ground is white at both ends of the scroll;
   the verdict is a coloured dot and a coloured word inside it, which is
   the part that has to change and the only part that does. */
/* ---- THE READING AT THE TOP, THE DISC ONCE YOU HAVE MOVED ----
   Both, and which one depends on the same flag the wordmark answers to.

   At the top of a page there is room and there is a reason: this is the
   one thing in the header that changes during the day, somebody who has
   just arrived has not asked it anything yet, and "Sea today · Good ·
   0.8 m" answers the question before it is put. Scrolled, that reader
   has moved on to something else and a 150px pill reporting the weather
   is the widest thing in a bar that now has a search in it — so it
   shuts into a disc the size of the two buttons beside it, exactly as
   the wordmark shuts into its badge, and for the same reason.

   .wm-shut is site.js's flag for "this page has been scrolled". It was
   built for the mark; it turns out to be the answer for anything in
   this header that is worth more room at rest than in passing. */
.sea-chip{
  display:inline-flex; align-items:center; gap:9px; flex:none;
  padding:5px 15px 5px 6px; border-radius:var(--r-chip); text-decoration:none;
  background:var(--surface); color:var(--ink); cursor:pointer;
  font-family:"Lexend",sans-serif; text-align:left;
  border:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  box-shadow:0 1px 3px -1px rgba(var(--sh),.18), 0 14px 28px -18px rgba(var(--sh),.6);
  transition:padding .34s cubic-bezier(.2,.9,.3,1), gap .34s cubic-bezier(.2,.9,.3,1),
             background .2s ease, border-color .2s ease;
}
.sea-chip:hover{background:#fff; border-color:color-mix(in srgb, var(--ink) 24%, transparent)}
.sea-chip:focus-visible{outline:2.5px solid var(--ac); outline-offset:2px}
.sea-chip[aria-expanded="true"]{
  background:color-mix(in srgb, var(--ink) 8%, var(--surface));
  border-color:color-mix(in srgb, var(--ink) 24%, transparent);
}

/* The glyph rides in a tinted disc of its own, and the tint is the
   verdict: green, amber or red off the instrument ramp, so the colour
   survives the collapse — shut, the disc IS the chip and the tint is
   the whole reading. */
.sea-ic{
  width:30px; height:30px; border-radius:50%; display:grid; place-items:center;
  flex:none; background:var(--s1-wash);
  transition:background .2s ease;
}
.sea-chip .ic{width:17px; height:17px; color:var(--s1-ink); transition:color .2s ease}
.sea-say{display:grid; line-height:1.15; gap:1px; overflow:hidden}
.sea-say i{
  font-style:normal; font-size:8.5px; letter-spacing:.15em; text-transform:uppercase;
  font-weight:700; color:var(--muted); white-space:nowrap;
}
.sea-say b{
  display:flex; align-items:baseline; gap:6px;
  font-size:13.5px; font-weight:650; white-space:nowrap;
}
.sea-say em{
  font-style:normal; font-size:11px; font-weight:500;
  font-variant-numeric:tabular-nums; color:var(--muted);
}
.sea-say em:empty{display:none}

/* THE VERDICT, in the disc and in the word. */
.sea-chip:has([data-verdict="warn"]) .sea-ic{background:var(--s2-wash)}
.sea-chip:has([data-verdict="warn"]) .ic{color:var(--s2-ink)}
.sea-chip:has([data-verdict="warn"]) [data-verdict]{color:var(--s2-ink)}
.sea-chip:has([data-verdict="bad"]) .sea-ic{background:var(--s4-wash)}
.sea-chip:has([data-verdict="bad"]) .ic{color:var(--s4-ink)}
.sea-chip:has([data-verdict="bad"]) [data-verdict]{color:var(--s4-ink)}
.sea-slot.is-down .sea-ic{background:var(--sna-wash)}
.sea-slot.is-down .ic{color:var(--sna-ink)}

/* ---- shut ----
   The words go and the pill closes onto its own glyph. Same 42px circle
   as the account and the drawer beside it: three identical objects, no
   pill, nothing in the row that is a different shape from its
   neighbours. The caption is not display:none — it is collapsed to
   nothing, so the transition has a width to run to and a screen reader
   still has the words. */
.wm-shut .sea-chip{padding:5px; gap:0; width:42px; height:42px; justify-content:center}
.wm-shut .sea-ic{width:100%; height:100%; background:none}
.wm-shut .sea-chip .ic{width:20px; height:20px}
.wm-shut .sea-say{
  width:0; opacity:0; pointer-events:none;
  transition:width .3s cubic-bezier(.2,.9,.3,1), opacity .18s ease;
}

/* Narrow, the reading sheds what it can before it shuts: the height
   first — the verdict is what decides a day, the number only qualifies
   it — and then the label. Below 560 there is no room for a pill beside
   a search bar at all, so it is the disc from the top of the page. */
@media (max-width:900px){
  .sea-chip{padding:5px 12px 5px 5px; gap:7px}
  .sea-ic{width:28px; height:28px}
  .sea-say em{display:none}
}
@media (max-width:560px){
  .sea-chip,.wm-shut .sea-chip{padding:5px; gap:0; width:38px; height:38px}
  .sea-ic,.wm-shut .sea-ic{width:100%; height:100%; background:none}
  .sea-chip .ic{width:18px; height:18px}
  .sea-say{width:0; opacity:0; pointer-events:none}
}
/* A place you can go is a plain word in ink, at rest. It was type at 68%
   of shell over black, which is a grey nobody chose and which read as
   four disabled rows; on the shell panel the word is simply the word. */
.nav a, .nav .nav-row{
  position:relative; isolation:isolate; text-decoration:none;
  color:var(--ink);
  font-size:15.5px; font-weight:400; white-space:nowrap;
  padding:12px 15px; border-radius:14px;
  transition:color .22s ease;

  /* A GLYPH, THE WORDS, AND WHATEVER THE ROW HAS TO ADD.
     Three columns rather than a flex row so the words start at the same
     x on every line: with `gap` alone a row whose glyph is a pixel
     narrower sets its label a pixel left of its neighbour, and a column
     of labels that does not line up is the thing that makes a menu look
     assembled rather than drawn. */
  display:grid; grid-template-columns:20px 1fr auto; align-items:center;
  gap:13px; text-align:left; width:100%;
  background:none; border:0; font-family:inherit; cursor:pointer;
}
.nav a .ic, .nav .nav-row .ic{
  width:19px; height:19px; flex:none; color:var(--muted);
  transition:color .22s ease;
}
.nav a:hover .ic, .nav .nav-row:hover .ic{color:var(--ink)}
/* The count on Saved, and the current setting on the preferences row:
   both are the third column, both are quiet, neither is ever the reason
   somebody looks at the row. */
.nav .nav-count{
  font-size:11.5px; font-weight:600; font-variant-numeric:tabular-nums;
  min-width:20px; text-align:center; padding:1px 7px; border-radius:999px;
  background:var(--su); color:var(--onacc);
}
.nav .nav-count[hidden]{display:none}
.nav .nav-stack{display:grid; gap:1px; min-width:0}
.nav .nav-say{
  font-style:normal; font-size:12px; font-weight:400; color:var(--muted);
  letter-spacing:.01em; white-space:normal;
}
/* The way out. A row like the others, and the arrow turned to point at
   the door rather than at another page of Magik. Not coral and not red:
   signing out is not destructive, it is just the last row. */
.nav .nav-out .ic{transform:rotate(0)}
.nav .nav-out{color:var(--muted)}
.nav .nav-out:hover{color:var(--ink)}
/* The ground is already the right shape, it just has not arrived yet. */
.nav a::before{
  content:""; position:absolute; inset:0; z-index:-1; border-radius:inherit;
  background:color-mix(in srgb, var(--ink) 7%, transparent);
  transform:scale(.8); opacity:0;
  transition:transform .3s cubic-bezier(.2,.9,.3,1), opacity .22s ease, background .22s ease;
}
.nav a:hover, .nav .nav-row:hover{color:var(--ink)}
.nav a:hover::before, .nav .nav-row:hover::before{transform:scale(1); opacity:1}
.nav a:focus-visible, .nav .nav-row:focus-visible{outline:2px solid var(--ink); outline-offset:2px}

/* The preferences panel, unfolded under its own row. Inside the drawer
   rather than in a second layer over it: a popover hanging off a popover
   is two things to dismiss and two places to lose the pointer, and this
   one has four controls in it. */
.nav-prefs{
  display:grid; gap:12px; margin:2px 3px 6px; padding:13px 14px 14px;
  border-radius:14px; background:color-mix(in srgb, var(--ink) 4.5%, transparent);
}
.nav-prefs[hidden]{display:none}
.nav-prefs h4{
  margin:0 0 6px; font-family:inherit; font-size:11px; font-weight:600;
  letter-spacing:.08em; text-transform:uppercase; color:var(--muted);
}
.nav-prefs .nav-pick{display:flex; flex-wrap:wrap; gap:6px}
.nav-prefs button{
  font:inherit; font-size:13px; padding:7px 12px; border-radius:999px; cursor:pointer;
  background:var(--surface); color:var(--ink); white-space:nowrap;
  border:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  transition:border-color .18s ease, background .18s ease;
}
.nav-prefs button:hover{border-color:color-mix(in srgb, var(--ink) 30%, transparent)}
.nav-prefs button[aria-pressed="true"]{
  background:color-mix(in srgb, var(--se) 26%, var(--surface));
  border-color:color-mix(in srgb, var(--sea-b) 40%, transparent);
  color:var(--sea-b); font-weight:550;
}
.nav-prefs button:focus-visible{outline:2px solid var(--ac); outline-offset:2px}
/* WHERE THE NUMBERS COME FROM, and it is not a live market. Small,
   grey, and never omitted -- a converted price with no provenance is a
   quote, and this is an estimate. */
.nav-prefs .nav-prefs-fine{
  margin:0; font-size:11px; line-height:1.45; color:var(--muted);
}
/* ------------------------------------------------ register your boat
   The one thing in the header that is not a place on the site but
   something to do, and the only reason a boat owner who has never heard
   of us stops here at all. So it is the one item left outside the
   drawer: everywhere you can GO is behind the button, and the thing you
   might have COME to do is in the open.
   It carries the helm and a line drawn round it, and under the pointer
   the line goes and the fill arrives. It is not the solid white of Sign
   in — that is the way in for somebody who is already here, and only one
   thing in the bar can be the brightest. */
.boat-cta{
  position:relative; isolation:isolate;
  display:inline-flex; align-items:center; gap:8px; flex:none;
  padding:11px 20px; text-decoration:none;
  border-radius:var(--r-chip);
  background:var(--surface);
  border:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  box-shadow:0 1px 3px -1px rgba(var(--sh),.18), 0 14px 28px -18px rgba(var(--sh),.6);
  color:var(--ink); font-size:14.5px; font-weight:550; white-space:nowrap;
  transition:border-color .22s ease, background .22s ease;
}
.boat-cta::before{
  content:""; position:absolute; inset:0; z-index:-1; border-radius:inherit;
  background:color-mix(in srgb, var(--tint) 70%, transparent);
  transform:scale(.86); opacity:0;
  transition:transform .3s cubic-bezier(.2,.9,.3,1), opacity .22s ease;
}
.boat-cta .ic{width:16px; height:16px; flex:none; color:var(--ac)}
.boat-cta:hover{border-color:color-mix(in srgb, var(--su) 55%, transparent)}
.boat-cta:hover::before{transform:scale(1); opacity:1}
.boat-cta:focus-visible{outline:2.5px solid var(--ac); outline-offset:2px}
/* Hidden means hidden: the display above would otherwise win over it. */
.boat-cta[hidden]{display:none}

/* And in the drawer, where it is authored. A row like the links, so the
   column stays a column — but on the coral wash, because inside a list of
   plain words it is still the one item that is a thing to DO rather than
   a place to go, and a row that looks exactly like its neighbours cannot
   say that.

   IT ALSO HAS TO SAY ITS OWN COLOUR HERE. `.nav a` is (0,1,1) and
   `.boat-cta` is only (0,1,0), so the drawer's link colour was winning
   over the button's — which, on the old black panel, painted near-white
   type on the button's near-white pill. The row was legitimately blank:
   "Register your boat" was being drawn in #F9F5EF on #F9F5EF. `.nav
   .boat-cta` is (0,2,0) and outranks both, so the label is stated once,
   here, where the rest of the drawer's version of this button is. */
.nav .boat-cta{
  display:grid; grid-template-columns:20px 1fr auto; align-items:center;
  gap:13px; width:100%; text-align:left;
  margin:0 0 2px; padding:13px 15px; border-radius:14px;
  font-size:15.5px; font-weight:500;
  color:var(--ink);
  background:var(--tint);
  border:1px solid color-mix(in srgb, var(--su) 32%, transparent);
  box-shadow:none;
}
/* The label over the sentence. `white-space:normal` because .boat-cta
   inherits nowrap from the bar version of this button, where the row is
   four words on one line -- in here the second line is a sentence and
   has to be allowed to be one. */
.nav .boat-cta .boat-cta-say{display:grid; gap:2px; min-width:0}
.nav .boat-cta .boat-cta-say i{
  font-style:normal; font-size:12px; font-weight:400; line-height:1.4;
  color:var(--muted); white-space:normal;
}
/* A switch does not need selling: it is a door somebody already knows
   about, pressed twice a day. */
.nav .boat-cta.is-switch .boat-cta-say i{display:none}
/* Coral is a fill and never type, so the wash deepens under the pointer
   rather than the words changing colour. */
.nav .boat-cta::before{background:color-mix(in srgb, var(--su) 24%, transparent)}
.nav .boat-cta:hover{border-color:color-mix(in srgb, var(--su) 60%, transparent)}
.nav .boat-cta .ic{color:var(--su-text)}

/* ---- and the same row, once it is the switch ----
   Register your boat is a thing to DO and takes the coral it has always
   taken. Switch to hosting is not: it is the door between the two halves
   of the site, and it happens twice a day for somebody who runs boats
   and charters them. So it is the water rather than the coral — the same
   Caustics Ocean Blue that means "this is the one selected" everywhere
   else — and it carries a chevron, because a switch that moves you
   somewhere should say that it moves you somewhere. */
.nav .boat-cta.is-switch{
  background:color-mix(in srgb, var(--se) 20%, var(--surface));
  border-color:color-mix(in srgb, var(--sea-b) 28%, transparent);
  color:var(--sea-b); font-weight:550; cursor:pointer;
}
.nav .boat-cta.is-switch .ic{color:var(--sea-b)}
.nav .boat-cta.is-switch::before{background:color-mix(in srgb, var(--se) 34%, transparent)}
.nav .boat-cta.is-switch:hover{border-color:color-mix(in srgb, var(--sea-b) 55%, transparent)}
.nav .boat-cta.is-switch:focus-visible{outline:2.5px solid var(--sea-b); outline-offset:2px}
/* The chevron sits at the far end of the row, where a "takes you
   somewhere" mark belongs, rather than beside the words. */
.nav .boat-cta.is-switch::after{
  content:""; width:6px; height:6px; margin-left:auto; flex:none;
  border-top:1.7px solid currentColor; border-right:1.7px solid currentColor;
  transform:rotate(45deg); opacity:.55;
  transition:transform .22s cubic-bezier(.2,.9,.3,1), opacity .18s ease;
}
.nav .boat-cta.is-switch:hover::after{opacity:1; transform:rotate(45deg) translate(1px,-1px)}

/* WHERE YOU ARE IS NOT AN ACTION, so it is not coral.
   On the black panel it had to be solid coral, because on black there was
   nothing quieter that would still read. On shell there is: the hover
   ground, made permanent, with the word carrying a little more weight.

   It matters because the drawer now has a coral ladder in it and the two
   rungs both mean DO THIS — the wash is the boat you might register, the
   solid is the way in. A page you are already looking at was landing on
   top of that as the loudest object in the panel, which made three
   corals in a five-row menu and put the shout on the one row with
   nothing behind it. */
.nav a[aria-current="page"]{color:var(--ink); font-weight:550}
.nav a[aria-current="page"]::before{
  transform:scale(1); opacity:1;
  background:color-mix(in srgb, var(--ink) 8%, transparent);
}
.header-cta{display:flex; flex-wrap:nowrap; gap:10px; align-items:center; min-width:0}
.header-cta #user-slot{display:flex; min-width:0}
/* The one solid, light thing on the dark bar, so the way in is the
   brightest object in the header. */
.header-cta .btn-ghost{
  background:var(--surface); border-color:transparent; color:var(--ink);
  backdrop-filter:none; -webkit-backdrop-filter:none;
}
.header-cta .btn-ghost:hover{background:#fff; border-color:transparent; color:var(--ink)}
.header-cta .account-chip{
  background:color-mix(in srgb, #fff 11%, transparent);
  border-color:color-mix(in srgb, #fff 16%, transparent);
}
.header-cta .account-chip .account-who b{color:var(--surface)}
.header-cta .account-chip .account-who i{color:color-mix(in srgb, var(--surface) 55%, transparent)}
/* The drawer's button, and the way to your own account. These used to
   appear only where the words would not fit; the words are in the drawer
   now, so these two ARE the header's navigation and they are always
   here — and with the dark slab gone they are objects on the page rather
   than glyphs inside a box. Same surface as the search bar below them,
   same hairline, same shadow: four things in one material across the
   header. */
.menu-toggle,.account-ic{
  display:grid; place-items:center; width:42px; height:42px; flex:none;
  border-radius:50%; padding:0; margin:0; cursor:pointer; text-decoration:none;
  background:var(--surface);
  border:1px solid color-mix(in srgb, var(--ink) 13%, transparent);
  box-shadow:0 1px 3px -1px rgba(var(--sh),.18), 0 14px 28px -18px rgba(var(--sh),.6);
  color:var(--ink); font-size:18px; line-height:1;
  transition:background .2s ease, border-color .2s ease, color .2s ease,
             transform .3s cubic-bezier(.2,.9,.3,1);
}
.menu-toggle .ic,.account-ic .ic{width:20px; height:20px}
.menu-toggle:hover,.account-ic:hover{
  background:#fff; border-color:color-mix(in srgb, var(--ink) 24%, transparent);
}
.menu-toggle:focus-visible,.account-ic:focus-visible{outline:2.5px solid var(--ac); outline-offset:2px}
/* Open gets a ground and nothing else. It used to turn into a coral disc
   with a cross in it, which was a promise that the cross was the way out
   — and it is not: pressing anywhere on the page closes the drawer, which
   is what people try first. A button that changes into a different button
   when you are not looking at it is also a button you cannot find again.
   The panel hanging under it is what says it is open. */
.menu-toggle[aria-expanded="true"]{
  background:color-mix(in srgb, var(--ink) 8%, var(--surface));
  border-color:color-mix(in srgb, var(--ink) 24%, transparent);
}

/* NO DRAWER ON A BOAT, because the page is already anchored.
   Standing on a hull somebody is doing one thing — reading a day and a
   price and deciding — and the whole page is built to hold them there:
   the bar at the foot carries the total and Book at every scroll
   position, the search bar above reprices this boat in place rather than
   sending anyone back to the results, and "All boats" is at the top for
   the one way back that is actually wanted. Three lines offering About
   us, the live fleet and Register your boat, over a fixed booking bar,
   is a door out of a decision and nothing else. Everything in it is one
   press away through the mark or the footer, both of which are still on
   this page.
   THE ACCOUNT GLYPH TAKES THE SLOT INSTEAD, docked as well as loose. It
   is normally hidden once the bar has docked, because the drawer holds
   the same link with the account holder's name on it — here there is no
   drawer to hold it, and somebody coming back to a boat they were
   looking at yesterday must still have a way to their own trips. It is
   one glyph in the space the burger had, so the row does not move. */
.page-boat .menu-toggle,
.page-boat .header-bar > .nav{display:none}
.docked .page-boat .account-ic{display:grid}

/* hero 
   The sea is the point, so it is no longer a band at the top , the
   whole hero stands in the water and the search bar floats on it.
   Only the very bottom edge fades out into the page. */
.hero{position:relative; padding-block:clamp(56px,9vw,110px) clamp(64px,8vw,104px)}
/* the water runs up underneath the sticky header, so the ocean starts
   at the very top of the page rather than under a seam */
.hero-water{
  position:absolute; left:0; right:0; top:calc(-1 * var(--header-h)); bottom:0;
  z-index:0; pointer-events:none; overflow:hidden;
  -webkit-mask-image:linear-gradient(#000 0%, #000 62%, rgba(0,0,0,.35) 86%, transparent 100%);
  mask-image:linear-gradient(#000 0%, #000 62%, rgba(0,0,0,.35) 86%, transparent 100%);
  opacity:.9;
}
.hero-water canvas{width:100%; height:100%; display:block}
/* Same reasoning as .search-top .wrap: the search bar's panels are
   sealed inside this box, so this box is what has to clear whatever the
   page puts below it — the cooler on the menu page is sticky, and a
   calendar opening behind it is a calendar you cannot use. */
.hero .wrap{position:relative; z-index:50}
.hero-inner{max-width:940px}
/* The search is the page now, so the bar gets the full column — and
   with no copy above it, it needs water around it rather than a room. */
.hero-search{padding-block:clamp(14px,2vw,26px) clamp(18px,2.4vw,32px)}
.hero-search .hero-inner{max-width:none}
.hero-search .lede{max-width:46ch}

/* TIGHT. The tabs are in the header now and the bar is directly under
   them, so the 86px of air that used to sit above the bar was holding
   apart two halves of one control — you chose Boats up there and then
   scrolled to say where and when. And the fleet is the answer to the bar,
   not a separate chapter: --sec is 132px at full width, which put the
   first photograph most of a screen below the question.
   The home page is a search and its results. It should read as one
   object, in roughly one screen. */
#fleet{padding-bottom:clamp(26px,3.2vw,42px)}
#soon{padding-block:0 clamp(40px,5vw,72px)}
.hero h1{margin-bottom:20px}
.hero h1 em:not(.hl){display:block; opacity:1; color:color-mix(in srgb, var(--ink) 46%, var(--bg))}
.hero .lede{margin-bottom:34px; max-width:52ch}
.hero-note{
  margin-top:18px; font-size:14px; color:var(--muted);
  text-shadow:0 1px 0 color-mix(in srgb, var(--bg) 60%, transparent);
}
.hero-note b{color:var(--ink); font-weight:600}

/* The promise.
   Two lines that rise in on load, then one uneven reef-coloured stroke is
   drawn under "doing nothing" in a single pass — the way you would
   underline it on a napkin. The phrase is set in California Sunshine, the
   face the app uses for the wordmark; the words stay ink, so they hold
   against moving water. The global reduced-motion rule lands every
   animation on its final frame. */
@font-face{
  font-family:"California Sunshine";
  src:url("../fonts/CaliforniaSunshineRegular.ttf") format("truetype");
  font-weight:400; font-style:normal; font-display:swap;
}

.hero-title{display:grid; gap:0}
.hl-line{
  display:block; opacity:0; transform:translateY(20px);
  animation:hl-rise .85s cubic-bezier(.22,.61,.36,1) forwards;
}
.hl-line:nth-child(2){animation-delay:.13s}
@keyframes hl-rise{to{opacity:1; transform:none}}

.hl{
  position:relative; font-style:normal; opacity:1; display:inline-block;
  white-space:nowrap; font-family:"California Sunshine","Bricolage Grotesque",sans-serif;
  font-size:1.42em; line-height:.9; letter-spacing:0; color:var(--ink);
  vertical-align:-.04em;
}
.hl > span{position:relative; z-index:1}
.hl-swipe{
  position:absolute; left:-5%; bottom:-.02em; width:110%; height:.34em;
  z-index:0; overflow:visible;
}
.hl-swipe path{
  fill:none; stroke:url(#reef); stroke-width:15; stroke-linecap:round;
  vector-effect:non-scaling-stroke; opacity:.9;
  stroke-dasharray:1200; stroke-dashoffset:1200;
  animation:hl-draw .85s cubic-bezier(.5,0,.2,1) .5s forwards;
}
@keyframes hl-draw{to{stroke-dashoffset:0}}

/* Beers. A mock control among real ones, so it is drawn as a nudge:
   tinted, with the can rocking every few seconds until it is used.

   THE TINT IS A THIRD OF WHAT IT WAS. At 20% amber it was the only
   filled field in the row and it read as a validation error — the one
   thing on the bar somebody had got wrong — rather than as the one thing
   left to try. A wash you notice without naming is enough; the can
   rocking is what does the actual asking. Under the pointer it takes the
   same lift as every other field, so it stops being special exactly when
   it becomes the field you are using. */
.sb-beers{background:color-mix(in srgb, var(--wa) 7%, transparent)}
.sb-beers:hover,.sb-beers:focus-within{
  background:var(--surface);
  box-shadow:0 1px 2px -1px rgba(var(--sh),.2), 0 10px 22px -12px rgba(var(--sh),.5);
}
.sb-beers b{
  display:flex; align-items:center; gap:7px;
  font-size:14.5px; line-height:1.35; font-weight:500; color:var(--ink);
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
.sb-beers .ic{width:15px; height:15px; flex:none; color:#B07600}
.sb-beers:hover .ic{animation:none}
.sb-beers .ic{animation:beer-rock 4.5s ease-in-out 1.6s infinite}
@keyframes beer-rock{
  0%,86%,100%{transform:rotate(0)}
  90%{transform:rotate(-13deg)}
  94%{transform:rotate(11deg)}
}

/* the booking bar 
   One frosted pill, four fields and the ocean-fill control. This is
   the first thing on the page: you can start a charter from here
   without being sent anywhere else first. */
.searchbar{
  display:grid; align-items:center;
  grid-template-columns:1.2fr .78fr .84fr 1.15fr .8fr auto;
  gap:2px; padding:6px 6px 6px 4px;
  background:color-mix(in srgb, var(--surface) 74%, transparent);
  backdrop-filter:blur(18px) saturate(165%); -webkit-backdrop-filter:blur(18px) saturate(165%);
  border:1px solid color-mix(in srgb, var(--ink) 10%, transparent);
  border-radius:var(--r-btn);
  box-shadow:0 2px 4px -2px rgba(var(--sh),.13), 0 24px 44px -26px rgba(var(--sh),.62);
}

/* ---- A FIELD LIFTS, IT DOES NOT DARKEN ----
   Hover used to lay a 4% ink wash over the field, which is a grey smudge
   on a bar that is already translucent over moving water: on the hero it
   was very nearly invisible, and where it did show it read as the field
   being disabled rather than as the field being under the pointer.
   A control you are about to press should come TOWARD you. So the field
   becomes an opaque pill with its own shadow, standing off a bar that is
   translucent — which is the same move the boat cards, the sea chip and
   the drawer all make, and the only one on this site that means "this
   one, now". */
.sb-field{
  position:relative; display:grid; gap:0; padding:8px 16px;
  border-radius:var(--r-btn); cursor:pointer; min-width:0;
  transition:background .18s ease, box-shadow .18s ease;
}
.sb-field:hover,.sb-field:focus-within{
  background:var(--surface);
  box-shadow:0 1px 2px -1px rgba(var(--sh),.2), 0 10px 22px -12px rgba(var(--sh),.5);
}

/* ---- and the rules beside it get out of the way ----
   The divider was an inset box-shadow, which is the same property the
   lift above needs, so the two could not both exist. It is a pseudo
   now — and it is a short hairline centred on the row rather than a
   full-height edge, because a line the height of the field turns five
   controls into a table of five cells.
   Both neighbours of the live field drop theirs: a raised pill with a
   rule welded to its left edge looks stuck to the thing beside it. */
.sb-field + .sb-field::before{
  content:""; position:absolute; left:-1px; top:50%; width:1px; height:24px;
  transform:translateY(-50%); border-radius:1px;
  background:color-mix(in srgb, var(--ink) 13%, transparent);
  transition:opacity .18s ease;
}
.sb-field:hover::before,
.sb-field:focus-within::before,
.sb-field:hover + .sb-field::before,
.sb-field:focus-within + .sb-field::before{opacity:0}

.sb-field > span{
  font-size:9.5px; line-height:1.45; letter-spacing:.11em; text-transform:uppercase;
  color:var(--muted); font-weight:600;
  transition:color .18s ease;
}
/* The label is what the field is; under the pointer it stops being a
   caption and becomes the question being answered. */
.sb-field:hover > span,.sb-field:focus-within > span{color:var(--ink)}
.sb-field input,.sb-field select{
  border:none; background:none; padding:0; margin:0; width:100%; min-width:0;
  font-family:"Lexend",sans-serif; font-size:14.5px; line-height:1.35;
  font-weight:500; color:var(--ink);
  appearance:none; -webkit-appearance:none; cursor:pointer;
  text-overflow:ellipsis; white-space:nowrap; overflow:hidden;
}
.sb-field input:focus,.sb-field select:focus{outline:none}
.sb-field:focus-within{outline:2.5px solid var(--ac); outline-offset:1px}
/* The glass alone, in both states. Five labelled fields have already said
   what this bar does by the time the eye gets here, so the word was only
   taking width away from the fields that carry meaning. */
.sb-go{
  width:48px; height:48px; padding:0; border-radius:50%; flex:none;
  transition:transform .18s ease, box-shadow .18s ease, background-color .18s ease,
             width .34s cubic-bezier(.2,.9,.3,1), height .34s cubic-bezier(.2,.9,.3,1);
}
.sb-go .ic{width:20px; height:20px; transition:transform .22s cubic-bezier(.2,.9,.3,1)}
/* A row has no room for it and does not need it; the folded bar below
   turns it back on. Not `hidden` on the element: the accessible name is
   the aria-label either way, and a span the CSS can switch is one less
   thing for a script to keep in step. */
.sb-go-t{display:none}

/* THE WRAPPER IS NOT A BOX until the phone needs it to be one.
   `display:contents` means the five fields and the button stay direct
   children of the bar's grid, so every rule and every `+` between them
   is written exactly as it was before the wrapper existed. It is here
   only so that the docked sheet on a phone has something to BE: without
   it the sheet would have to be the form itself, the form would have to
   leave the header to become the sheet, and the header would collapse
   around the hole where the pill had been. */
.sb-body{display:contents}
/* Both belong to the docked phone bar and nothing else draws them. */
.sb-sheet-tabs{display:none}
.sb-summary{display:none}
/* It is the one coral object in the bar and the only thing here that
   leaves the page, so it answers the pointer with more than a colour. */
.sb-go:hover{transform:scale(1.06)}
.sb-go:hover .ic{transform:rotate(-8deg)}
.sb-go:active{transform:scale(.97)}

/* docked: the same bar, compressed.
   The second line under When is what sets the height of the whole bar, so
   compressing means dropping that line first and the paddings second. */
.searchbar.is-docked{
  flex:1 1 auto; min-width:0; margin:0;
  grid-template-columns:minmax(0,1.15fr) minmax(0,.74fr) minmax(0,.8fr) minmax(0,1fr) minmax(0,.74fr) 40px;
  gap:2px; padding:4px 4px 4px 3px;
  /* In the hero the bar is 72% and the sea reads through it, which is the
     point. Docked it spends its life over photographs, so it stops being
     a window and becomes a surface. */
  background:var(--surface);
  border-color:color-mix(in srgb, var(--ink) 14%, transparent);
  box-shadow:0 1px 3px -1px rgba(var(--sh),.18), 0 14px 28px -18px rgba(var(--sh),.6);
}
.searchbar.is-docked .sb-field{padding:6px 13px}
/* Docked the bar is a solid surface rather than a window, so a pill of
   the same surface would not read at all: it goes to white, and the
   shadow tightens because the whole bar is smaller. */
.searchbar.is-docked .sb-field:hover,
.searchbar.is-docked .sb-field:focus-within{
  background:#fff;
  box-shadow:0 1px 2px -1px rgba(var(--sh),.22), 0 7px 16px -10px rgba(var(--sh),.5);
}
.searchbar.is-docked .sb-field + .sb-field::before{height:20px}
.searchbar.is-docked .sb-field > span{font-size:8.5px; letter-spacing:.1em}
.searchbar.is-docked .sb-val,
.searchbar.is-docked .sb-beers b{font-size:13.5px}
.searchbar.is-docked .sb-val em{display:none}
/* Below 1040 the undocked bar folds to two rows and the button takes a
   row of its own. Docked it never folds, so it has to be put back into
   its own column or it drops under the fields. */
.searchbar.is-docked .sb-go{grid-column:auto; width:40px; height:40px; border-radius:50%}
.searchbar.is-docked .sb-go .ic{width:18px; height:18px}
/* Docked is a row at every width, so the folded bar's word is off here
   rather than in the phone query -- between 901 and 1040 the bar folds
   and can also be docked, and the word would land inside a 40px disc. */
.searchbar.is-docked .sb-go-t{display:none}

/* availability */
.avail-head{
  display:flex; align-items:flex-end; justify-content:space-between;
  gap:20px; flex-wrap:wrap; margin-bottom:clamp(28px,3.5vw,44px);
}
.avail-head .sub{margin-top:8px}
.boat-foot + .fine{margin-top:-2px}

/* the pillars 
   A full-bleed band of water with the four pillars standing on it. */
.pillars-sec{position:relative; overflow:hidden}
.pillars-water{
  position:absolute; inset:0; z-index:0; pointer-events:none; opacity:.8;
  -webkit-mask-image:linear-gradient(transparent 0%, #000 16%, #000 84%, transparent 100%);
  mask-image:linear-gradient(transparent 0%, #000 16%, #000 84%, transparent 100%);
}
.pillars-water canvas{width:100%; height:100%; display:block}
.pillars-sec .wrap{position:relative; z-index:2}
.pillar{
  display:grid; gap:11px; align-content:start; padding:26px 24px 30px;
  background:color-mix(in srgb, var(--surface) 62%, transparent);
  border:var(--cardbd); border-radius:var(--r-card); box-shadow:var(--elev);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
}
.pill-n{
  font-family:"Bricolage Grotesque",sans-serif; font-variation-settings:"wdth" 86;
  font-weight:800; font-size:13px; letter-spacing:.08em;
  color:var(--ac); opacity:.85;
}
.pillar p{font-size:14.5px; color:var(--muted)}

/* provisions & amenities */
/* The menu takes more of the page than it did. It is two columns now
   rather than one grid of cards, so the width it is given is split twice
   over — at 1.5fr each list came out at 333px, which is a thumbnail, a
   button and about twenty characters. */
.aboard-grid{
  display:grid; grid-template-columns:minmax(0,1.9fr) minmax(0,.8fr);
  gap:clamp(22px,2.8vw,36px); align-items:start;
}
.amen-group{
  font-size:11px; letter-spacing:.16em; text-transform:uppercase;
  font-family:"Lexend",sans-serif; font-weight:600; color:var(--muted);
  margin:26px 0 10px;
}
.amen-group:first-child{margin-top:0}
.amen-list{display:grid; gap:8px}
.amen{
  display:grid; grid-template-columns:auto 1fr auto auto; align-items:center;
  gap:14px; padding:13px 16px;
  background:var(--cardbg); border:var(--cardbd); border-radius:var(--r-card);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  transition:border-color .2s, background .2s;
}
.amen.on{
  border-color:color-mix(in srgb, var(--su) 55%, transparent);
  background:color-mix(in srgb, var(--tint) 55%, transparent);
}
.amen-ic{
  width:38px; height:38px; border-radius:var(--r-chip); flex:none;
  display:grid; place-items:center; font-size:17px; line-height:1;
  background:color-mix(in srgb, var(--tint2) 70%, transparent);
}
.amen-t{display:grid; gap:1px; min-width:0}
.amen-t b{font-size:15px; font-weight:550}
.amen-t i{font-style:normal; font-size:12.5px; color:var(--muted)}
.amen-p{font-size:15px; font-weight:600; white-space:nowrap}
.amen-p em{font-size:11.5px; font-weight:400; color:var(--muted); opacity:1}

.stepper{
  display:flex; align-items:center; gap:2px; flex:none;
  border:1px solid color-mix(in srgb, var(--ink) 12%, transparent);
  border-radius:var(--r-btn); padding:3px;
  background:color-mix(in srgb, var(--surface) 70%, transparent);
}
.stepper button{
  width:28px; height:28px; border:none; border-radius:50%; cursor:pointer;
  background:none; color:var(--ink); font-size:17px; line-height:1;
  font-family:"Lexend",sans-serif; display:grid; place-items:center;
  transition:background .15s, color .15s;
}
.stepper button:hover{background:var(--tint2); color:var(--ac)}
.stepper button:focus-visible{outline:2px solid var(--ac); outline-offset:1px}
.stepper .qty{
  min-width:22px; text-align:center; font-size:14px; font-weight:600;
  font-variant-numeric:tabular-nums;
}

/* The cooler is pinned for the whole menu: what you have picked should
   never be something you scroll back to find. A long list scrolls inside
   the card rather than pushing it past the bottom of the window. */
/* 92px was measured against a header that has since grown a scrim: the
   bar lays the page's own colour back down for its full height and then
   fades it out over another 44 pixels, and the docked search bar drops a
   shadow into the same band. At 92 the top of this card sat inside all of
   it — the word "Your cart" read through a gradient and the card's own top
   edge disappeared. Measured off the header instead, plus the depth of
   what the header throws below itself. */
.amen-basket{
  position:sticky; top:calc(var(--header-h, 76px) + 46px);
  max-height:calc(100vh - var(--header-h, 76px) - 62px);
  overflow:auto; overscroll-behavior:contain;
}
.basket-lines{list-style:none; margin:0; padding:0; display:grid; gap:9px}
.basket-lines li{
  display:flex; justify-content:space-between; gap:14px; align-items:baseline;
  font-size:14px;
}
.basket-lines li span{color:var(--muted)}
.basket-lines li em{font-style:normal; color:var(--muted); font-size:12.5px; opacity:1}
.basket-lines .basket-empty{
  display:block; color:var(--muted); font-size:13.5px; line-height:1.5;
}
/* A line you can strike, on the cart you can still change — the menu's
   own cooler, not the read-only summary the boat page shows. The cross is
   faint until the line is under the pointer rather than absent: it takes
   something off your order, and a control that can do that must never be
   an invisible 24px of hit target sitting next to the price. */
.basket-lines .basket-line{align-items:center}
.basket-lines .basket-line > span{flex:1 1 auto; min-width:0}
.bl-x{
  flex:none; width:24px; height:24px; margin-right:-4px; padding:0;
  border:none; border-radius:50%; background:none; cursor:pointer;
  color:var(--muted); font-size:17px; line-height:1;
  font-family:"Lexend",sans-serif; display:grid; place-items:center;
  opacity:.4; transition:opacity .15s, background .15s, color .15s;
}
.basket-line:hover .bl-x,
.basket-line:focus-within .bl-x,
.bl-x:focus-visible{opacity:1}
.bl-x:hover{background:var(--tint2); color:var(--ac)}
.bl-x:focus-visible{outline:2px solid var(--ac); outline-offset:1px}
@media (hover:none){ .bl-x{opacity:.7} }

/* live AIS board */
.ais-board{padding:0; overflow:hidden}
.ais-bar{
  display:flex; align-items:center; gap:14px; flex-wrap:wrap;
  padding:15px 20px; border-bottom:1px solid color-mix(in srgb, var(--ink) 9%, transparent);
}
.ais-stamp{font-size:13px; color:var(--muted); letter-spacing:.02em}
.ais-legend{
  margin-left:auto; display:flex; align-items:center; gap:5px;
  font-size:12px; color:var(--muted);
}
.ais-legend i{
  width:9px; height:9px; border-radius:50%; display:inline-block;
  margin-left:9px;
}
.ais-legend i:first-child{margin-left:0}
.lg-under{background:var(--su)}
.lg-moored{background:var(--faint)}

.ais-body{display:grid; grid-template-columns:minmax(0,1.85fr) minmax(0,1fr)}
.ais-chart{display:block; width:100%; height:auto; background:color-mix(in srgb, var(--ac) 5%, transparent)}
.ais-land{fill:color-mix(in srgb, var(--se) 20%, var(--bg)); stroke:color-mix(in srgb, var(--ink) 16%, transparent); stroke-width:1.5}
.ais-depth path{fill:none; stroke:color-mix(in srgb, var(--ac) 34%, transparent); stroke-width:1.2; stroke-dasharray:7 9}
.ais-place{
  font-family:"Lexend",sans-serif; font-size:13px; font-weight:600;
  letter-spacing:.16em; fill:color-mix(in srgb, var(--ink) 42%, transparent);
}
.ais-bay{
  font-family:"Lexend",sans-serif; font-size:15px; font-weight:500;
  letter-spacing:.3em; fill:color-mix(in srgb, var(--ac) 62%, transparent);
}

/* Once real tiles arrive the drawn bay steps aside; without a network it
   stays, so the board is never an empty rectangle. */
.ais-tiles image{opacity:.92}
.has-map .ais-land,.has-map .ais-depth,.has-map .ais-place,.has-map .ais-bay{display:none}
.has-map .ais-chart rect:first-of-type{display:none}
.ais-attr{margin-top:8px; font-size:11px}
.ais-attr a{color:var(--muted)}

.ais-trail{stroke:var(--su); stroke-width:2.4; stroke-linecap:round; opacity:.55; stroke-dasharray:3 7}
.ais-halo{fill:var(--su); opacity:.16}
.ais-dot{fill:color-mix(in srgb, var(--surface) 92%, transparent); stroke:var(--su); stroke-width:2}
.ais-arrow{fill:var(--su)}
.ais-name{
  font-family:"Lexend",sans-serif; font-size:14px; font-weight:600;
  fill:var(--ink);
  paint-order:stroke; stroke:color-mix(in srgb, var(--bg) 80%, transparent); stroke-width:4px;
}

.ais-side{
  padding:20px; border-left:1px solid color-mix(in srgb, var(--ink) 9%, transparent);
  display:grid; align-content:start; gap:12px;
}
.ais-side h4{
  font-size:11px; letter-spacing:.16em; text-transform:uppercase;
  font-family:"Lexend",sans-serif; font-weight:600; color:var(--muted);
}
.ais-list{list-style:none; margin:0; padding:0; display:grid; gap:6px}
.ais-row{
  display:grid; grid-template-columns:auto 1fr auto; align-items:center; gap:11px;
  padding:11px 12px; border-radius:14px;
  background:color-mix(in srgb, var(--surface) 55%, transparent);
  border:1px solid color-mix(in srgb, var(--ink) 7%, transparent);
}
.ais-swatch{
  width:9px; height:9px; border-radius:50%; background:var(--su); flex:none;
  box-shadow:0 0 0 4px color-mix(in srgb, var(--su) 18%, transparent);
}
/* alongside: grey, and no heading to show */
.ais-vessel.moored .ais-halo{fill:var(--faint)}
.ais-vessel.moored .ais-dot{stroke:var(--faint)}
.ais-vessel.moored .ais-arrow{display:none}
.ais-row.moored .ais-swatch{
  background:var(--faint); box-shadow:0 0 0 4px color-mix(in srgb, var(--faint) 18%, transparent);
}
.ais-who{display:grid; gap:1px; min-width:0}
.ais-who b{font-size:13.5px; font-weight:550}
.ais-who i{
  font-style:normal; font-size:11px; color:var(--muted);
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
.ais-tel{display:grid; justify-items:end; gap:1px; flex:none}
.ais-tel b{font-size:13.5px; font-weight:600}
.ais-tel i{font-style:normal; font-size:11px; color:var(--muted)}
.ais-foot{margin-top:4px}

/* the phone 
   iPhone 17 Pro: titanium rail, black bezel, Dynamic Island,
   home indicator. Aspect ratio 1206/2622. */
.phone{width:min(300px, 78vw); margin-inline:auto; filter:drop-shadow(0 34px 60px rgba(var(--sh),.28))}
.frame{
  background:linear-gradient(150deg,#9AA0A8,#4A4E55 20%,#7B8189 44%,#33373C 70%,#868C94);
  border-radius:16.4%/7.6%; padding:2px;
  box-shadow:0 22px 46px -26px rgba(0,0,0,.82), 0 1px 0 rgba(255,255,255,.28) inset;
}
.bezel{background:#050506; border-radius:15.6%/7.2%; padding:3px}
.scr{
  position:relative; background:var(--bg); border-radius:13.6%/6.3%; overflow:hidden;
  aspect-ratio:1206/2622; display:flex; flex-direction:column; color:var(--ink);
  font-size:11px; line-height:1.45;
}
.island{
  position:absolute; top:1.35%; left:50%; transform:translateX(-50%);
  width:31.5%; height:4.1%; background:#000; border-radius:99px; z-index:9;
}
.homebar{
  position:absolute; bottom:.85%; left:50%; transform:translateX(-50%);
  width:33%; height:3.4px; background:var(--ink); opacity:.3; border-radius:99px; z-index:9;
}
/* vertical padding resolves against width, which is always definite here */
.status{
  position:relative; z-index:8; display:flex; align-items:center; justify-content:space-between;
  padding:4.6% 7.5% 1.4%; flex:none;
}
.stime{font-size:9.5px; font-weight:700; letter-spacing:.01em}
.sright{display:flex; align-items:center; gap:3.5px}
.cellbars{display:flex; align-items:flex-end; gap:1px}
.cellbars i{width:2px; background:currentColor; border-radius:.5px; display:block}
.cellbars i:nth-child(1){height:3px} .cellbars i:nth-child(2){height:4.5px}
.cellbars i:nth-child(3){height:6px} .cellbars i:nth-child(4){height:7.5px}
.wifi{width:11px; height:8.5px; fill:currentColor}
.batt{
  width:16px; height:8.5px; border:1px solid currentColor; border-radius:2.6px;
  padding:1.2px; position:relative; opacity:.92;
}
.batt b{display:block; height:100%; width:76%; background:currentColor; border-radius:1px}
.batt::after{
  content:""; position:absolute; right:-2.6px; top:32%; height:36%; width:1.6px;
  background:currentColor; border-radius:0 1.5px 1.5px 0; opacity:.55;
}
.scr-water{
  position:absolute; top:0; left:0; right:0; height:34%; z-index:0; pointer-events:none;
  -webkit-mask-image:linear-gradient(#000 0%, #000 46%, transparent 100%);
  mask-image:linear-gradient(#000 0%, #000 46%, transparent 100%);
}
.scr-water canvas{width:100%; height:100%; display:block}
.scr-body{
  position:relative; z-index:2; flex:1; min-height:0; overflow:hidden;
  display:flex; flex-direction:column; padding:8px 12px 12px; gap:8px;
}

/* in-phone miniatures , the app's own components at app scale */
.p-top{display:flex; align-items:center; justify-content:space-between; gap:6px}
.p-wordmark{height:9.5px; width:auto}
.p-search{
  display:flex; align-items:center; gap:5px; background:var(--surface);
  border:var(--cardbd); border-radius:var(--r-btn); padding:5px 5px 5px 9px;
  box-shadow:var(--elev);
}
.p-sf{display:grid; flex:1; min-width:0}
.p-sf i{font-size:7px; color:var(--muted); font-style:normal}
.p-sf b{font-size:8.5px}
.p-sbtn{
  width:22px; height:22px; border-radius:50%; background:var(--btnbg); color:var(--onacc);
  display:grid; place-items:center; font-size:11px; flex:none;
}
.p-rowline{display:flex; justify-content:space-between; font-size:8px}
.p-rowline .lo{color:var(--su-text); font-weight:600}
.p-rowline .ct{color:var(--muted)}
.p-bcard{
  background:var(--cardbg); border:var(--cardbd); border-radius:var(--r-card);
  overflow:hidden; box-shadow:var(--elev);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
}
.p-bimg{position:relative; aspect-ratio:16/9}
.p-bimg img{width:100%; height:100%; object-fit:cover}
.p-badge{
  position:absolute; left:6px; top:6px; background:var(--surface); color:var(--ink);
  border-radius:var(--r-chip); padding:2px 6px; font-size:7px; font-weight:700;
}
.p-bbody{padding:7px 8px; display:grid; gap:3px}
.p-bt{display:flex; justify-content:space-between; align-items:baseline; gap:6px}
.p-bt b{font-size:10px}
.p-bt span{font-size:8px; color:var(--muted)}
.p-tabs{
  display:flex; justify-content:space-around; padding:5px 0 7px; margin:auto -12px -12px;
  background:var(--surface); border-top:1px solid var(--line); flex:none;
}
.p-tabs i{font-size:7.5px; font-style:normal; color:var(--muted); display:grid; justify-items:center; gap:2px}
.p-tabs i.on{color:var(--ac)}
.p-tabs i b{font-size:11px; font-weight:400}

/* proof strip */
.strip{
  display:grid; grid-template-columns:repeat(4,1fr); gap:1px;
  border-radius:var(--r-card); overflow:hidden;
  background:color-mix(in srgb, var(--ink) 8%, transparent);
  border:var(--cardbd); box-shadow:var(--elev);
}
.strip > div{
  background:color-mix(in srgb, var(--surface) 78%, transparent);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  padding:26px 22px; text-align:center;
}
.strip b{
  display:block; font-family:"Bricolage Grotesque",sans-serif; font-weight:800;
  font-variation-settings:"wdth" 86; font-size:clamp(28px,3.4vw,40px);
  line-height:1; letter-spacing:-.02em; margin-bottom:8px;
}
.strip span{font-size:13px; color:var(--muted); line-height:1.4; display:block}

/* The fleet.
   There are six boats, not sixty. A three-up grid spends most of its life
   showing an orphan row and a hole where a fourth card would go, which
   makes a curated fleet look like a shop that has run out. Two up, larger,
   with the photograph big enough to be worth looking at: the same six
   boats then read as the whole list rather than the end of one. */
.grid-fleet{
  display:grid; grid-template-columns:repeat(2,minmax(0,1fr));
  gap:clamp(20px,2.4vw,30px);
}
/* Two up only moves the orphan: five results give 2 + 2 + 1 and the last
   card still sits beside a hole. So an odd last card takes the whole row
   and lies down — the row it is on reads as a decision rather than as the
   place the grid ran out. */
.grid-fleet > .boat:last-child:nth-child(odd){
  grid-column:1 / -1;
  grid-template-columns:48% minmax(0,1fr);
  grid-template-rows:auto;
}
.grid-fleet > .boat:last-child:nth-child(odd) .boat-img{aspect-ratio:auto; min-height:290px}
.grid-fleet > .boat:last-child:nth-child(odd) .boat-body{align-content:center; padding:26px 32px}
/* The save button and the promo tag are siblings of the photograph, not
   children of it, so they hang off the card. On a card that is half
   photograph they have to be pulled back over it: the body is the other
   52%, so that plus the usual inset is how far in from the right they go. */
.grid-fleet > .boat:last-child:nth-child(odd) .fav,
.grid-fleet > .boat:last-child:nth-child(odd) .promo-tag{right:calc(52% + 12px)}

/* generic grids */
.grid-3{display:grid; grid-template-columns:repeat(3,minmax(0,1fr)); gap:20px}
.grid-4{display:grid; grid-template-columns:repeat(4,minmax(0,1fr)); gap:18px}
.grid-2{display:grid; grid-template-columns:repeat(2,minmax(0,1fr)); gap:clamp(24px,4vw,54px)}
.split{display:grid; grid-template-columns:minmax(0,1fr) minmax(0,.86fr); gap:clamp(30px,5vw,66px); align-items:center}

/* steps */
.step{display:grid; gap:12px; align-content:start}
.step .n{
  font-family:"Bricolage Grotesque",sans-serif; font-variation-settings:"wdth" 86;
  font-weight:800; font-size:15px; width:40px; height:40px; border-radius:50%;
  display:grid; place-items:center; background:var(--btnbg); color:var(--onacc);
  box-shadow:var(--btnsh); position:relative; overflow:hidden; isolation:isolate;
}
.step .n::before{
  content:""; position:absolute; inset:0; z-index:-1;
  background-image:var(--wtex); background-size:200% 200%;
  opacity:var(--btn-tex-o); mix-blend-mode:overlay;
  animation:btndrift 11s ease-in-out infinite alternate;
}
.step p{color:var(--muted); font-size:15.5px}

/* role cards */
.role{
  display:grid; gap:12px; align-content:start; padding:24px 22px 26px;
  background:var(--cardbg); border:var(--cardbd); border-radius:var(--r-card);
  box-shadow:var(--elev); backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  transition:transform .22s ease, box-shadow .22s ease;
}
.role:hover{transform:translateY(-4px); box-shadow:0 2px 4px -2px rgba(var(--sh),.16), 0 22px 38px -22px rgba(var(--sh),.55)}
.ric{
  width:42px; height:42px; border-radius:var(--r-chip); display:grid; place-items:center;
  font-size:19px; flex:none; line-height:1;
}
.r1{background:var(--tint); color:var(--su-text)}
.r2{background:var(--tint2); color:var(--ac)}
.r3{background:var(--tint3); color:#4E9331}
.r4{background:color-mix(in srgb, var(--hi) 18%, var(--bg)); color:#D63A75}
.role p{font-size:14.5px; color:var(--muted)}
.role ul{margin:2px 0 0; padding-left:0; list-style:none; display:grid; gap:7px}
.role li{font-size:13.5px; color:var(--muted); display:flex; gap:8px; align-items:flex-start}
.role li::before{content:"—"; color:var(--muted); flex:none}

/* fleet */
.boat{
  border-radius:var(--r-card); overflow:hidden; background:var(--cardbg);
  border:var(--cardbd); box-shadow:var(--elev);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  display:grid; grid-template-rows:auto 1fr;
  transition:transform .22s ease, box-shadow .22s ease;
}
.boat:hover{transform:translateY(-4px); box-shadow:0 2px 4px -2px rgba(var(--sh),.16), 0 24px 42px -24px rgba(var(--sh),.6)}
.boat-img{position:relative; aspect-ratio:16/10; overflow:hidden}
.boat-img img{width:100%; height:100%; object-fit:cover; transition:transform .5s ease}
.boat:hover .boat-img img{transform:scale(1.045)}
.boat-img .pill{position:absolute; left:12px; top:12px; box-shadow:0 2px 8px -3px rgba(var(--sh),.5)}
/* Somewhere you have already been this visit. It sits along the bottom of
   the photograph so it never has to share a corner with Instant book or a
   promotion, and it is the quietest thing on the card: a reminder, not a
   claim about the boat. */
.boat-img .pill.seen{
  top:auto; bottom:12px; left:12px;
  background:color-mix(in srgb, var(--surface) 88%, transparent);
  color:var(--muted); font-weight:600;
  backdrop-filter:blur(6px); -webkit-backdrop-filter:blur(6px);
}
.pill.seen .ic{width:13px; height:13px; opacity:.8}
.boat-body{padding:18px 20px 22px; display:grid; gap:10px; align-content:start}
.boat-head{display:flex; justify-content:space-between; align-items:baseline; gap:12px}
.boat-head h3{font-size:20px}
/* At two up the card has room to be looked at rather than scanned, so the
   photograph gets a wider crop and the name gets a size to match. */
.grid-fleet .boat-img{aspect-ratio:16/9}
.grid-fleet .boat-body{padding:22px 26px 26px; gap:11px}
.grid-fleet .boat-head h3{font-size:23px}
.grid-fleet .price{font-size:29px}
.rate{font-size:13.5px; color:var(--muted); white-space:nowrap; display:inline-flex; gap:4px; align-items:center}
.boat-meta{font-size:14px; color:var(--muted)}
.boat-foot{
  display:flex; align-items:baseline; justify-content:space-between; gap:12px;
  margin-top:4px; padding-top:14px;
  border-top:1px solid color-mix(in srgb, var(--ink) 8%, transparent);
}
.price{font-family:"Bricolage Grotesque",sans-serif; font-variation-settings:"wdth" 86;
  font-weight:800; font-size:25px; letter-spacing:-.02em}
.price small{font-size:13px; font-weight:400; color:var(--muted); font-family:"Lexend",sans-serif}

/* price breakdown (the transparency panel) */
.breakdown{display:grid; gap:0}
.breakdown .row{
  display:flex; justify-content:space-between; align-items:baseline; gap:16px;
  padding:14px 0; border-bottom:1px solid color-mix(in srgb, var(--ink) 8%, transparent);
  font-size:15px;
}
.breakdown .row:last-child{border-bottom:none}
.breakdown .row span:first-child{color:var(--muted)}
.breakdown .row b{font-variant-numeric:tabular-nums; font-weight:600}
.breakdown .row.promo span:first-child,
.breakdown .row.promo b{color:var(--su-text)}
.breakdown .row.total{
  padding-top:18px; margin-top:4px;
  border-top:1.5px solid color-mix(in srgb, var(--ink) 14%, transparent);
}
.breakdown .row.total span:first-child{color:var(--ink); font-weight:600; font-size:17px}
.breakdown .row.total b{font-family:"Bricolage Grotesque",sans-serif; font-variation-settings:"wdth" 86;
  font-weight:800; font-size:29px; letter-spacing:-.02em}
/* a row that carries a footnote hands its rule down to the note, so the
   line sits under the pair rather than through the middle of it */
.breakdown .row.has-note{border-bottom:none; padding-bottom:2px}
.breakdown .note{
  font-size:12.5px; color:var(--muted); line-height:1.45;
  padding-bottom:13px; border-bottom:1px solid color-mix(in srgb, var(--ink) 8%, transparent);
}

/* safety */
.safety-item{display:flex; gap:15px; align-items:flex-start; padding-block:18px}
.safety-item + .safety-item{border-top:1px solid color-mix(in srgb, var(--ink) 8%, transparent)}
.safety-ic{
  width:38px; height:38px; border-radius:var(--r-chip); flex:none; display:grid;
  place-items:center; background:var(--tint2); color:var(--ac); font-size:17px;
}
.safety-item h4{margin-bottom:5px}
.safety-item p{font-size:14.5px; color:var(--muted)}

.live-card{position:relative; border-radius:var(--r-card); overflow:hidden;
  border:var(--cardbd); box-shadow:var(--elev)}
.live-card img{width:100%; aspect-ratio:4/3; object-fit:cover}
.live-card .pill{position:absolute; left:14px; top:14px}
.live-foot{
  position:absolute; left:12px; right:12px; bottom:12px; padding:14px 16px;
  border-radius:calc(var(--r-card) - 8px);
  background:color-mix(in srgb, var(--surface) 62%, transparent);
  backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  border:var(--cardbd); display:flex; align-items:center; gap:12px;
}
.live-foot img{width:38px; height:38px; border-radius:50%; object-fit:cover; aspect-ratio:1; flex:none}
.live-foot b{display:block; font-size:14.5px}
.live-foot i{font-style:normal; font-size:12.5px; color:var(--muted)}

/* FAQ */
.faq{display:grid; gap:12px; max-width:840px}
.faq details{
  background:var(--cardbg); border:var(--cardbd); border-radius:var(--r-card);
  box-shadow:var(--elev); backdrop-filter:var(--blur); -webkit-backdrop-filter:var(--blur);
  padding:4px 24px; transition:border-color .2s;
}
.faq details[open]{border-color:color-mix(in srgb, var(--ac) 30%, transparent)}
.faq summary{
  cursor:pointer; list-style:none; padding:20px 34px 20px 0; position:relative;
  font-size:16.5px; font-weight:500; color:var(--ink);
}
.faq summary::-webkit-details-marker{display:none}
.faq summary::after{
  content:"+"; position:absolute; right:0; top:50%; transform:translateY(-50%);
  font-size:24px; font-weight:300; color:var(--ac); line-height:1; transition:transform .25s;
}
.faq details[open] summary::after{transform:translateY(-50%) rotate(45deg)}
.faq summary:focus-visible{outline:2.5px solid var(--ink); outline-offset:3px; border-radius:8px}
.faq .answer{padding:0 0 22px; color:var(--muted); font-size:15.5px; max-width:64ch}

/* closing CTA */
.cta{position:relative; overflow:hidden; border-radius:var(--r-card);
  border:var(--cardbd); box-shadow:var(--elev)}
.cta-water{position:absolute; inset:0; z-index:0; opacity:.72}
.cta-water canvas{width:100%; height:100%; display:block}
.cta-inner{
  position:relative; z-index:2; padding:clamp(40px,5.5vw,72px) clamp(26px,5vw,60px) 0;
  display:grid; grid-template-columns:minmax(0,1fr) minmax(0,.62fr);
  gap:clamp(28px,4vw,56px); align-items:end;
  background:color-mix(in srgb, var(--surface) 60%, transparent);
  backdrop-filter:blur(11px) saturate(145%); -webkit-backdrop-filter:blur(11px) saturate(145%);
}
.cta-copy{padding-bottom:clamp(40px,5.5vw,72px); display:grid; gap:20px; align-content:center}
.cta-copy p{color:color-mix(in srgb, var(--ink) 74%, transparent); max-width:46ch}
.cta-copy .fine{margin-top:-8px}
/* the phone rises out of the bottom edge of the panel */
.cta-inner .phone{width:min(268px,100%); margin:0 auto -2px; align-self:end}
.cta-inner p{max-width:52ch; color:var(--muted)}

/* footer */
.site-footer{
  border-top:1px solid color-mix(in srgb, var(--ink) 8%, transparent);
  /* The last 34px are the bottom of the document, and with the page
     drawn under the home indicator they are the 34px the indicator is
     sitting on -- the copyright line and the DIMAR note read through a
     white bar. Everywhere without one the inset is 0. */
  padding-block:clamp(44px,6vw,68px) calc(34px + env(safe-area-inset-bottom));
}
.footer-grid{display:grid; grid-template-columns:1.5fr repeat(3,1fr); gap:34px; margin-bottom:44px}
.footer-grid h4{font-size:12px; letter-spacing:.15em; text-transform:uppercase;
  color:var(--muted); font-family:"Lexend",sans-serif; font-weight:600; margin-bottom:14px}
.footer-grid ul{list-style:none; margin:0; padding:0; display:grid; gap:9px}
.footer-grid a{text-decoration:none; color:var(--muted); font-size:14.5px; transition:color .18s}
.footer-grid a:hover{color:var(--ac)}
.footer-brand .wordmark{margin-bottom:16px; width:116px; height:29px}
.footer-brand p{font-size:14px; color:var(--muted); max-width:34ch}
.footer-bot{
  display:flex; flex-wrap:wrap; gap:12px 26px; align-items:center;
  padding-top:26px; border-top:1px solid color-mix(in srgb, var(--ink) 8%, transparent);
  font-size:13px; color:var(--muted);
}
.footer-bot .spacer{margin-left:auto}

/* reveal on scroll */
.rv{opacity:0; transform:translateY(16px); transition:opacity .6s ease, transform .6s ease}
.rv.in{opacity:1; transform:none}
@media (prefers-reduced-motion:reduce){.rv{opacity:1; transform:none}}

/* responsive */
@media (max-width:1040px){
  /* the search bar folds to two rows before the fields get too narrow
     to read the values in */
  .searchbar{
    grid-template-columns:1fr 1fr; border-radius:26px; padding:8px;
    gap:6px;
  }
  .sb-field{border-radius:18px}
  /* THE HAIRLINE BETWEEN TWO FIELDS ONLY MEANS ANYTHING ALONG A ROW.
     It is a 1px rule hung at left:-1px of every field after the first,
     which is where the seam is while the five of them sit side by side.
     Folded, there is no seam there: the fields are stacked, so all it
     draws is a stray 24px tick floating off the left edge of the card,
     four of them down the bar. This rule used to say `box-shadow:none`,
     from when the divider WAS an inset shadow — it has been a pseudo
     since the fields learned to lift under the pointer, and the tick
     has been on every phone since. */
  .sb-field + .sb-field::before{display:none}
  /* ACROSS THE CARD, NOT A CIRCLE STRETCHED ACROSS IT.
     The button is 48x48 with border-radius:50% along a row, which is a
     disc; given the whole width of a folded bar the same 50% resolves
     per-axis and it draws a 350x48 ELLIPSE — a coral lozenge with its
     own corners cut away, on the one control the entire site is steered
     with. A pill is what a full-width button is, so say the radius in
     pixels rather than in halves. */
  .sb-go{
    grid-column:1 / -1; width:100%; height:52px; border-radius:999px;
    display:inline-flex; align-items:center; justify-content:center; gap:10px;
  }
  .sb-go-t{display:inline; font-size:16px; font-weight:600}
  .aboard-grid{grid-template-columns:1fr}
  .amen-basket{position:static}
}
@media (max-width:980px){
  .grid-4{grid-template-columns:repeat(2,minmax(0,1fr))}
  .strip{grid-template-columns:repeat(2,1fr)}
  .split{grid-template-columns:1fr}
  .footer-grid{grid-template-columns:1fr 1fr; gap:30px}
  .ais-body{grid-template-columns:1fr}
  .ais-side{border-left:none; border-top:1px solid color-mix(in srgb, var(--ink) 9%, transparent)}
  .cta-inner{grid-template-columns:1fr; text-align:center; justify-items:center}
  .cta-copy{padding-bottom:0; justify-items:center}
  .cta-copy .btn-row{justify-content:center}
  .cta-inner .phone{margin-top:8px}
}
/* The header runs out of room before the page does , five links and two
   CTAs stop fitting around 900px, so it collapses to a drawer there while
   the content grids carry on to 760px. */
@media (max-width:900px){
  /* With the nav out of the flow there is nothing left to shrink-wrap
     around, so the bar takes the full column again on a phone. */
  .header-bar{width:auto}
  /* The drawer hangs off the floating bar as a second floating card in
     the same shell, and it is opaque rather than frosted: nested inside
     the bar's own backdrop-filter, a translucent panel composites against
     a blurred backdrop twice and the hero reads straight through it. */
  /* The row itself is the pill here, and the drawer measures itself
     against the whole of it rather than hanging off the button: at this
     width a 248px panel tucked under one corner is narrower than the
     thing it belongs to. */
  .header-bar > .nav{
    top:calc(100% + 10px); left:0; right:0; width:auto; max-width:none;
  }
  .nav a{padding:13px 16px; font-size:16px}
  .nav a::before{transform:scale(1)}
  /* The phone header used to wrap the whole row in a dark pill, because
     the row held a dark slab and a mark and the two needed to be made one
     object. There is no slab any more — the mark, the button and the two
     glyphs all stand on the page at every width — so the row is a row.
     Static AND unanimated, so the drawer below measures itself against
     the whole of it. position:static alone is not enough: an element with
     an animation on transform is a containing block for absolutely
     positioned descendants even while the animation is only filling its
     last frame at transform:none. */
  .header-bar{
    position:static; flex:1; min-width:0; justify-content:flex-end;
    padding:0; gap:8px; animation:none;
  }
  .site-header .wrap{gap:12px}
  /* The same geometry, stepped down: 173px of word instead of 250. The
     phone does not step down as far proportionally as the desktop went
     up — a 94px disc plus the header's own padding would be a 126px
     sticky bar on a 667px screen, which is a fifth of the page spent on
     the mark before anything else gets a row. */
  .wm-lockup{
    --wm-w:173px; --wm-h:43.25px; --wm-m-w:39.4px;
    --wm-agik-x:39.7px; --wm-agik-w:134px; --disc:65px;
  }
  /* and the phone's badge holds at its own old size, for the same reason
     the desktop's does. This has to be here rather than inherited: the
     desktop `.wm-shut .wm-lockup` outranks a bare `.wm-lockup` in the
     media query, so without it the phone would dock to a 78px badge. */
  .wm-shut .wm-lockup{
    --wm-w:144px; --wm-h:36px; --wm-m-w:32.9px;
    --wm-agik-x:33px; --wm-agik-w:111px; --disc:54px;
  }
  .brand{padding-left:10px}
  /* The nav is out of the flow in the drawer, so nothing is left to push
     the toggle over — the CTA has to claim the free space itself. Two
     plateless icons need no air between them: their own hit areas are
     the spacing. */
  .header-cta{margin-left:auto; gap:2px}
  /* Four words never fitted on this row. The button is not droppable —
     it is the only thing in the header a boat owner came for — so
     site.js puts it in the drawer at this width instead, where it has a
     column to itself and keeps its words. Nothing to do here. */
}

/* ---- and one step further down, for the narrowest phones ----
   THE HEADER IS A ROW OF FOUR THINGS AND THE ROW HAS A WIDTH.
   10px of brand inset, 173px of wordmark, a 12px gap and three 44px
   discs with 2px between them is 331px of content; a 360px phone offers
   320 between its gutters and a 320px one offers 280. It fitted while
   the discs were 42, 42 and 38 -- and then only just, which is not
   fitting, it is not having overflowed yet. Raising them to a size a
   thumb can actually hit spent the last of the slack, and the row went
   sixteen pixels off the right edge of every page.

   THE DISCS ARE NOT WHAT GIVES. They are the three controls in the
   header and they are already at the floor of what a finger can find;
   taking them back to 38 to keep a wordmark whole is choosing the
   decoration over the interface. So the mark steps down instead, as it
   already steps down once from the desktop's 250px to the phone's 173.
   Every number below is the phone's set at 0.867, which is the scale
   that leaves the row 162px for a mark and puts 12 of them back as
   slack -- the whole lockup is proportional, so one ratio through all
   six keeps the M, the disc and the AGIK in exactly the register they
   were drawn in. */
@media (max-width:380px){
  .wm-lockup{
    --wm-w:150px; --wm-h:37.5px; --wm-m-w:34.2px;
    --wm-agik-x:34.4px; --wm-agik-w:116px; --disc:56.4px;
  }
  /* Shut, the lockup is the disc alone and there is room to spare -- but
     the rule has to be restated for the same reason it is restated in
     the block above: `.wm-shut .wm-lockup` from the desktop outranks a
     bare `.wm-lockup` here, so without this the narrowest phone would
     dock to the widest badge. */
  .wm-shut .wm-lockup{
    --wm-w:125px; --wm-h:31.2px; --wm-m-w:28.5px;
    --wm-agik-x:28.6px; --wm-agik-w:96.2px; --disc:47px;
  }
  .brand{padding-left:4px}
}

/* ---- and the last step, for a 320px screen ----
   The oldest width anything still renders at, and the header has never
   fitted on it: at the sizes this file shipped with, 10px of inset, a
   173px mark, a 12px gap and three discs came to 321px of content inside
   a 280px column, and forty of those pixels hung off the right of every
   page. It was not introduced by the touch sizes above -- those took it
   from forty over to twenty-two -- but a pass that measures every page
   at three widths and leaves one of them scrolling sideways has not
   finished, so it is closed here.

   Twenty-two pixels, found in three places rather than taken out of any
   one: the gap between the mark and the controls goes to 8, the brand's
   own inset to 0, and the mark to 124.7 -- the same 173 base at 0.721,
   which is the scale that makes the lockup exactly the width that is
   left. Below this there is no more to give, and below this there are
   no more phones. */
@media (max-width:345px){
  .site-header .wrap{gap:8px}
  .brand{padding-left:0}
  /* AND DOCKED, AT THIS WIDTH, THE SEA GOES BACK IN THE DRAWER.
     Undocked there is room for all three discs and the reading stays out
     where it can be seen changing, which is the whole argument for it
     being a disc in the header at all. Docked, the row also has to hold
     the bar, and 280px will not carry a badge, three discs and a field
     wide enough to read a place name in -- with the chip out here the
     value gets 62px, which shows `Isla...` and answers nothing.
     So at this one width, in this one state, the working control wins
     over the ambient one: the bar is what somebody scrolling a list of
     results is actually using, and the reading is two rows down the
     drawer under Sea forecast. */
  .docked .sea-slot{display:none}
  .wm-lockup{
    --wm-w:124.7px; --wm-h:31.2px; --wm-m-w:28.4px;
    --wm-agik-x:28.6px; --wm-agik-w:96.6px; --disc:46.9px;
  }
}
@keyframes nav-drop{from{opacity:0; transform:translateY(-10px) scale(.98)} to{opacity:1; transform:none}}

/* ---- docked: the navigation pill closes into one button ----
   At any width, because docking is about the search taking the room, not
   about how wide the window is. These sit after the phone rules and win
   on specificity, which is also how the phone's whole-row pill is undone
   when the row has a search bar in it. */
.docked .site-header .wrap{
  width:100%; max-width:var(--maxw); margin-inline:auto;
  padding:0 var(--gut);
  /* the initial needs air before the bar starts, and less of it on a phone */
  gap:clamp(14px, 2vw, 24px);
  background:none; border:none; box-shadow:none;
  backdrop-filter:none; -webkit-backdrop-filter:none; animation:none;
}
/* Docked, the header is the mark, the search and one button. Everything
   the docked state used to have to undo — the dark slab, the shell type,
   the bare glyphs — is gone from the undocked header too, so the two
   states are one design and this block is down to what genuinely differs:
   the row tightens, and the account glyph goes, because the search bar
   is six fields wide and needs the room, and the drawer's own chip is
   the same link with the account holder's name on it. The header was
   showing it twice. */
.docked .site-header .header-bar{flex:none; width:auto; min-width:0; gap:6px}
.docked .header-cta{gap:6px}
.docked .account-ic{display:none}
/* The drawer's geometry is the same docked or not — it is set once, up
   with the nav — so the only thing left here is the phone override being
   undone: docked, the row is no longer a pill for the panel to match. */
.docked .header-bar > .nav{
  top:calc(100% + 12px); right:0; left:auto;
  width:max(300px, 21vw); max-width:calc(100vw - 2 * var(--gut));
}

/* Inside the drawer: the way in is a row, not a button that happens to be
   at the bottom of a list. It is also the foot of the panel rather than
   another item in it — everywhere you can GO is above the rule, and who
   you are is below it. */
.nav #user-slot{display:block; margin:6px 3px 2px}
/* SIGN IN IS THE ONE SOLID CORAL IN THE DRAWER, the way it is the one
   solid coral everywhere else. On the old black panel it had to be the
   white thing because white was the only bright thing available; on shell
   it can be the button it actually is. --onacc on --su is 6.03:1. */
.nav #user-slot .btn-ghost{
  width:100%; background:var(--su); border-color:transparent; color:var(--onacc);
  font-weight:550; box-shadow:var(--btnsh);
  backdrop-filter:none; -webkit-backdrop-filter:none;
}
.nav #user-slot .btn-ghost:hover{
  background:var(--ac); border-color:transparent; color:var(--onacc); transform:none;
}
/* Signed in there is nothing to press, so the chip is quiet: a name and a
   role on the faintest ground the panel has. */
.nav #user-slot .account-chip{
  width:100%; background:color-mix(in srgb, var(--ink) 5%, transparent);
  border-color:color-mix(in srgb, var(--ink) 10%, transparent);
  backdrop-filter:none; -webkit-backdrop-filter:none;
}
.nav #user-slot .account-chip:hover{border-color:color-mix(in srgb, var(--su) 55%, transparent)}
.nav #user-slot .account-who b{color:var(--ink)}
.nav #user-slot .account-who i{color:var(--muted)}

/* Docked on a phone there is no room for six fields — they shred into
   "Islas …", "A…", "Sat …" and stop being readable at all. Two survive:
   where you are going and when. The rest keep their values and are a
   scroll away in the full bar, and their hidden inputs still submit. */
@media (max-width:900px){
  /* the glass gets a track of its own rather than `auto`: beside two fr
     columns an auto track resolves to nothing and the button collapses */
  .searchbar.is-docked{
    grid-template-columns:minmax(0,1.2fr) minmax(0,1fr) 36px;
    gap:2px; padding:3px;
  }
  /* Descendant, not child: `.sb-body` sits between the bar and its
     fields in the DOM now, and `>` stopped reaching them. It is
     `display:contents`, so the GRID still sees them as its own children
     -- but a selector reads the tree, not the layout. */
  .searchbar.is-docked [data-pick="guests"],
  .searchbar.is-docked [data-pick="kind"],
  .searchbar.is-docked .sb-beers{display:none}
  .searchbar.is-docked .sb-field{padding:5px 11px}
  /* Docked, the bar is a row again inside the header, so the button is
     back to being the glass on its own — 36px of it, which is no place
     for a word. */
  .searchbar.is-docked .sb-go{grid-column:auto; width:36px; height:36px; border-radius:50%}
  .searchbar.is-docked .sb-go .ic{width:16px; height:16px}
  /* the header tightens to make room for the bar it is now carrying */
  .docked .menu-toggle,
  .docked .account-ic{width:36px; height:36px; font-size:16.5px}
  .docked .header-cta{gap:4px}
  .docked .header-bar{margin-left:9px}
}

/* ---- and on a phone the docked bar is a SENTENCE, not a strip ----
   TWO FIELDS IN A HUNDRED AND SIXTY PIXELS IS NEITHER OF THEM.
   Docked, the header is a badge, a bar and two discs, and on a 390px
   screen the bar gets 161 of the 350 that are going. Split two ways with
   an icon in each, that left 62px for WHERE and 51 for WHEN -- and once
   the pin and the calendar had taken 20 of those, the bar that exists to
   keep your criteria on screen for the length of the list was rendering
   `Islas del Rosario` as `I...` and `Sat 5 Sept` as `...`. Cut down to
   one field it read `Islas del Ro...` and said nothing at all about the
   day, the party, or which of the three things you were looking at.

   A CONTROL THAT WILL NOT FIT SHOULD STOP BEING A CONTROL.
   There is no width at which five labelled fields go into a header on a
   phone, and the docked bar does not need to be five fields: nobody
   edits a search from a strip in a header, they READ one from it and
   press it when they want it changed. So it becomes what it is -- a
   sentence about the search, in the two lines the same space holds
   comfortably. What you are looking at and where, then when and with how
   many. Four facts where one was, in less width than the one took.

   AND THE PRESS OPENS ALL OF IT. The bar is still the bar: pressing the
   pill drops the whole thing as a sheet under the header, tabs across
   the top and the five fields under them -- which is also the only place
   boats, food and extras are reachable on a phone once the page has
   scrolled past the chooser at the top of it. */
@media (max-width:560px){
  /* The pill. The bar keeps its own surface, border and shadow from
     `.is-docked`; this only changes its shape and what is inside it. */
  .searchbar.is-docked{
    display:block; grid-template-columns:none;
    padding:0; border-radius:999px; overflow:visible;
  }
  .searchbar.is-docked .sb-body{display:none}
  .searchbar.is-docked .sb-summary{
    display:grid; gap:1px; width:100%; min-height:44px; align-content:center;
    padding:6px 15px; margin:0; border:0; background:none; cursor:pointer;
    border-radius:999px; text-align:left; font-family:"Lexend",sans-serif;
  }
  .searchbar.is-docked .sb-summary:focus-visible{
    outline:2.5px solid var(--ac); outline-offset:2px;
  }
  /* One line each, always: a summary that wraps is a paragraph, and it
     would push the header taller the moment somebody searched a longer
     destination. The first line gives up characters before the second
     does -- a place is recognised from its opening, a date is not. */
  .sb-sum-1,.sb-sum-2{
    display:block; min-width:0;
    white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
  }
  .sb-sum-1{font-size:13.5px; font-weight:600; color:var(--ink); line-height:1.25}
  .sb-sum-2{font-size:11.5px; font-weight:400; color:var(--muted); line-height:1.3}

  /* ---- opened: the whole bar, hanging from the pill it came from ----
     Absolutely positioned against the form -- the form IS the pill -- so
     it drops from it the way a picker panel drops from a field, and it
     is pulled out to the width of the window by `--sb-dx`, the distance
     the pill's own left edge sits from where the sheet wants to start.
     `position:fixed` would be the obvious way to say "as wide as the
     screen" and it is the wrong one: the bar carries a backdrop-filter,
     a filtered element is the containing block for anything fixed inside
     it, and the sheet would have been measured against the pill anyway
     -- silently, and only in some browsers. */
  .searchbar.is-docked.is-sheet .sb-body{
    display:grid; grid-template-columns:1fr; gap:6px; z-index:41;
    position:absolute; top:calc(100% + 10px);
    left:calc(-1 * var(--sb-dx, 0px)); width:calc(100vw - 24px);
    padding:8px; border-radius:26px;
    background:var(--surface); border:var(--cardbd);
    box-shadow:0 3px 8px -4px rgba(var(--sh),.2), 0 30px 54px -28px rgba(var(--sh),.75);
    /* NOT `overflow:auto`, and the picker panels are why. Everything in
       here opens a panel that is positioned against this box, so a
       scroller here is a clip on all five of them: press WHEN and the
       calendar is cut off at the edge of the sheet it came out of.
       It does not need one. The sheet is tabs, five fields and a button
       -- about 420px -- and it is only ever drawn under 560px wide,
       which on a phone means upright, which means at least 560 of
       height to put it in. The one case that could run short gets a
       scroller below, and accepts the clip that comes with it. */
    overflow:visible;
  }
  @media (max-height:620px){
    .searchbar.is-docked.is-sheet .sb-body{
      max-height:min(78vh, var(--sb-max, 78vh)); overflow:auto;
    }
  }
  /* The three tabs, across the top of the sheet. site.js walks the one
     copy of them in here while it is open and back out when it shuts. */
  .searchbar.is-docked.is-sheet .sb-sheet-tabs{
    display:flex; justify-content:center; padding:2px 0 8px;
  }
  .searchbar.is-docked.is-sheet .sb-sheet-tabs .search-tabs{display:flex}
  /* and every field is a field again. The compressions the docked ROW
     needed -- half a label, no second line, three fields dropped
     entirely -- are all undone in here, because in here there is a whole
     screen to spend. */
  .searchbar.is-docked.is-sheet [data-pick="guests"],
  .searchbar.is-docked.is-sheet [data-pick="kind"],
  .searchbar.is-docked.is-sheet [data-pick="when"],
  .searchbar.is-docked.is-sheet .sb-beers{display:grid}
  .searchbar.is-docked.is-sheet .sb-field{padding:8px 16px; border-radius:18px}
  .searchbar.is-docked.is-sheet .sb-field > span{font-size:9.5px; letter-spacing:.11em}
  .searchbar.is-docked.is-sheet .sb-val{font-size:14.5px}
  .searchbar.is-docked.is-sheet .sb-val .ic{display:inline}
  .searchbar.is-docked.is-sheet .sb-val em{display:block}
  .searchbar.is-docked.is-sheet .sb-go{
    grid-column:1 / -1; width:100%; height:52px; border-radius:999px;
    display:inline-flex; align-items:center; justify-content:center; gap:10px;
  }
  .searchbar.is-docked.is-sheet .sb-go .ic{width:20px; height:20px}
  .searchbar.is-docked.is-sheet .sb-go-t{display:inline; font-size:16px; font-weight:600}
}

/* The page recedes behind an open sheet. On the body rather than inside
   the bar, for the same reason the sheet is absolute rather than fixed:
   the bar's backdrop-filter is a containing block, and a scrim that only
   covers the pill is not a scrim. It is also the tap that shuts the
   sheet -- searchbar.js closes on any press outside it. */
body.sb-sheeting::after{
  /* Above everything the page pins down and below the header the sheet
     hangs from. 39 was under the results page's filter rail, which is
     sticky at 40, so on that one page a row of undimmed chips floated on
     top of the scrim. The header is 60 and has to stay above this -- the
     pill is what closes the sheet. */
  content:""; position:fixed; inset:0; z-index:50;
  background:color-mix(in srgb, var(--ink) 26%, transparent);
  animation:sb-scrim .22s ease both;
}
@keyframes sb-scrim{from{opacity:0} to{opacity:1}}

@media (max-width:760px){
  body{font-size:16px}
  /* one column, so there is no orphan to rescue and no half-card to pull
     the overlay controls back over */
  .grid-fleet{grid-template-columns:1fr}
  .grid-fleet > .boat:last-child:nth-child(odd){grid-template-columns:1fr; grid-template-rows:auto 1fr}
  .grid-fleet > .boat:last-child:nth-child(odd) .boat-img{aspect-ratio:16/10; min-height:0}
  .grid-fleet > .boat:last-child:nth-child(odd) .boat-body{align-content:start; padding:18px 20px 22px}
  .grid-fleet > .boat:last-child:nth-child(odd) .fav,
  .grid-fleet > .boat:last-child:nth-child(odd) .promo-tag{right:12px}
  .grid-3,.grid-2{grid-template-columns:1fr}
  .grid-4{grid-template-columns:1fr}
  .strip{grid-template-columns:1fr}
  .footer-grid{grid-template-columns:1fr}
  /* Four links 19px tall with 9px between them is a 28px pitch: on a
     phone that is four targets inside the width of one thumb, and the
     one you get is the one you were nearest rather than the one you
     meant. The rows get the height instead of the type -- 14.5px is a
     readable link, it was only ever the spacing that was wrong. */
  .footer-grid ul{gap:0}
  .footer-grid a{display:block; padding-block:11px}
  .btn,.btn-ghost{width:100%}
  .btn-row{flex-direction:column; align-items:stretch}
  .searchbar{grid-template-columns:1fr}
  /* the price and stepper drop under the item name rather than
     squeezing a four-column row into 320px */
  .amen{grid-template-columns:auto 1fr; row-gap:12px}
  .amen-p{grid-column:2; justify-self:start}
  .stepper{grid-column:2; justify-self:end; margin-top:-40px}
  .ais-legend{margin-left:0; width:100%}
}

/* ---- the panel behind the sea chip ----
   Pressing a chip that says "Good" and being thrown onto a forecast page
   is a big answer to a small question: most of the time what is wanted is
   the rest of the numbers, not a change of page.

   COLOUR CARRIES THE VERDICT. Somebody opening this has one question — is
   that a boat day — and a traffic light answers it before a word is read.
   Green, amber and red, and they are the port authority's own three, not
   a scale we invented: the band at the top is today and the strip below
   is the next three days in the same colours. */
.sea-slot{position:relative; flex:none; display:flex}
.sea-chip{cursor:pointer; font-family:"Lexend",sans-serif; text-align:left}
.sea-pop{
  position:absolute; right:0; top:calc(100% + 10px); z-index:70;
  width:min(300px, calc(100vw - 24px)); overflow:hidden;
  border-radius:var(--r-card); border:var(--cardbd); background:var(--surface);
  box-shadow:0 4px 10px -4px rgba(var(--sh),.28), 0 30px 56px -26px rgba(var(--sh),.85);
}
.sea-pop[hidden]{display:none}

/* THE DAY, AS A BAND OF COLOUR WITH THE FLAG WRITTEN ON IT.
   Green, amber, red — the port authority's own three, out of the
   instrument ramp on :root, which is the same palette the forecast page
   draws its week and its map in. It used to be the brand's teal, amber
   and coral, so a "green flag" day was painted turquoise: the one word
   on the panel that names a colour, and the panel showed a different
   one. --s1/--s2/--s4 are the green, the yellow and the red of every
   marine forecast there is, and the wash and ink variants come with
   them, so the label on the band is legible on it rather than being the
   same hue one step darker. */
.sea-band{
  display:grid; gap:2px; padding:11px 18px 14px;
  background:var(--s1-wash);
  border-bottom:1px solid color-mix(in srgb, var(--s1) 32%, transparent);
}
.sea-band-flag{
  font-size:9.5px; letter-spacing:.15em; text-transform:uppercase; font-weight:700;
  color:var(--s1-ink);
}
.sea-band-word{
  font-family:"Bricolage Grotesque",sans-serif; font-variation-settings:"wdth" 86;
  font-weight:700; font-size:23px; letter-spacing:-.02em; line-height:1.1;
  color:var(--s1-ink);
}
.sea-band.is-warn{
  background:var(--s2-wash); border-bottom-color:color-mix(in srgb, var(--s2) 40%, transparent);
}
.sea-band.is-warn .sea-band-flag,.sea-band.is-warn .sea-band-word{color:var(--s2-ink)}
.sea-band.is-bad{
  background:var(--s4-wash); border-bottom-color:color-mix(in srgb, var(--s4) 36%, transparent);
}
.sea-band.is-bad .sea-band-flag,.sea-band.is-bad .sea-band-word{color:var(--s4-ink)}
.sea-band.is-na{
  background:var(--sna-wash); border-bottom-color:color-mix(in srgb, var(--ink) 10%, transparent);
}
.sea-band.is-na .sea-band-flag,.sea-band.is-na .sea-band-word{color:var(--sna-ink)}

/* ---- walking the days ----
   The arrows sit inside the coloured band, above the flag, because the
   colour IS the day: moving between days and watching the whole band go
   from green to red is the fastest thing this panel does. Their ground
   is a hole punched in the band rather than a fill of their own, so they
   take its colour instead of adding a fourth one. */
.sea-step{
  display:flex; align-items:center; justify-content:space-between; gap:8px;
  margin-bottom:3px;
}
.sea-when{
  font-size:12px; font-weight:600; color:inherit; text-align:center;
  flex:1 1 auto; min-width:0; white-space:nowrap; overflow:hidden;
  text-overflow:ellipsis;
}
.sea-arrow{
  width:26px; height:26px; flex:none; display:grid; place-items:center;
  padding:0; cursor:pointer; border-radius:50%; color:inherit;
  background:color-mix(in srgb, #fff 55%, transparent);
  border:1px solid color-mix(in srgb, var(--ink) 12%, transparent);
  transition:background .16s ease, opacity .16s ease, transform .16s ease;
}
.sea-arrow .ic{width:14px; height:14px}
.sea-arrow:hover{background:#fff}
.sea-arrow:active{transform:scale(.92)}
.sea-arrow:focus-visible{outline:2px solid var(--ink); outline-offset:2px}
.sea-arrow:disabled{opacity:.3; cursor:default}
.sea-arrow:disabled:hover{background:color-mix(in srgb, #fff 55%, transparent)}
/* The band's own colour is what says which day this is, so it inherits
   rather than being told: one rule per tone above, not four. */
.sea-band .sea-step{color:var(--s1-ink)}
.sea-band.is-warn .sea-step{color:var(--s2-ink)}
.sea-band.is-bad .sea-step{color:var(--s4-ink)}
.sea-band.is-na .sea-step{color:var(--sna-ink)}

.sea-pop-flag{
  margin:0; padding:13px 18px 0; font-size:12.5px; line-height:1.55; color:var(--muted);
}
/* THE FOUR READINGS, EACH WITH THE THING IT IS A READING OF.
   A glyph, the name in small capitals beside it, the figure under both.
   Four numbers in a two-by-two with SWELL and WIND set over them is a
   table you have to read; a wave beside 0.9 m is a wave height, and the
   eye gets there without stopping at the label. */
.sea-pop-nums{
  list-style:none; margin:13px 18px 0; padding:13px 0 0;
  display:grid; grid-template-columns:1fr 1fr; gap:12px 14px;
  border-top:1px solid color-mix(in srgb, var(--ink) 11%, transparent);
}
.sea-pop-nums li{
  display:grid; grid-template-columns:22px minmax(0,1fr);
  align-items:center; gap:1px 8px;
}
.sea-pop-nums .ic{
  grid-row:1 / span 2; width:19px; height:19px; align-self:center;
  color:var(--sea-b);
}
.sea-pop-nums i{
  font-style:normal; font-size:9.5px; letter-spacing:.12em; text-transform:uppercase;
  color:var(--muted); font-weight:600;
}
.sea-pop-nums b{font-size:15px; font-weight:600; font-variant-numeric:tabular-nums}
/* The swell and the wind are the two the verdict is actually made of, so
   they take the day's own colour and the other two stay quiet. */
.sea-pop-nums li:nth-child(-n+2) .ic{color:var(--s1-ink)}
.sea-pop:has(.sea-band.is-warn) .sea-pop-nums li:nth-child(-n+2) .ic{color:var(--s2-ink)}
.sea-pop:has(.sea-band.is-bad) .sea-pop-nums li:nth-child(-n+2) .ic{color:var(--s4-ink)}
.sea-pop:has(.sea-band.is-na) .sea-pop-nums li:nth-child(-n+2) .ic{color:var(--sna-ink)}
.sea-pop-nums li:nth-child(n+3) .ic{color:var(--muted)}

/* where the numbers come from: what a sceptic wants, out of everyone
   else's way */
.sea-more{margin:14px 18px 0}
.sea-more summary{
  cursor:pointer; list-style:none; display:inline-block;
  font-size:11.5px; color:var(--muted);
  text-decoration:underline; text-underline-offset:3px;
}
.sea-more summary::-webkit-details-marker{display:none}
.sea-more summary:hover{color:var(--ink)}
.sea-more summary:focus-visible{outline:2px solid var(--ink); outline-offset:2px; border-radius:4px}
.sea-more p{margin:8px 0 0; font-size:11.5px; line-height:1.5; color:var(--muted)}

.sea-pop-go{width:calc(100% - 36px); justify-content:center; margin:16px 18px 18px}

@media (max-width:560px){
  .sea-pop{position:fixed; left:12px; right:12px; top:auto; width:auto}
}


/* =====================================================================
   WHAT A FINGER CAN ACTUALLY HIT

   Every size on this site was chosen against a pointer, which is one
   pixel wide and lands exactly where it was aimed. A fingertip is about
   forty-four of them and lands somewhere inside itself, so a 32px heart
   on the corner of a photograph is a control you press three times.

   `pointer:coarse`, not a width. The two questions are different ones
   and this site had been answering the second: a laptop with a narrow
   window got phone-sized controls it did not need, and a tablet held in
   two hands got desktop ones it could not use. What decides a hit area
   is the thing doing the hitting.

   ONLY THE HIT AREA GROWS. Nothing here changes a glyph, a font size or
   a colour -- the heart is still a 22px heart, it is simply carrying
   44px of press around itself. Where the box cannot grow without moving
   the layout (the heart floats over a photograph, the zoom sits on a
   map) the padding goes on and the position comes back by the same
   amount, so the drawing lands where it always did.

   THIS IS NOT THE ONLY BLOCK OF ITS KIND, and it cannot be. Every rule
   here has to outrank the one that set the small size, and this file is
   loaded first: components.css, app.css and each page's own sheet all
   come after it, so a `.b-fav{width:44px}` written here loses to the
   `.b-fav{width:32px}` written there at exactly the same specificity.
   The first pass at this was one block in this file and half of it
   silently did nothing. So each sheet carries the sizes for the things
   it owns, under the same media query and a one-line pointer back to
   this note. Search `pointer:coarse` to find all of them.
   ===================================================================== */
@media (hover:none) and (pointer:coarse){

  /* The three discs in the header are one row and one size -- that is
     the whole argument for the sea reading having become a disc. The
     other two are 42px and the sea chip had been left at 38, which is
     both under the thumb and visibly the odd one out beside its
     neighbours. All three to 44. */
  .menu-toggle,.account-ic{width:44px; height:44px}
  .sea-chip,.wm-shut .sea-chip{width:44px; height:44px}
  /* Docked they shrink to make room for the bar, and 40 is the floor
     that leaves: three 44px discs plus a search bar do not fit across a
     360px phone, and the bar is what the row is FOR. */
  .docked .menu-toggle,.docked .account-ic{width:40px; height:40px}

  /* The arrows either side of the day in the sea panel. */
  .sea-arrow{min-width:44px; min-height:44px}

  /* NOT the value buttons inside the search bar, deliberately. They
     measure 300x20 and every audit flags them, and padding them out to
     44 adds 14px to each of five stacked rows -- fifty-five pixels off
     the top of a phone screen, on the one object the whole site is
     steered with. It would buy nothing: the field around each of them
     is already 49px, searchbar.js opens the panel from a press anywhere
     in it, and `.sb-field:focus-within` already draws the focus ring
     around the whole row. The target is the row. It always was. */

  /* Small type that is also a destination: the back links and the
     by-lines. 13px is fine to read and a 21px row is not fine to hit,
     so the row gets taller and the words stay exactly where they are.
     (.by-tag and .course-by are app.css's, and are done there.) */
  /* .backlink is already an inline-flex row with a gap of its own and
     it stands alone above a page, so it can simply have the height. */
  .backlink{min-height:44px}

  /* ---- and these grow a hit area WITHOUT growing themselves ----
     The rules above give a control more box, which is right when the
     control is a row with space around it. It is wrong for everything
     below, and it broke all of them: a by-line tag is a coloured pill
     18px tall and `min-height:44px` made it a 44px lozenge; "with La
     Pescaderia" is a text node, a <b> and an arrow, and `inline-flex`
     turned the whitespace between them into flex-item separation and
     printed `withLa Pescaderia`; a 19px round glyph button became a 44px
     one. Every one of those is a visual change, and none of them was
     asked for -- the ask was that a finger can land on the thing.
     So the box stays exactly as it was drawn and an invisible one is
     centred over it. It is `::after` on each, which is free on all of
     them, and it is 44px tall whatever the type does. */
  .back-menu{position:relative}
  .back-menu::after{
    content:""; position:absolute; left:0; right:0; top:50%;
    height:44px; transform:translateY(-50%);
  }
}
