/* ===========================================================================
   Online Firework Shop — layout
   Deploy 003. Header, navigation, payment strips, footer.

   Loads after ofs.css. Extracted from the approved concepts rather than
   retyped, so the two cannot drift.

   Bootstrap 3 is still loaded, so a few rules below carry more specificity
   than they otherwise would. Those are marked. They come out when Bootstrap
   does.
   =========================================================================== */

.wrap{width:100%; max-width:var(--container); margin-inline:auto; padding-inline:20px}
@media(min-width:768px){.wrap{padding-inline:32px}}
@media(min-width:1024px){.wrap{padding-inline:48px}}

/* ---------- pay in 3 bar (above hero) ----------
   Paper ground for contrast against the night canvas. Cyan links fail on paper
   (1.9:1), so links here use --ink-800, which is 17.2:1. */
.paybar{background:var(--paper); color:var(--ink-900)}
.paybar__row{display:flex; flex-wrap:wrap; align-items:center; justify-content:center;
  gap:4px 10px; padding-block:9px; font-size:.8125rem; line-height:1.45; text-align:center}
.paybar i{color:#003087; font-size:1.0625rem; line-height:1}
.paybar strong{font-weight:700}
.paybar span{color:#3A3F52}
.paybar a{color:var(--ink-800); font-weight:700; text-decoration:underline;
  text-underline-offset:2px}
.paybar a:hover{color:#000}
@media(max-width:600px){
  .paybar__row{font-size:.75rem; gap:3px 8px; padding-block:8px}
}

/* ---------- payment strip ---------- */
/* Sits between the news band and the footer, so it needs its own darker ground
   and a rule top and bottom to separate from both. */
.paystrip{background:var(--ink-900); border-top:1px solid var(--ink-700);
  border-bottom:1px solid var(--ink-700)}
.paystrip__row{display:flex; flex-wrap:wrap; align-items:center;
  gap:var(--s-3) var(--s-5); padding-top:14px}
.paystrip__mark{font-size:1.875rem; line-height:1; color:#009CDE; flex:none}
.paystrip__copy{display:flex; flex-wrap:wrap; align-items:baseline; gap:4px var(--s-3)}
.paystrip__lead{font-weight:700; font-size:1.0625rem}
.paystrip__sub{color:var(--text-secondary); font-size:.9375rem}
.paystrip__cards{display:flex; align-items:center; gap:11px; margin-left:auto;
  font-size:1.75rem; line-height:1; color:var(--text-tertiary)}
.paystrip__link{white-space:nowrap; font-weight:700; font-size:.9375rem}
.paystrip__note{font-size:.75rem; line-height:1.5; color:var(--text-tertiary);
  padding-top:6px; padding-bottom:12px}
@media(max-width:767px){
  /* A compliant BNPL banner is unavoidably wordy, so on small screens it is tightened
     hard rather than truncated - the risk wording has to stay with the promotion. */
  .paystrip__row{gap:10px var(--s-4); padding-top:12px}
  .paystrip__mark{font-size:1.5rem}
  .paystrip__copy{gap:2px}
  .paystrip__lead{font-size:1rem; line-height:1.3}
  .paystrip__sub{font-size:.8125rem; line-height:1.4}
  .paystrip__link{font-size:.875rem}
  .paystrip__cards{margin-left:0; width:100%; font-size:1.375rem; gap:9px}
  .paystrip__note{font-size:.6875rem; line-height:1.45; padding-bottom:12px}
}

/* ---------- header ---------- */
.util{background:var(--ink-900); border-bottom:1px solid var(--ink-700); font-size:.8125rem}
.util .wrap{display:flex; gap:var(--s-5); align-items:center; min-height:40px; flex-wrap:wrap}
@media(max-width:600px){.util__hide-sm{display:none}}
.util a{color:var(--text-tertiary)}
.util a:hover{color:var(--text-secondary)}
.util__spacer{margin-left:auto}
.util .util__tel{color:var(--text-primary); font-weight:700}
.util .util__tel:hover{color:var(--text-primary)}

.hdr{position:sticky; top:0; z-index:50; background:rgba(12,0,84,.92);
  backdrop-filter:blur(12px); border-bottom:1px solid var(--ink-700)}
.hdr .wrap{display:flex; align-items:center; gap:var(--s-4);
  min-height:84px; padding-block:15px}
@media(min-width:768px){.hdr .wrap{min-height:134px; padding-block:17px}}
/* The logo is a stacked lockup (1271x840), so it is sized by HEIGHT and the
   clear space is structural padding, not a happy accident of min-height.
   A horizontal lockup would let this grow — see brand-style-guide.md section 2. */
.hdr__logo{display:flex; align-items:center; flex:none}
.hdr__logo img{height:54px; width:auto}
@media(min-width:768px){.hdr__logo img{height:100px}}
/* The bar appears at 1280px, not 1180px. With the search stacked under the
   icons (see .hdr__tools below) there are 756px beside the logo at 1280 and
   751px at 1440 — it barely moves, because the wrap is capped at 1224px. Six
   items measure 739px at 1.25rem, so that is the size, with about 15px spare.
   1.375rem needs 797px and does not fit. At 1180 there is not enough room for
   any legible size, so below 1280 the nav goes in the burger. */
.nav{display:none; gap:var(--s-4); margin-left:var(--s-5)}
@media(min-width:1280px){.nav{display:flex}}
.hdr__tools{margin-left:auto; display:flex; align-items:center; gap:var(--s-3)}
/* From 1280px the search sits under the account and basket, not beside them.
   The tools block is then as wide as the search field rather than the field
   plus the icons, which hands the nav back about 170px — enough to put the bar
   back to its full size. Done by wrapping rather than by regrouping the markup,
   because common/header.twig is one of the files OCMOD shadows and a change
   there would not show until Modifications were refreshed. */
@media(min-width:1280px){
  /* The width has to be stated. A wrapped flex container is still sized by its
     max-content as though it had not wrapped, so without this the block stayed
     342px wide — the field plus the icons — and stacking bought the nav nothing. */
  .hdr__tools{flex-wrap:wrap; justify-content:flex-end; align-items:flex-end;
    row-gap:var(--s-2); width:var(--search-w)}
  .hdr__tools .search{order:2; flex-basis:100%; margin-left:auto}
}
/* --search-w is the one place this width is written. .hdr__tools matches it
   from 1280px so the stacked column is as wide as the field and no wider. */
.hdr{--search-w:230px}
@media(min-width:1360px){.hdr{--search-w:290px}}
.search{display:none; align-items:center; gap:8px; background:var(--ink-900);
  border:1px solid var(--ink-700); border-radius:var(--r-control); padding:0 12px; height:44px;
  width:var(--search-w)}
@media(min-width:900px){.search{display:flex}}
.search input{background:none; border:0; color:var(--text-primary); font:inherit; font-size:.9375rem; width:100%}
.search input::placeholder{color:var(--text-tertiary)}
.search input:focus{outline:none}
.iconbtn{display:inline-flex; align-items:center; justify-content:center; width:44px; height:44px;
  border:1px solid var(--ink-700); border-radius:var(--r-control); background:var(--ink-900);
  color:var(--text-secondary); cursor:pointer}
/* Gold fill on hover, with everything inside it in brand blue — the badge
   inverts too, or a gold pill on a gold button disappears. 10.7:1 for the
   glyph. :focus-visible gets the same treatment so a keyboard sees what a
   mouse sees. */
.iconbtn:hover,
.iconbtn:focus-visible{background:var(--fuse-gold); border-color:var(--fuse-gold);
  color:var(--ink-800)}
.iconbtn:hover .iconbtn__n,
.iconbtn:hover .basket__n,
.iconbtn:focus-visible .iconbtn__n,
.iconbtn:focus-visible .basket__n{background:var(--ink-800); color:var(--fuse-gold)}
.iconbtn{transition:background var(--t-micro) ease-out, border-color var(--t-micro) ease-out,
  color var(--t-micro) ease-out}

/* The header holds four icons on a phone, not five: five 44px buttons plus the
   logo need 421px and a 390px phone leaves 335. The wish list is the one that
   gives way, and menu.twig carries it into the burger at the same width so it
   is moved rather than lost. */
/* Hidden by default and shown only in the burger below 480px.
   .nav .nav__top sets display:inline-flex, and it sits later in this file, so
   an equal-specificity rule here loses on source order — the item leaked into
   the desktop bar as a seventh entry and overlapped the tools by 90px. Three
   classes settles it wherever the rule happens to sit. */
.nav .nav__top.nav__top--wish{display:none}
@media(max-width:479px){
  .iconbtn--wish{display:none}
  .hdr--menu-open .nav .nav__top.nav__top--wish{display:inline-flex; gap:10px}
}

/* the wish list count, same pill as the basket's */
.iconbtn__n{position:absolute; top:-6px; right:-6px; min-width:18px; height:18px; padding:0 5px;
  display:grid; place-items:center; border-radius:var(--r-pill);
  background:var(--fuse-gold); color:var(--text-on-accent);
  font-size:.6875rem; font-weight:700; line-height:1}
.iconbtn{position:relative}

/* ---------- basket drop-down ---------- */
.basketwrap{position:relative}
.cartdrop{position:absolute; top:calc(100% + 4px); right:0; z-index:70; display:none;
  width:340px; max-width:calc(100vw - 32px); padding:var(--s-4);
  background:var(--ink-800); border:1px solid var(--ink-700);
  border-radius:var(--r-card); box-shadow:0 18px 40px rgba(0,0,0,.5)}
.basketwrap:hover .cartdrop,
.basketwrap:focus-within .cartdrop{display:block}
/* The panel sits 8px clear of the button, and the pointer crossing that gap
   would drop the hover and shut it. This bridges it without moving anything. */
/* Taller than the 4px gap on purpose: butted exactly against the button they
   share a boundary pixel, and the pointer crossing it lands on neither. The
   extra 2px overlaps the button so the path is continuous. */
.cartdrop::before{content:""; position:absolute; left:0; right:0; top:-6px; height:6px}
.cartdrop__list{list-style:none; margin:0 0 var(--s-4); padding:0;
  display:grid; gap:var(--s-3); max-height:320px; overflow-y:auto}
.cartdrop__list li{display:grid; grid-template-columns:44px minmax(0,1fr) auto; gap:var(--s-3);
  align-items:start}
.cartdrop__thumb img{width:44px; height:44px; object-fit:cover; border-radius:var(--r-control);
  background:var(--paper)}
.cartdrop__body{display:grid; gap:2px; min-width:0}
.cartdrop .cartdrop__name{font-size:.875rem; line-height:1.3; color:var(--text-primary)}
.cartdrop .cartdrop__name:hover{text-decoration:underline; color:var(--spark-cyan)}
.cartdrop__opt,.cartdrop__qty{font-size:.75rem; color:var(--text-tertiary)}
.cartdrop__total{font-size:.875rem; font-weight:700; white-space:nowrap}
.cartdrop__totals{margin:0 0 var(--s-4); padding-top:var(--s-3);
  border-top:1px solid var(--ink-700); display:grid; gap:4px}
.cartdrop__totals div{display:flex; justify-content:space-between; gap:var(--s-3);
  font-size:.875rem; color:var(--text-secondary)}
.cartdrop__totals dt,.cartdrop__totals dd{margin:0}
.cartdrop__totals div:last-child{color:var(--text-primary); font-weight:700}
.cartdrop__act{display:grid; grid-template-columns:1fr 1fr; gap:var(--s-3)}
.cartdrop__act .btn{justify-content:center}
.cartdrop__empty{margin:0 0 var(--s-4); font-size:.875rem; color:var(--text-secondary)}
.cartdrop__empty + .cartdrop__act{grid-template-columns:1fr}
.iconbtn--menu{display:inline-flex}
/* Must match the breakpoint the nav bar appears at, or there is a band of
   widths with neither a bar nor a burger. */
@media(min-width:1280px){.iconbtn--menu{display:none}}
.iconbtn--search{display:inline-flex}
@media(min-width:900px){.iconbtn--search{display:none}}
.basket{position:relative}
.basket__n{position:absolute; top:-6px; right:-6px; background:var(--fuse-gold); color:var(--text-on-accent);
  font-size:11px; font-weight:700; min-width:18px; height:18px; border-radius:var(--r-pill);
  display:grid; place-items:center; padding:0 4px}

/* ---------- buttons ---------- */
.btn{display:inline-flex; align-items:center; justify-content:center; gap:8px;
  height:52px; padding:0 24px; border-radius:var(--r-control); font-family:var(--font-body);
  font-weight:700; font-size:1rem; border:1px solid transparent; cursor:pointer;
  transition:transform var(--t-micro) ease-out, background var(--t-micro) ease-out, border-color var(--t-micro) ease-out}
@media(min-width:768px){.btn{height:48px}}
.btn:hover{text-decoration:none; transform:translateY(-1px)}
.btn--primary{background:var(--fuse-gold); color:var(--text-on-accent)}
.btn--primary:hover{background:#FFD34A; color:var(--text-on-accent)}
.btn--secondary{background:transparent; color:var(--spark-cyan); border-color:var(--spark-cyan)}
.btn--secondary:hover{background:rgba(60,180,252,.1); color:var(--spark-cyan)}
.btn--sm{height:44px; padding:0 16px; font-size:.875rem}
.btn--block{width:100%}

/* ---------- footer ---------- */
.ftr{background:var(--ink-800); border-top:1px solid var(--ink-700); padding-block:var(--s-8) var(--s-6)}
.ftr__grid{display:grid; gap:var(--s-6)}
@media(min-width:768px){.ftr__grid{grid-template-columns:repeat(2,minmax(0,1fr))}}
@media(min-width:1024px){.ftr__grid{grid-template-columns:1.4fr 1fr 1fr 1.3fr; gap:var(--s-7)}}
.ftr h3{font-size:1.125rem; margin-bottom:var(--s-4)}
.ftr ul{list-style:none; margin:0; padding:0; display:flex; flex-direction:column; gap:2px}
.ftr ul a{display:inline-flex; align-items:center; min-height:36px}
.ftr a{color:var(--text-secondary); font-size:.9375rem}
.ftr a:hover{color:var(--text-primary)}
.nap{font-style:normal; font-size:.9375rem; color:var(--text-secondary); line-height:1.7}
.nap strong{color:var(--text-primary); font-weight:700}
.news-form{display:flex; gap:var(--s-2); margin-top:var(--s-3)}
.news-form input{flex:1; min-width:0; height:48px; background:var(--ink-900);
  border:1px solid var(--ink-700); border-radius:var(--r-control); color:var(--text-primary);
  font:inherit; font-size:.9375rem; padding:0 14px}
.news-form input::placeholder{color:var(--text-tertiary)}
.ftr__legal{margin-top:var(--s-7); padding-top:var(--s-5); border-top:1px solid var(--ink-700);
  display:flex; flex-wrap:wrap; gap:var(--s-3) var(--s-5); justify-content:space-between;
  font-size:.8125rem; color:var(--text-tertiary)}
.age{display:inline-flex; align-items:center; gap:8px; color:var(--fuse-gold); font-weight:700}
.age b{border:1.5px solid var(--fuse-gold); border-radius:var(--r-pill); width:26px; height:26px;
  display:grid; place-items:center; font-size:11px}

/* ---------- living with Bootstrap 3 --------------------------------------
   Bootstrap defines .btn, .nav and .container. Our .btn is a different
   component with the same name, so these override its worst assumptions
   until Bootstrap is removed. Delete this whole block with Bootstrap. */
.hdr .nav{margin:0; padding:0; list-style:none; float:none}
.hdr .nav > li{float:none}
.btn{white-space:nowrap; -webkit-appearance:none; appearance:none}
.btn.btn--primary,.btn.btn--secondary{background-image:none; text-shadow:none; box-shadow:none}
.paystrip a,.paybar a,.util a,.ftr a{text-decoration:none}

/* OpenCart's stylesheet.css sets footer{margin-top:30px}, which leaves a strip
   of page background between the last section and the footer. Our sections
   carry their own vertical rhythm, so the footer sits flush. */
footer.ftr{margin-top:0}

/* ---------- the header must never overflow --------------------------------
   Category names come from the client's catalogue and can be any length.
   "Buy 1 Get 1 FREE Fireworks Promotion" is 36 characters, which at 22px made
   logo + nav + tools 1341px inside a 1224px container and pushed the basket
   off the right of the screen.

   The nav is the only part allowed to give way: the logo and the tools are
   fixed, and the nav shrinks and clips rather than displacing anything. A
   clipped nav item is a cue to shorten the category name; a missing basket is
   a broken site. */
.hdr .wrap{min-width:0}
.hdr__logo,.hdr__tools{flex:none}
/* overflow:hidden used to be here, to hide a menu that did not fit. The six
   items now measure 622px against 639px of room, so nothing needs clipping —
   and clipping would hide the drop-down panels completely, since they are
   absolutely positioned children of a 37px-tall bar. */
.nav{flex:0 1 auto; min-width:0}
.nav a{flex:none}

/* Stock OpenCart pages still render Bootstrap panels and wells on the dark
   canvas. Give them a surface so they are legible until each template is
   rebuilt. Temporary. */
.panel,.well,.table{background:var(--ink-800); color:var(--text-secondary);
  border-color:var(--ink-700)}
.breadcrumb{background:transparent; padding-left:0}

/* ---------- mobile header toggles ----------------------------------------
   The nav is hidden below 1280 and the search field below 900. These reveal
   them as panels under the header when the buttons are pressed. */
.hdr__name{font-family:var(--font-display); font-weight:700; text-transform:uppercase;
  font-size:1.5rem; letter-spacing:.02em; color:var(--text-primary)}
/* Not display:contents. That was here so #cart did not disturb the tools row,
   but an element with it generates no box at all: position:relative had nothing
   to apply to, so the drop-down anchored to an ancestor further up and landed
   79px below the button, under the search field — and .basketwrap:hover could
   never match, because there was no box to hover. inline-flex keeps the button
   sitting exactly as it did while giving the panel something to hang from. */
/* Selected as #cart.basketwrap, at 110, so it beats the stock stylesheet's
   plain #cart at 100 whichever order the two files load in.
   stylesheet.css carries `#cart{margin-bottom:10px}` for OpenCart's own header.
   It never bit while this element had display:contents and generated no box;
   giving it one brought the margin to life, and because the tools row aligns to
   flex-end it lifted the basket 10px above the other two icons. The rest of the
   stock #cart rules target .btn and .dropdown-menu, which this markup does not
   use, so this is the only one to answer. */
#cart.basketwrap{display:inline-flex; margin:0}

@media(max-width:1279px){
  .hdr--menu-open .nav{
    display:flex; flex-direction:column; align-items:stretch; gap:0;
    position:absolute; left:0; right:0; top:100%; z-index:60;
    background:var(--ink-800); border-top:1px solid var(--ink-700);
    box-shadow:0 18px 40px rgba(0,0,0,.5); margin:0; padding:var(--s-2) 0;
    /* The menu is taller than a phone — 1431px against 812 with both panels
       open — and it is absolutely positioned inside a sticky header, so the
       page cannot scroll to its lower half. Without this the last few items,
       Sky Diving among them, could not be reached at all. dvh first for the
       browser chrome; vh is the fallback. */
    max-height:calc(100vh - 150px);
    max-height:calc(100dvh - 150px);
    overflow-y:auto; overscroll-behavior:contain;
  }
  /* At 768 and up the header is 134px rather than 84, and the utility bar above
     it is still on screen at the top of the page, which is the worst case. */
  @media(min-width:768px){
    .hdr--menu-open .nav{max-height:calc(100vh - 200px); max-height:calc(100dvh - 200px)}
  }
  .hdr--menu-open .nav a{
    padding:14px var(--s-5); border-bottom:0; min-height:52px; align-items:center;
    display:flex; font-size:1.25rem;
  }
  .hdr--menu-open .nav a:hover{background:var(--ink-600)}
  .hdr{position:sticky}
  .hdr .wrap{position:relative}
}

@media(max-width:899px){
  .hdr--search-open .search{
    display:flex; position:absolute; left:var(--s-5); right:var(--s-5); top:100%;
    z-index:61; width:auto; height:52px; margin-top:8px;
    box-shadow:0 18px 40px rgba(0,0,0,.5);
  }
}

/* ---------------------------------------------------------------------------
   Main navigation (deploy 073)
   Six top-level items, two of which open a panel. The panels are plain CSS
   from 1280px up — :hover and :focus-within, so a keyboard reaches them without
   script — and the small amount of JavaScript in footer.twig only exists to
   keep aria-expanded honest and to close a panel on Escape or an outside click.
   Below 1280px the whole nav lives in the burger menu, where the panels are
   simply always open: a drop-down inside a drop-down is not worth the tap.
   --------------------------------------------------------------------------- */

.nav__group{position:relative; display:flex}

/* The top row. A button and an anchor have to look identical here. */
.nav .nav__top{display:inline-flex; align-items:center; gap:7px;
  font-family:var(--font-display); font-weight:700; font-size:1.25rem; line-height:1;
  text-transform:uppercase; letter-spacing:.02em; color:var(--text-primary); white-space:nowrap;
  padding-block:9px; border:0; border-bottom:3px solid transparent; background:none; cursor:pointer;
  transition:border-color var(--t-micro) ease-out, color var(--t-micro) ease-out}
.nav .nav__top:hover,
.nav .nav__top:focus-visible{text-decoration:none; border-bottom-color:var(--spark-cyan); color:var(--spark-cyan)}
/* No rule under the two that open a panel — the panel itself is the thing that
   answers the hover, and a rule as well reads as two states for one action.
   The colour still changes, and the border stays in the box so nothing shifts. */
.nav .nav__group .nav__top:hover,
.nav .nav__group .nav__top:focus-visible{border-bottom-color:transparent}
.nav .nav__top--offer{color:var(--fuse-gold)}
.nav .nav__top--offer:hover{color:var(--fuse-gold); border-bottom-color:var(--fuse-gold)}
.nav__top i{font-size:.6875rem; transition:transform var(--t-micro) ease-out}
.nav__ext{font-size:.625rem; opacity:.7}

/* The panel */
/* Gold panel, brand blue type. 10.7:1, and white on brand blue for the hover
   is 18.4:1, so both are well clear of the 4.5:1 body text needs. The border is
   the same gold: the dark ink-700 edge it had was drawn for a dark panel and
   read as a dirty outline against this one. */
.nav__panel{position:absolute; top:100%; left:0; z-index:60; display:none;
  min-width:300px; padding:var(--s-4);
  background:var(--fuse-gold); border:1px solid var(--fuse-gold);
  border-radius:var(--r-card); box-shadow:0 18px 40px rgba(0,0,0,.45)}
.nav__panel--narrow{min-width:250px}
.nav__panel ul{list-style:none; margin:0; padding:0; display:grid; gap:1px}
.nav .nav__panel a{display:block; padding:9px 12px; border-radius:var(--r-control);
  font-family:var(--font-body); font-size:.9375rem; font-weight:400; text-transform:none;
  letter-spacing:0; line-height:1.3; color:var(--ink-800); white-space:normal;
  transition:background var(--t-micro) ease-out, color var(--t-micro) ease-out}
.nav .nav__panel a:hover,
.nav .nav__panel a:focus-visible{text-decoration:none; background:var(--ink-800); color:var(--text-primary)}

@media(min-width:1280px){
  /* Two columns for the long list, so it does not run off the bottom. */
  #nav-fireworks{min-width:520px}
  #nav-fireworks ul{grid-template-columns:repeat(2,minmax(0,1fr)); gap:1px var(--s-3)}
  .nav__group:hover .nav__panel,
  .nav__group:focus-within .nav__panel,
  .nav__top[aria-expanded="true"] + .nav__panel{display:block}
  .nav__group:hover .nav__top i,
  .nav__top[aria-expanded="true"] i{transform:rotate(180deg)}
}

/* In the burger menu the nav is a stacked column and the panels are open.
   1279, matching the width the bar appears at — at 1180-1279 the burger opens
   the nav but these rules were absent, so the two panels could not be opened
   at all. */
@media(max-width:1279px){
  /* No overflow:visible here. This block sits after the one that gives the menu
     its own scroll, so at equal specificity it won, the max-height stopped
     clipping and the lower half of the menu became unreachable again. */
  .hdr--menu-open .nav{display:flex; flex-direction:column; align-items:flex-start;
    gap:var(--s-3); margin:var(--s-4) 0 0; width:100%}
  .nav__group{display:block; width:100%}
  .nav .nav__top{width:100%; justify-content:space-between}
  .nav__top[aria-controls] i{display:none}
  /* No gold here: in the burger the panel has no background of its own, so the
     brand blue the desktop drop-down uses would be blue on blue — the header is
     the same #0C0054. The stacked list keeps the light type it always had. */
  .nav__panel{position:static; display:block; min-width:0; width:100%;
    padding:0 0 var(--s-3) var(--s-3); background:none; border:0; box-shadow:none}
  .nav .nav__panel a{color:var(--text-secondary)}
  .nav .nav__panel a:hover,
  .nav .nav__panel a:focus-visible{background:var(--ink-700); color:var(--text-primary)}
  #nav-fireworks ul,.nav__panel ul{grid-template-columns:minmax(0,1fr)}
}
