/* Écrin (task 7.0f): the app's components in CSS, for every page of the site. The keys of
   noctave_button.dart (a face on its edge, varnish, rim, the face going down and lighting up when
   pressed), the lacquered panels of noctave_panel.dart (gold lines, inner frame with cut-in
   corners, diamonds, ringed medallion), the arches of the home screen (home_frames.dart) and the
   night sky of the title screen. Loaded after styles.css or compte/compte.css; no inline style
   (the pages' CSP), ornaments are small SVGs in data: URLs (img-src data: is allowed). */

:root {
  --gold: #FFC46B;
  --gold-deep: #C98A3C;
  --gold-light: #FFE7B5;
  --gold-rgb: 255, 196, 107;
  --lacquer: linear-gradient(to bottom, rgba(34, 31, 52, 0.95), rgba(18, 17, 32, 0.96));
  --key-ease: cubic-bezier(0.33, 1, 0.68, 1);
  --diamond: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M5 0L10 5L5 10L0 5Z' fill='%23FFC46B' fill-opacity='.85'/%3E%3C/svg%3E");
  --diamond-light: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M5 0L10 5L5 10L0 5Z' fill='%23FFF1D2'/%3E%3C/svg%3E");
  --glint: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3E%3Cpath d='M10 0Q12.2 7.8 20 10Q12.2 12.2 10 20Q7.8 12.2 0 10Q7.8 7.8 10 0Z' fill='%23FFF1D6'/%3E%3C/svg%3E");
  --glint-white: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3E%3Cpath d='M10 0Q11.6 8.4 20 10Q11.6 11.6 10 20Q8.4 11.6 0 10Q8.4 8.4 10 0Z' fill='white'/%3E%3C/svg%3E");
  --dot: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Ccircle cx='2' cy='2' r='1.6' fill='%23FFC46B' fill-opacity='.9'/%3E%3C/svg%3E");
  /* The inner gold frame of a panel: cut-in corners and four diamonds (a 9-slice image). */
  --inner-frame: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='48' height='48' viewBox='0 0 48 48'%3E%3Cpath d='M17.5 4.5H30.5A13 13 0 0 0 43.5 17.5V30.5A13 13 0 0 0 30.5 43.5H17.5A13 13 0 0 0 4.5 30.5V17.5A13 13 0 0 0 17.5 4.5Z' fill='none' stroke='%23FFC46B' stroke-opacity='.6'/%3E%3Cg fill='%23FFC46B' fill-opacity='.8'%3E%3Cpath d='M1 4.5L4.5 1L8 4.5L4.5 8Z'/%3E%3Cpath d='M40 4.5L43.5 1L47 4.5L43.5 8Z'/%3E%3Cpath d='M1 43.5L4.5 40L8 43.5L4.5 47Z'/%3E%3Cpath d='M40 43.5L43.5 40L47 43.5L43.5 47Z'/%3E%3C/g%3E%3C/svg%3E");
}

/* Tones, as the panels of the app say them (never alone: icon and title say it too). */
.tone-cyan   { --tone: 92, 225, 255;  --tone-light: #C9F5FF; }
.tone-violet { --tone: 178, 141, 255; --tone-light: #E3D6FF; }
.tone-amber  { --tone: 255, 196, 107; --tone-light: #FFEBC9; }
.tone-mint   { --tone: 107, 242, 176; --tone-light: #CFFBE6; }
.tone-rose   { --tone: 255, 107, 138; --tone-light: #FFD0DB; }

/* ================================================================== Keys (buttons) */

/* A key: the face lies on its edge, as the keys of the game's keyboard. Height 48 / 56 / 72 px,
   face 43 / 50 / 62 px on an edge of 5 / 6 / 10 px. The label follows the face. */
.key {
  --depth: 6px;
  --radius: 12px;
  --height: 56px;
  --face-top: #FFDDA0;
  --face-low: #F3A955;
  --edge-top: #B86E28;
  --edge: #7A4414;
  --ink: #2A1A08;
  --light: 255, 196, 107;
  --pool: 0.34;
  --varnish: 0.32;
  --rim: 0.85;
  --line: transparent;
  --core: radial-gradient(ellipse 30% 45% at 50% 58%, rgba(255, 246, 222, 0.2), transparent);
  --flow: linear-gradient(transparent, transparent);
  position: relative;
  isolation: isolate;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  min-height: var(--height);
  margin: 0;
  padding: 0 28px var(--depth);
  border: 0;
  border-radius: var(--radius);
  background: none;
  color: var(--ink);
  font-family: var(--font-ui);
  font-size: 16px;
  font-weight: 500;
  line-height: 1.2;
  letter-spacing: 0.01em;
  text-align: center;
  text-decoration: none;
  cursor: pointer;
  user-select: none;
  -webkit-tap-highlight-color: transparent;
  box-shadow: none;
  transform: none;
  transition: padding 160ms var(--key-ease);
}

/* The edge (the key's thickness), its shadow on the bed and the pool of light under it. */
.key::before {
  content: "";
  position: absolute;
  inset: var(--depth) 0 0;
  z-index: -2;
  border-radius: var(--radius);
  background: linear-gradient(to bottom, var(--edge-top), var(--edge));
  box-shadow:
    0 3px 7px rgba(0, 0, 0, 0.55),
    0 9px 20px -6px rgba(var(--light), var(--pool));
  transition: box-shadow 160ms var(--key-ease);
}

/* The face: varnish on the upper half, the lit core, the face's gradient; the rim on top. */
.key::after {
  content: "";
  position: absolute;
  inset: 0 0 var(--depth);
  z-index: -1;
  border-radius: var(--radius);
  background:
    linear-gradient(to bottom, rgba(255, 255, 255, var(--varnish)), rgba(255, 255, 255, 0) 45%),
    var(--core),
    var(--flow),
    linear-gradient(to bottom, var(--face-top), var(--face-low));
  box-shadow:
    inset 0 1.4px 0 rgba(255, 255, 255, var(--rim)),
    inset 0 0 0 1px var(--line);
  transition: transform 160ms var(--key-ease);
}

.key:hover {
  color: var(--ink);
  --pool: 0.5;
}

/* Played: the face goes down to the bed of the edge, a core lights up and light leaks below. */
.key:active,
.key.is-pressed {
  padding-top: calc(var(--depth) - 1px);
  padding-bottom: 1px;
  --core: radial-gradient(ellipse 45% 70% at 50% 60%, rgba(255, 246, 222, 0.7), transparent);
  transition-duration: 70ms;
}

.key:active::after,
.key.is-pressed::after {
  transform: translateY(calc(var(--depth) - 1px));
  transition-duration: 70ms;
}

.key:active::before,
.key.is-pressed::before {
  box-shadow:
    0 1px 3px rgba(0, 0, 0, 0.35),
    0 1.5px 0 rgba(255, 246, 222, 0.9),
    0 6px 26px rgba(var(--light), 0.85);
  transition-duration: 70ms;
}

.key:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 3px;
}

.key svg {
  width: 20px;
  height: 20px;
  flex: none;
}

/* Medium (48 px): forms and secondary places. */
.key.small {
  --depth: 5px;
  --height: 48px;
  padding-left: 22px;
  padding-right: 22px;
  font-size: 15px;
}

/* « Secondaire »: black lacquer, a gold line at 20 %, filled with violet light when played. */
.key.secondary {
  --face-top: #3A3852;
  --face-low: #232135;
  --edge-top: #4A4763;
  --edge: #15141F;
  --ink: var(--text-primary);
  --light: 178, 141, 255;
  --pool: 0;
  --varnish: 0.15;
  --rim: 0.32;
  --line: rgba(var(--gold-rgb), 0.2);
  --core: linear-gradient(transparent, transparent);
  --flow: linear-gradient(to bottom, rgba(178, 141, 255, 0) 20%, rgba(178, 141, 255, 0.08));
}

.key.secondary:hover {
  --pool: 0.12;
  --line: rgba(var(--gold-rgb), 0.35);
}

.key.secondary:active,
.key.secondary.is-pressed {
  --core: linear-gradient(transparent, transparent);
  --flow: linear-gradient(to bottom, rgba(178, 141, 255, 0) 20%, rgba(178, 141, 255, 0.63));
  --line: rgba(var(--gold-rgb), 0.5);
}

/* « Danger »: rose, a pale line. */
.key.danger {
  --face-top: #FFA6B9;
  --face-low: #E5536F;
  --edge-top: #A83452;
  --edge: #6E1B31;
  --ink: #2E0A14;
  --light: 255, 107, 138;
  --line: rgba(255, 255, 255, 0.35);
}

.key.danger:active,
.key.danger.is-pressed {
  --core: radial-gradient(ellipse 45% 70% at 50% 60%, rgba(255, 246, 222, 0.5), transparent);
}

/* « Discret »: amber text, an amber pad when held. */
.key.quiet {
  --ink: var(--accent);
  padding: 0 16px;
  min-height: 48px;
}

.key.quiet::before {
  display: none;
}

.key.quiet::after {
  inset: 2px;
  background: transparent;
  box-shadow: none;
  transition: background-color 160ms var(--key-ease);
}

.key.quiet:hover {
  color: #FFE2B0;
}

.key.quiet:active,
.key.quiet.is-pressed {
  padding: 0 16px;
}

.key.quiet:active::after,
.key.quiet.is-pressed::after {
  transform: none;
  background: rgba(var(--gold-rgb), 0.12);
}

/* Disabled: the face goes out, the label greys, no light. */
.key:disabled,
.key[aria-disabled="true"] {
  --face-top: #2A2838;
  --face-low: #201E2E;
  --edge-top: #201E2E;
  --edge: #15141F;
  --ink: rgba(166, 163, 189, 0.6);
  --pool: 0;
  --varnish: 0.05;
  --rim: 0.08;
  --line: transparent;
  --core: linear-gradient(transparent, transparent);
  --flow: linear-gradient(transparent, transparent);
  cursor: default;
  opacity: 1;
}

.key:disabled:active,
.key[aria-disabled="true"]:active {
  padding-top: 0;
  padding-bottom: var(--depth);
}

.key:disabled:active::after,
.key[aria-disabled="true"]:active::after {
  transform: none;
}

.key:disabled::before,
.key[aria-disabled="true"]::before {
  box-shadow: 0 3px 7px rgba(0, 0, 0, 0.3);
}

/* « Héros » (72 px): its light breathes, a reflection sweeps the face, a gold filigree with
   diamonds frames it (the wrapper .filigree). */
.key.hero {
  --depth: 10px;
  --radius: 18px;
  --height: 72px;
  --pool: 0.5;
  padding-left: 40px;
  padding-right: 40px;
  font-size: 20px;
  letter-spacing: 0.02em;
}

.key.hero::before {
  animation: hero-breathe 3.2s ease-in-out infinite;
}

.key.hero::after {
  background:
    linear-gradient(105deg, transparent 38%, rgba(255, 255, 255, 0.38) 48%, transparent 58%) -150% 0 / 250% 100% no-repeat,
    linear-gradient(to bottom, rgba(255, 255, 255, var(--varnish)), rgba(255, 255, 255, 0) 45%),
    var(--core),
    linear-gradient(to bottom, var(--face-top), var(--face-low));
  animation: hero-sweep 5.5s ease-in-out infinite;
}

.key.hero:active::before,
.key.hero.is-pressed::before {
  animation: none;
}

@keyframes hero-breathe {
  0%, 100% { box-shadow: 0 3px 7px rgba(0, 0, 0, 0.55), 0 10px 26px -6px rgba(var(--light), 0.45); }
  50% { box-shadow: 0 3px 7px rgba(0, 0, 0, 0.55), 0 12px 40px -4px rgba(var(--light), 0.75); }
}

@keyframes hero-sweep {
  0%, 55% { background-position: -150% 0, 0 0, 0 0, 0 0; }
  85%, 100% { background-position: 250% 0, 0 0, 0 0, 0 0; }
}

.filigree {
  position: relative;
  display: inline-flex;
  margin: 10px 20px;
}

.filigree::before {
  content: "";
  position: absolute;
  inset: -8px;
  border: 1px solid rgba(var(--gold-rgb), 0.45);
  border-radius: 24px;
  pointer-events: none;
  transition: border-color 160ms var(--key-ease);
}

/* Diamonds at the ends and on top, a dot beyond each end. */
.filigree::after {
  content: "";
  position: absolute;
  inset: -12px -21px -8px;
  pointer-events: none;
  background:
    var(--diamond) 8px calc(50% + 2px) / 10px 10px no-repeat,
    var(--diamond) calc(100% - 8px) calc(50% + 2px) / 10px 10px no-repeat,
    var(--dot) 0 calc(50% + 2px) / 4px 4px no-repeat,
    var(--dot) 100% calc(50% + 2px) / 4px 4px no-repeat,
    var(--diamond) 50% 0 / 8px 8px no-repeat;
}

.filigree:has(.key:active)::before {
  border-color: rgba(var(--gold-rgb), 0.9);
}

/* ================================================================== Panels */

/* The lacquer of the app's panels: a gold line, a soft sheen on top. */
.ecrin {
  position: relative;
  isolation: isolate;
  border-radius: 22px;
  background:
    linear-gradient(to bottom, rgba(255, 255, 255, 0.05), rgba(255, 255, 255, 0) 180px),
    var(--lacquer);
  box-shadow:
    inset 0 0 0 1px rgba(var(--gold-rgb), 0.28),
    0 18px 50px rgba(0, 0, 0, 0.45);
}

/* For the important moments: the tone's glow around it and its light falling from the top, the
   inner frame with cut-in corners and diamonds. */
.ecrin.ornate {
  background:
    radial-gradient(ellipse 40% 170px at 50% 0, rgba(var(--tone, 255, 196, 107), 0.16), transparent 100%),
    linear-gradient(to bottom, rgba(255, 255, 255, 0.06), rgba(255, 255, 255, 0) 200px),
    var(--lacquer);
  box-shadow:
    inset 0 0 0 1px rgba(var(--gold-rgb), 0.33),
    0 0 40px rgba(var(--tone, 255, 196, 107), 0.18),
    0 18px 50px rgba(0, 0, 0, 0.45);
}

.ecrin.ornate::before {
  content: "";
  position: absolute;
  inset: 4.5px;
  z-index: -1;
  border: 20px solid transparent;
  border-image: var(--inner-frame) 20 / 20px stretch;
  pointer-events: none;
}

/* With a medallion astride the top edge. */
.ecrin.medalled {
  margin-top: 40px;
  padding-top: 56px;
}

.ecrin.medalled > .medal {
  position: absolute;
  top: 0;
  left: 50%;
  margin: 0;
  transform: translate(-50%, -50%);
}

/* The ringed medallion: a gold ring, a dark groove, the tone inside, a highlight and four tiny
   diamonds like the setting of a jewel. */
.medal {
  position: relative;
  display: grid;
  place-items: center;
  width: 76px;
  height: 76px;
  margin: 0 0 20px;
  border: 4px solid transparent;
  border-radius: 50%;
  background:
    radial-gradient(circle at 40% 30%, var(--tone-light, #FFEBC9), rgb(var(--tone, 255, 196, 107)) 75%) padding-box,
    linear-gradient(to bottom, var(--gold-light), var(--gold) 50%, var(--gold-deep)) border-box;
  box-shadow:
    inset 0 0 0 2px #14131F,
    0 0 26px rgba(var(--tone, 255, 196, 107), 0.5);
  color: #0A0A12;
}

.medal::before {
  content: "";
  position: absolute;
  inset: 5px;
  border: 2px solid transparent;
  border-top-color: rgba(255, 255, 255, 0.55);
  border-radius: 50%;
  transform: rotate(-38deg);
}

.medal::after {
  content: "";
  position: absolute;
  inset: -6.5px;
  background:
    var(--diamond-light) 50% 0 / 5px 5px no-repeat,
    var(--diamond-light) 50% 100% / 5px 5px no-repeat,
    var(--diamond-light) 0 50% / 5px 5px no-repeat,
    var(--diamond-light) 100% 50% / 5px 5px no-repeat;
}

.medal svg {
  width: 32px;
  height: 32px;
}

.medal.small {
  width: 56px;
  height: 56px;
  border-width: 3px;
}

.medal.small svg {
  width: 24px;
  height: 24px;
}

/* The ornament under a title: line, diamond, line. */
.ornament {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  width: 180px;
  height: 10px;
  margin: 16px auto 20px;
}

.ornament::before,
.ornament::after {
  content: "";
  flex: 1;
  height: 1px;
  background: linear-gradient(to right, rgba(var(--gold-rgb), 0), rgba(var(--gold-rgb), 0.7));
}

.ornament::after {
  background: linear-gradient(to left, rgba(var(--gold-rgb), 0), rgba(var(--gold-rgb), 0.7));
}

.ornament {
  background: var(--diamond) center / 9px 9px no-repeat;
}

.ornament.left {
  margin-left: 0;
  justify-content: flex-start;
}

/* ================================================================== Arches */

/* A doorway of the title screen: straight sides under an arch rising --rise above them, an outer
   gold line (gold 75 % → 30 %), an inner line, diamonds in the bottom corners and the keystone. */
.arch {
  --rise: 64px;
  --corner: 22px;
  position: relative;
  isolation: isolate;
  border-radius: 50% 50% var(--corner) var(--corner) / var(--rise) var(--rise) var(--corner) var(--corner);
  background:
    radial-gradient(ellipse 45% 25% at 50% 100%, rgba(var(--tone, 255, 196, 107), 0.14), transparent),
    linear-gradient(to bottom, rgba(255, 255, 255, 0.06), rgba(255, 255, 255, 0.02) 35%, rgba(255, 255, 255, 0) 60%),
    var(--lacquer);
  box-shadow:
    0 0 36px rgba(var(--tone, 255, 196, 107), 0.2),
    0 24px 60px rgba(0, 0, 0, 0.5);
}

.arch::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 1;
  padding: 1.2px;
  border-radius: inherit;
  background: linear-gradient(to bottom, rgba(var(--gold-rgb), 0.75), rgba(var(--gold-rgb), 0.3));
  -webkit-mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
  -webkit-mask-composite: xor;
  mask: linear-gradient(#000 0 0) content-box exclude, linear-gradient(#000 0 0);
  pointer-events: none;
}

.arch::after {
  content: "";
  position: absolute;
  inset: 9px;
  z-index: 1;
  border-radius: 50% 50% calc(var(--corner) - 9px) calc(var(--corner) - 9px) / calc(var(--rise) - 9px) calc(var(--rise) - 9px) calc(var(--corner) - 9px) calc(var(--corner) - 9px);
  box-shadow: inset 0 0 0 0.8px rgba(var(--gold-rgb), 0.4);
  background:
    var(--diamond) 3px calc(100% - 3px) / 7px 7px no-repeat,
    var(--diamond) calc(100% - 3px) calc(100% - 3px) / 7px 7px no-repeat;
  pointer-events: none;
}

/* The keystone: a diamond and a glint at the top of the arch. */
.keystone {
  position: absolute;
  top: 0;
  left: 50%;
  z-index: 2;
  width: 26px;
  height: 26px;
  transform: translate(-50%, -50%);
  background:
    var(--glint) center / 16px 16px no-repeat,
    var(--diamond) center / 12px 12px no-repeat;
  filter: drop-shadow(0 0 4px rgba(var(--gold-rgb), 0.7));
  pointer-events: none;
}

/* ================================================================== Capture frames */

/* A capture of the app, set in a lacquered frame with the inner gold frame. */
.shot {
  margin: 0;
  padding: 16px;
}

.shot img {
  display: block;
  width: 100%;
  height: auto;
  aspect-ratio: 16 / 9;
  border-radius: 10px;
  box-shadow:
    0 0 0 1px rgba(var(--gold-rgb), 0.35),
    0 10px 30px rgba(0, 0, 0, 0.5);
  background: #0A0A12;
}

/* ================================================================== Night sky */

/* The sky of the title screen: a deep night, the milky way, the moon whose halo breathes,
   twinkling stars and a shooting star now and then. sky.js paints the fine stars once; without
   it the sky keeps its glows, its moon and its bright stars. */
.sky {
  position: absolute;
  inset: 0;
  z-index: -1;
  overflow: hidden;
  pointer-events: none;
  /* The sky fades into the page below it, with no seam. */
  -webkit-mask-image: linear-gradient(to bottom, #000 calc(100% - 220px), transparent);
  mask-image: linear-gradient(to bottom, #000 calc(100% - 220px), transparent);
  background:
    radial-gradient(ellipse 80% 60% at 50% 0%, rgba(43, 36, 84, 0.55), transparent 70%),
    radial-gradient(ellipse 50% 40% at 12% 30%, rgba(92, 225, 255, 0.10), transparent 70%),
    radial-gradient(ellipse 50% 45% at 88% 55%, rgba(178, 141, 255, 0.12), transparent 70%),
    radial-gradient(ellipse 70% 30% at 50% 100%, rgba(255, 196, 107, 0.07), transparent 70%);
}

/* The milky way: a soft band across the sky, its brighter core. */
.sky .milky-way {
  position: absolute;
  left: -20%;
  right: -20%;
  top: 34%;
  height: 34%;
  transform: rotate(-16deg);
  background:
    radial-gradient(ellipse 30% 22% at 58% 50%, rgba(255, 236, 214, 0.10), transparent 70%),
    radial-gradient(ellipse 50% 40% at 40% 50%, rgba(178, 141, 255, 0.10), transparent 72%),
    radial-gradient(ellipse 50% 36% at 70% 55%, rgba(92, 225, 255, 0.08), transparent 72%),
    linear-gradient(to bottom, transparent, rgba(220, 210, 255, 0.05) 40%, rgba(220, 210, 255, 0.06) 55%, transparent);
  filter: blur(6px);
}

.sky canvas {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
}

/* The moon: seas, a lit rim, a halo that breathes. */
.sky .moon {
  position: absolute;
  top: 110px;
  right: 9%;
  width: clamp(56px, 7vw, 92px);
  aspect-ratio: 1;
  border-radius: 50%;
  background:
    radial-gradient(ellipse 34% 24% at 40% 40%, rgba(150, 144, 178, 0.30), transparent 75%),
    radial-gradient(ellipse 22% 30% at 64% 60%, rgba(150, 144, 178, 0.24), transparent 75%),
    radial-gradient(ellipse 26% 14% at 46% 72%, rgba(150, 144, 178, 0.16), transparent 75%),
    radial-gradient(ellipse 12% 9% at 66% 30%, rgba(150, 144, 178, 0.20), transparent 75%),
    radial-gradient(circle at 38% 32%, #FFFDF4, #F1EAD8 55%, #CFC6B4);
  box-shadow:
    inset -6px -4px 12px rgba(120, 110, 150, 0.35),
    0 0 0 1px rgba(255, 246, 222, 0.5),
    0 0 30px rgba(255, 240, 210, 0.45);
}

.sky .moon::before {
  content: "";
  position: absolute;
  inset: -80%;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(255, 236, 200, 0.22), rgba(178, 141, 255, 0.08) 45%, transparent 70%);
  animation: moon-breathe 6s ease-in-out infinite;
}

/* Phones: a small moon in the corner, clear of the title. */
@media (max-width: 600px) {
  .sky .moon {
    top: 14px;
    right: 14px;
    width: 40px;
  }

  .sky .shooting {
    width: 90px;
  }
}

@keyframes moon-breathe {
  0%, 100% { opacity: 0.7; transform: scale(0.94); }
  50% { opacity: 1; transform: scale(1.06); }
}

/* Bright stars: four-pointed glints that twinkle as they turn. */
.sky .glint {
  position: absolute;
  width: 18px;
  height: 18px;
  background: var(--glint-white) center / contain no-repeat;
  filter: drop-shadow(0 0 5px rgba(184, 241, 255, 0.9));
  opacity: 0.85;
  animation: twinkle 4.2s ease-in-out infinite;
}

.sky .glint:nth-of-type(1) { top: 16%; left: 8%;  animation-delay: -0.6s; }
.sky .glint:nth-of-type(2) { top: 30%; left: 24%; width: 12px; height: 12px; animation-delay: -2.1s; }
.sky .glint:nth-of-type(3) { top: 12%; left: 46%; width: 14px; height: 14px; animation-delay: -3.3s; filter: drop-shadow(0 0 5px rgba(220, 203, 255, 0.9)); }
.sky .glint:nth-of-type(4) { top: 40%; left: 70%; width: 12px; height: 12px; animation-delay: -1.4s; }
.sky .glint:nth-of-type(5) { top: 26%; left: 84%; animation-delay: -2.8s; filter: drop-shadow(0 0 5px rgba(255, 220, 160, 0.9)); }
.sky .glint:nth-of-type(6) { top: 58%; left: 6%;  width: 12px; height: 12px; animation-delay: -3.9s; }
.sky .glint:nth-of-type(7) { top: 62%; left: 93%; width: 14px; height: 14px; animation-delay: -0.2s; }

@keyframes twinkle {
  0%, 100% { opacity: 0.85; transform: scale(1) rotate(0deg); }
  45% { opacity: 0.3; transform: scale(0.55) rotate(30deg); }
  60% { opacity: 1; transform: scale(1.15) rotate(45deg); }
}

/* A shooting star every 11 s, for 0.9 s. */
.sky .shooting {
  position: absolute;
  top: 14%;
  left: 62%;
  width: 140px;
  height: 2px;
  border-radius: 999px;
  background: linear-gradient(to left, rgba(255, 255, 255, 0.95), rgba(184, 241, 255, 0.4) 30%, transparent);
  filter: drop-shadow(0 0 4px rgba(184, 241, 255, 0.8));
  opacity: 0;
  transform: rotate(-24deg) translateX(0);
  animation: shooting 11s linear infinite;
  animation-delay: 3s;
}

@keyframes shooting {
  0% { opacity: 0; transform: rotate(150deg) translateX(0); }
  1% { opacity: 1; }
  7% { opacity: 0; transform: rotate(150deg) translateX(-320px); }
  100% { opacity: 0; transform: rotate(150deg) translateX(-320px); }
}

/* ================================================================== Reference page */

/* web/ecrin.html: every component and state, to judge them on a tablet. */
.portal h1.specimen-title {
  font-family: var(--font-title);
  font-weight: 300;
  font-size: clamp(40px, 6vw, 64px);
  text-shadow: none;
}

.specimen-grid {
  display: grid;
  gap: 28px;
}

.specimen-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 20px 24px;
}

.specimen-name {
  width: 120px;
  color: var(--text-secondary);
  font-size: 13px;
  font-weight: 500;
  letter-spacing: 0.12em;
  text-transform: uppercase;
}

.specimen-panels {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(260px, 1fr));
  gap: 56px 24px;
}

.specimen-panel {
  padding: 56px 24px 28px;
  text-align: center;
}

.specimen-panel.card {
  margin-top: 40px;
  padding-top: 28px;
}

.specimen-panel h3 {
  margin: 0;
  font-family: var(--font-title);
  font-size: 24px;
  font-weight: 300;
}

.specimen-panel p {
  margin: 0;
  color: var(--text-secondary);
}

.specimen-panel .chips {
  justify-content: center;
  margin-top: 12px;
}

.specimen-panel .panel-actions {
  gap: 12px;
  margin-top: 20px;
}

.specimen-arches {
  display: grid;
  grid-template-columns: minmax(0, 340px) minmax(0, 1fr);
  align-items: end;
  gap: 40px;
}

.specimen-arch h3 {
  margin: 0 0 8px;
  font-family: var(--font-title);
  font-size: 26px;
  font-weight: 300;
}

.specimen-arch {
  min-height: 360px;
}

@media (max-width: 760px) {
  .specimen-arches {
    grid-template-columns: minmax(0, 1fr);
  }
}

/* ================================================================== Reduced motion */

@media (prefers-reduced-motion: reduce) {
  .key,
  .key::before,
  .key::after,
  .filigree::before {
    transition: none;
  }

  .key.hero::before,
  .key.hero::after,
  .sky .moon::before,
  .sky .glint {
    animation: none;
  }

  .sky .shooting {
    display: none;
  }
}
