/* JOI · widget styles
   A device, not a page: it looks the same over light and dark desktops.
   Smoked glass, a hologram rim (cyan -> violet -> magenta), a colour LCD. */

.joi {
  --joi-w: 288px;
  --joi-shell-hi: #282143;
  --joi-shell: #17132A;
  --joi-shell-lo: #0C0A16;
  --joi-cyan: #5CF2FF;
  --joi-magenta: #FF4FD8;
  --joi-violet: #9B6BFF;
  --joi-pink: #FFB3E6;
  --joi-ink: #EEE8FF;
  --joi-ink-2: #B7ACD8;
  --joi-ink-3: #7F74A6;
  --joi-field: #0E0B1B;
  --joi-field-edge: rgb(255 255 255 / .07);
  --joi-px: 'Silkscreen', ui-monospace, 'SF Mono', Menlo, monospace;
  --joi-mono: 'Fragment Mono', ui-monospace, 'SF Mono', Menlo, monospace;
  --joi-ease: cubic-bezier(.23, 1, .32, 1);
  --joi-enter: 280ms;
  --joi-exit: 200ms;
  --joi-shadow: 0 24px 60px rgb(0 0 0 / .55), 0 4px 12px rgb(0 0 0 / .4), 0 0 44px rgb(155 107 255 / .16);
  position: fixed;
  left: 0;
  top: 0;
  z-index: 2147483000;
  font-family: var(--joi-mono);
  color: var(--joi-ink);
  -webkit-font-smoothing: antialiased;
  -webkit-tap-highlight-color: transparent;
}
.joi *, .joi *::before, .joi *::after { box-sizing: border-box; }
.joi[data-open="false"] .joi-shell,
.joi[data-open="true"] .joi-pill { display: none; }

/* ------------------------------------------------------------------ shared body */
.joi-shell,
.joi-pill {
  position: relative;
  background:
    radial-gradient(120% 70% at 18% 0%, rgb(155 107 255 / .16), transparent 62%),
    linear-gradient(170deg, var(--joi-shell-hi), var(--joi-shell) 46%, var(--joi-shell-lo));
  box-shadow:
    inset 0 1px 0 rgb(255 255 255 / .10),
    0 0 0 1px rgb(6 4 14 / .9),
    var(--joi-shadow);
  transition: transform 200ms var(--joi-ease), box-shadow 200ms var(--joi-ease);
}
/* hologram rim: a 1px gradient border */
.joi-shell::before,
.joi-pill::before {
  content: '';
  position: absolute;
  inset: 0;
  border-radius: inherit;
  padding: 1px;
  /* the rim never fades out entirely: over a dark wallpaper it is what draws the device's edge */
  background: linear-gradient(150deg, rgb(92 242 255 / .55), rgb(155 107 255 / .3) 38%, rgb(255 79 216 / .16) 70%, rgb(255 79 216 / .38));
  -webkit-mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
  -webkit-mask-composite: xor;
  mask-composite: exclude;
  pointer-events: none;
}
.joi.is-carried .joi-shell,
.joi.is-carried .joi-pill {
  transform: translateY(-4px) rotate(-1.2deg) scale(1.02);
  box-shadow: inset 0 1px 0 rgb(255 255 255 / .10), 0 0 0 1px rgb(6 4 14 / .9),
    0 34px 70px rgb(0 0 0 / .6), 0 8px 18px rgb(0 0 0 / .4), 0 0 56px rgb(92 242 255 / .18);
  cursor: grabbing;
}
.joi.is-snapping { transition: left 300ms var(--joi-ease), top 300ms var(--joi-ease); }

/* nothing animates on load; after boot, the swap between pill and shell rises into place */
.joi.is-booted .joi-shell { animation: joi-rise var(--joi-enter) var(--joi-ease); transform-origin: 100% 100%; }
.joi.is-booted .joi-pill { animation: joi-rise var(--joi-exit) var(--joi-ease); transform-origin: 100% 100%; }
@keyframes joi-rise { from { opacity: 0; transform: translateY(6px) scale(.97); } }

/* ------------------------------------------------------------------ closed: the pill */
.joi-pill {
  display: flex;
  align-items: center;
  gap: 10px;
  height: 48px;
  padding: 0 12px 0 6px;
  border: 0;
  border-radius: 999px;
  color: var(--joi-ink);
  cursor: pointer;
  touch-action: none;
  user-select: none;
  -webkit-user-select: none;
}
.joi-pill:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 3px; }
.joi-pill-face {
  display: grid;
  place-items: center;
  width: 36px;
  height: 36px;
  border-radius: 50%;
  background: radial-gradient(closest-side, rgb(255 216 74 / .22), rgb(255 216 74 / 0));
}
.joi-mini { display: block; width: 32px; height: 32px; image-rendering: pixelated; }
.joi-pill-text { display: flex; flex-direction: column; align-items: flex-start; gap: 4px; }
.joi-pill-name { font: 11px/1 var(--joi-px); letter-spacing: .14em; }
.joi-pill-mood { font: 8px/1 var(--joi-px); letter-spacing: .14em; text-transform: uppercase; color: var(--joi-ink-3); }
.joi-new {
  display: none;
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--joi-magenta);
  box-shadow: 0 0 8px var(--joi-magenta);
}
.joi[data-unread="true"] .joi-new { display: block; }
.joi-chev { display: grid; place-items: center; width: 20px; height: 20px; color: var(--joi-ink-2); }

/* ------------------------------------------------------------------ open: the device */
.joi-shell {
  width: var(--joi-w);
  max-width: calc(100vw - 24px);
  padding: 8px 16px 14px;
  border-radius: 22px;
}
.joi-top {
  display: flex;
  align-items: center;
  gap: 8px;
  height: 28px;
  margin-bottom: 6px;
  cursor: grab;
  touch-action: none;
  user-select: none;
  -webkit-user-select: none;
}
.joi-top:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 2px; border-radius: 6px; }
.joi-led {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--joi-cyan);
  box-shadow: 0 0 8px rgb(92 242 255 / .9);
  transition: background 200ms, box-shadow 200ms;
}
.joi[data-led="think"] .joi-led { background: var(--joi-violet); box-shadow: 0 0 9px var(--joi-violet); animation: joi-pulse 1.1s ease-in-out infinite; }
.joi[data-led="speak"] .joi-led { background: var(--joi-magenta); box-shadow: 0 0 9px var(--joi-magenta); }
.joi[data-led="sleep"] .joi-led { background: #3B3358; box-shadow: none; }
@keyframes joi-pulse { 50% { opacity: .35; } }
.joi-name { font: 11px/1 var(--joi-px); letter-spacing: .14em; }
.joi-mood {
  flex: 1;
  font: 8px/1 var(--joi-px);
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--joi-ink-3);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.joi-engine {
  font: 7px/1 var(--joi-px);
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--joi-ink-3);
  padding: 3px 5px 2px;
  border-radius: 4px;
  box-shadow: inset 0 0 0 1px rgb(255 255 255 / .1);
}
.joi-engine[hidden] { display: none; }
.joi-icon {
  display: grid;
  place-items: center;
  width: 26px;
  height: 26px;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: var(--joi-ink-2);
  cursor: pointer;
  transition: background 120ms, color 120ms, transform 160ms var(--joi-ease);
}
.joi-close { margin-right: -6px; }
.joi-icon:active { transform: scale(.94); }
.joi-icon:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 1px; }
.joi-icon[aria-pressed="true"] { color: var(--joi-cyan); background: rgb(92 242 255 / .1); }
@media (hover: hover) and (pointer: fine) {
  .joi-icon:hover { background: rgb(255 255 255 / .07); color: var(--joi-ink); }
  .joi-icon[aria-pressed="true"]:hover { background: rgb(92 242 255 / .14); color: var(--joi-cyan); }
}
.joi-icon svg { width: 15px; height: 15px; }

/* the screen: 256 CSS px = 64 cells x 4 */
.joi-screen {
  position: relative;
  width: 256px;
  height: 256px;
  margin: 0 auto;
  border-radius: 10px;
  overflow: hidden;
  background: #0B0916;
  box-shadow: 0 0 0 1px rgb(0 0 0 / .7), 0 0 0 3px rgb(255 255 255 / .035), 0 0 24px rgb(155 107 255 / .12);
  cursor: pointer;
  touch-action: none;
  outline: none;
  isolation: isolate;
}
.joi-screen:focus-visible { box-shadow: 0 0 0 2px var(--joi-cyan), 0 0 24px rgb(92 242 255 / .25); }
.joi-lcd,
.joi-bloom { position: absolute; inset: 0; width: 100%; height: 100%; display: block; }
.joi-lcd { image-rendering: pixelated; z-index: 0; }
/* the glow: a touch softer in v8, so it reads as light from the panel rather than haze over her */
.joi-bloom { z-index: 1; filter: blur(6px) saturate(1.2); opacity: .28; mix-blend-mode: screen; pointer-events: none; }
.joi-scan {
  position: absolute;
  left: 0;
  right: 0;
  top: -30%;
  height: 30%;
  z-index: 2;
  background: linear-gradient(rgb(92 242 255 / 0), rgb(92 242 255 / .045) 60%, rgb(92 242 255 / 0));
  animation: joi-scan 8s linear infinite;
  pointer-events: none;
}
@keyframes joi-scan { to { transform: translateY(433%); } }
.joi-glass {
  position: absolute;
  inset: 0;
  z-index: 3;
  border-radius: inherit;
  background: linear-gradient(162deg, rgb(255 255 255 / .09), rgb(255 255 255 / 0) 34%);
  box-shadow: inset 0 2px 8px rgb(0 0 0 / .45), inset 0 0 0 1px rgb(255 255 255 / .05);
  pointer-events: none;
}
.joi[data-clip="sleep"] .joi-scan { animation-duration: 14s; opacity: .5; }
/* clean pixels unless the colour-LCD treatment is on */
.joi:not([data-lcd="true"]) .joi-scan,
.joi:not([data-lcd="true"]) .joi-bloom { display: none; }
.joi:not([data-lcd="true"]) .joi-glass { background: none; }
/* v8: the panel's edges fall off a little, as a lit screen's do (only with the LCD effect on) */
.joi[data-lcd="true"] .joi-glass {
  background:
    linear-gradient(162deg, rgb(255 255 255 / .08), rgb(255 255 255 / 0) 34%),
    radial-gradient(120% 120% at 50% 45%, rgb(0 0 0 / 0) 62%, rgb(6 3 14 / .26) 100%);
}

/* the status bar (v7): which day together it is, since when, and how many messages, under her screen */
.joi-status {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  width: 256px;
  height: 14px;
  margin: 9px auto 0;
  font: 7px/1 var(--joi-px);
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--joi-ink-3);
  white-space: nowrap;
  user-select: none;
  -webkit-user-select: none;
  /* v8: a button (click to see more), without looking like one */
  padding: 0 2px;
  border: 0;
  border-radius: 4px;
  background: none;
  cursor: pointer;
  transition: color 120ms;
}
.joi-status:focus-visible { outline: 1px solid var(--joi-cyan); outline-offset: 2px; }
@media (hover: hover) and (pointer: fine) { .joi-status:hover { color: var(--joi-ink-2); } }
.joi-status span { transition: opacity 160ms; }
.joi-status[hidden], .joi[data-mode="style"] .joi-status { display: none; }
.joi-status-day { display: inline-flex; align-items: center; gap: 6px; color: var(--joi-ink-2); }
/* a filled pixel heart (the icon rule below strokes every svg in the widget) */
.joi .joi-status svg { width: 14px; height: 12px; fill: var(--joi-pink); stroke: none; filter: drop-shadow(0 0 4px rgb(255 179 230 / .45)); }

/* her line (v9): three lines high, always, so the widget never changes size while she talks. The line is laid out
   whole before she types it (a span per letter) and the letters fade in where they sit; a longer line scrolls inside,
   with a fade at the edge that has more. It hangs off a thin hologram bar that stays put while the text scrolls */
.joi-say {
  --joi-line: 18px;
  position: relative;
  margin: 12px 2px 0;
  padding-left: 12px;
  height: calc(var(--joi-line) * 3);
  font-size: 12px;
  line-height: var(--joi-line);
  color: var(--joi-ink);
  cursor: default;
}
.joi[data-speaking="true"] .joi-say { cursor: pointer; }
.joi-say-in {
  position: relative;
  height: 100%;
  overflow-y: auto;
  white-space: pre-wrap;
  overflow-wrap: break-word;
  scrollbar-width: none;
  overscroll-behavior: contain;
}
.joi-say-in::-webkit-scrollbar { display: none; }
/* more above: the top edge fades; more below (you scrolled back up): the bottom edge does */
.joi-say[data-more="up"] .joi-say-in { -webkit-mask-image: linear-gradient(to bottom, transparent 0, #000 14px); mask-image: linear-gradient(to bottom, transparent 0, #000 14px); }
.joi-say[data-more="down"] .joi-say-in { -webkit-mask-image: linear-gradient(to top, transparent 0, #000 14px); mask-image: linear-gradient(to top, transparent 0, #000 14px); }
.joi-say[data-more="both"] .joi-say-in { -webkit-mask-image: linear-gradient(transparent 0, #000 14px, #000 calc(100% - 14px), transparent); mask-image: linear-gradient(transparent 0, #000 14px, #000 calc(100% - 14px), transparent); }
.joi-say::before {
  content: '';
  position: absolute;
  left: 0;
  top: 2px;
  bottom: 2px;
  width: 2px;
  border-radius: 1px;
  background: linear-gradient(var(--joi-cyan), var(--joi-violet) 60%, var(--joi-magenta));
  opacity: .75;
}
.joi-say-text:empty::before { content: attr(data-empty); color: var(--joi-ink-3); }
.joi[data-speaking="true"] .joi-say-text:empty::before { content: none; }
/* a letter not said yet keeps its place, unseen; said, it fades in */
.joi-ch { opacity: 0; transition: opacity 180ms linear; }
.joi-ch.is-on { opacity: 1; }
@media (prefers-reduced-motion: reduce) { .joi-ch { transition: none; } }
/* the caret follows the last letter she said (placed by widget.js, so it never pushes the text) */
.joi-caret {
  position: absolute;
  left: 0;
  top: 0;
  width: 6px;
  height: 11px;
  background: var(--joi-cyan);
  box-shadow: 0 0 6px rgb(92 242 255 / .8);
  animation: joi-caret 1s steps(1) infinite;
  pointer-events: none;
}
.joi-caret[hidden] { display: none; }
@keyframes joi-caret { 50% { opacity: 0; } }

/* history */
.joi-log { margin-top: 10px; padding-top: 10px; border-top: 1px solid rgb(255 255 255 / .06); }
.joi-log[hidden] { display: none; }
.joi-log-list {
  display: flex;
  flex-direction: column;
  gap: 9px;
  max-height: 168px;
  margin: 0;
  padding: 0 2px;
  overflow-y: auto;
  list-style: none;
  font-size: 11px;
  line-height: 15px;
  scrollbar-width: thin;
  scrollbar-color: rgb(255 255 255 / .12) transparent;
}
.joi-msg { display: flex; flex-direction: column; gap: 3px; }
.joi-msg-who { font: 7px/1 var(--joi-px); letter-spacing: .14em; text-transform: uppercase; color: var(--joi-ink-3); }
.joi-msg-text { color: var(--joi-ink-2); white-space: pre-wrap; overflow-wrap: anywhere; }
.joi-msg[data-who="you"] { align-items: flex-end; text-align: right; }
.joi-msg[data-who="you"] .joi-msg-text { color: #BDF8FF; }
.joi-msg[data-error="true"] .joi-msg-text { color: var(--joi-pink); }

/* input */
.joi-ask {
  display: flex;
  align-items: flex-end;
  gap: 4px;
  margin-top: 10px;
  padding: 4px;
  border-radius: 14px;
  background: var(--joi-field);
  box-shadow: inset 0 0 0 1px var(--joi-field-edge), inset 0 1px 3px rgb(0 0 0 / .4);
  transition: box-shadow 160ms var(--joi-ease);
}
.joi-ask:focus-within { box-shadow: inset 0 0 0 1px rgb(92 242 255 / .45), 0 0 0 3px rgb(92 242 255 / .08); }
.joi-input {
  flex: 1;
  min-width: 0;
  min-height: 28px;
  max-height: 96px;
  padding: 5px 4px;
  border: 0;
  outline: 0;
  resize: none;
  background: transparent;
  color: var(--joi-ink);
  font: 12px/18px var(--joi-mono);
}
.joi-input::placeholder { color: var(--joi-ink-3); }
.joi-send,
.joi-hist {
  position: relative;
  display: grid;
  place-items: center;
  flex: none;
  width: 28px;
  height: 28px;
  border: 0;
  border-radius: 10px;
  cursor: pointer;
  transition: background 120ms, color 120ms, transform 120ms var(--joi-ease);
}
.joi-send { background: var(--joi-cyan); color: #0B0916; box-shadow: 0 0 12px rgb(92 242 255 / .35); }
.joi-send:active:not(:disabled) { transform: scale(.94); }
.joi-send:disabled { background: rgb(255 255 255 / .06); color: var(--joi-ink-3); box-shadow: none; cursor: default; }
.joi-hist { background: transparent; color: var(--joi-ink-3); }
.joi-hist:hover { color: var(--joi-ink-2); background: rgb(255 255 255 / .05); }
.joi-hist[aria-expanded="true"] { color: var(--joi-cyan); background: rgb(92 242 255 / .08); }
.joi-send:focus-visible, .joi-hist:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 1px; }
.joi-hist-n {
  position: absolute;
  top: 1px;
  right: 0;
  min-width: 13px;
  height: 11px;
  padding: 0 3px;
  border-radius: 6px;
  background: rgb(155 107 255 / .9);
  color: #fff;
  font: 7px/11px var(--joi-px);
  text-align: center;
  box-shadow: 0 0 0 2px var(--joi-field);
}
.joi-hist-n:empty { display: none; }
.joi svg { width: 14px; height: 14px; fill: none; stroke: currentColor; stroke-width: 1.7; stroke-linecap: round; stroke-linejoin: round; }
.joi-chev svg, .joi-close svg { width: 12px; height: 12px; }

/* ------------------------------------------------------------------ style drawer (wardrobe)
   Replaces the chat area while it is open; her screen stays in view above it. */
.joi[data-mode="style"] .joi-say,
.joi[data-mode="style"] .joi-log,
.joi[data-mode="style"] .joi-ask { display: none; }
.joi-style { margin-top: 12px; }
.joi-style[hidden] { display: none; }
.joi-tabs {
  display: flex;
  gap: 2px;
  padding: 3px;
  border-radius: 11px;
  background: rgb(0 0 0 / .3);
  box-shadow: inset 0 0 0 1px rgb(255 255 255 / .04);
}
.joi-tab {
  flex: 1 1 auto;
  min-width: 0;
  height: 24px;
  padding: 0 2px;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: var(--joi-ink-3);
  font: 8px/1 var(--joi-px);
  letter-spacing: .04em;
  text-transform: uppercase;
  cursor: pointer;
  transition: background 140ms, color 140ms;
}
.joi-tab[aria-selected="true"] { background: rgb(255 255 255 / .09); color: var(--joi-ink); box-shadow: inset 0 1px 0 rgb(255 255 255 / .06); }
.joi-tab:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: -2px; }
@media (hover: hover) and (pointer: fine) { .joi-tab:hover:not([aria-selected="true"]) { color: var(--joi-ink-2); } }
.joi-style-body {
  max-height: 268px;
  margin: 10px -4px 0;
  padding: 0 4px 2px;
  overflow-y: auto;
  overscroll-behavior: contain;
  scrollbar-width: thin;
  scrollbar-color: rgb(255 255 255 / .12) transparent;
}
.joi-group + .joi-group { margin-top: 12px; }
.joi-group-head { display: flex; align-items: baseline; justify-content: space-between; gap: 8px; margin-bottom: 7px; }
.joi-group-name { font: 7px/1 var(--joi-px); letter-spacing: .16em; text-transform: uppercase; color: var(--joi-ink-3); }
.joi-group-pick { font-size: 11px; line-height: 1; color: var(--joi-cyan); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.joi-opts { display: flex; flex-wrap: wrap; gap: 6px; }
/* tiles are drawn at a whole number of device pixels per field pixel (widget.js tileGeom), so the grid
   takes their size rather than stretching them */
.joi-group-tile .joi-opts { display: grid; grid-template-columns: repeat(4, max-content); justify-content: space-between; row-gap: 6px; }
.joi-opt {
  position: relative;
  padding: 0;
  border: 0;
  cursor: pointer;
  transition: transform 160ms var(--joi-ease), box-shadow 140ms, filter 140ms;
}
.joi-opt:active { transform: scale(.95); }
.joi-opt:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 2px; }
/* a tile: 40x40 field pixels at 1.5 CSS px (3 device px on retina), square corners inside a soft frame */
.joi-tile {
  display: block;
  border-radius: 9px;
  overflow: hidden;
  background: var(--joi-field);
  box-shadow: inset 0 0 0 1px rgb(255 255 255 / .07);
}
.joi-tile canvas { display: block; width: 60px; height: 60px; image-rendering: pixelated; }
.joi-tile::after { content: ''; position: absolute; inset: 0; border-radius: inherit; box-shadow: inset 0 0 0 1px rgb(0 0 0 / .35); pointer-events: none; }
.joi-tile[aria-pressed="true"]::after { box-shadow: inset 0 0 0 2px var(--joi-cyan), inset 0 0 0 3px rgb(11 9 22 / .8); }
.joi-tile[aria-pressed="true"] { box-shadow: 0 0 14px rgb(92 242 255 / .28); }
/* the scene that follows the clock (v7): it shows the scene of the moment, so it carries a badge */
.joi-tile[data-auto]::before {
  content: 'AUTO';
  position: absolute;
  left: 4px;
  bottom: 4px;
  padding: 3px 4px 2px;
  border-radius: 4px;
  background: rgb(11 9 22 / .78);
  color: var(--joi-cyan);
  font: 6px/1 var(--joi-px);
  letter-spacing: .1em;
  pointer-events: none;
}
@media (hover: hover) and (pointer: fine) { .joi-tile:hover:not([aria-pressed="true"]) { filter: brightness(1.12); } }
/* a swatch: two levels of the ramp, split on the diagonal */
.joi-swatch {
  width: 24px;
  height: 24px;
  border-radius: 50%;
  box-shadow: inset 0 0 0 1px rgb(255 255 255 / .18), 0 1px 2px rgb(0 0 0 / .4);
}
.joi-swatch[aria-pressed="true"] { box-shadow: inset 0 0 0 1px rgb(255 255 255 / .18), 0 0 0 2px var(--joi-shell), 0 0 0 3.5px var(--joi-cyan); }
.joi-swatch.joi-auto { background: repeating-linear-gradient(135deg, rgb(255 255 255 / .1) 0 3px, transparent 3px 6px), var(--joi-field); }
@media (hover: hover) and (pointer: fine) { .joi-swatch:hover { transform: scale(1.08); } }
/* body size: a segmented control */
.joi-group-seg .joi-opts { gap: 2px; padding: 3px; border-radius: 10px; background: rgb(0 0 0 / .3); }
.joi-seg {
  flex: 1;
  height: 24px;
  border-radius: 7px;
  background: transparent;
  color: var(--joi-ink-2);
  font: 11px/1 var(--joi-mono);
}
.joi-seg[aria-pressed="true"] { background: rgb(255 255 255 / .1); color: var(--joi-ink); }
.joi-style-foot { display: flex; gap: 6px; margin-top: 12px; }
/* the Looks tab: your saved looks carry a remove button; the last tile saves the look she's wearing */
.joi-saved { position: relative; }
.joi-forget {
  position: absolute;
  top: -5px;
  right: -5px;
  display: grid;
  place-items: center;
  width: 18px;
  height: 18px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: var(--joi-shell-hi);
  color: var(--joi-ink-2);
  box-shadow: 0 0 0 1px rgb(255 255 255 / .14), 0 2px 6px rgb(0 0 0 / .5);
  cursor: pointer;
  opacity: 0;
  transform: scale(.8);
  transition: opacity 140ms var(--joi-ease), transform 140ms var(--joi-ease), color 120ms;
}
.joi-forget svg { width: 10px; height: 10px; stroke-width: 2; }
.joi-saved:hover .joi-forget, .joi-saved:focus-within .joi-forget { opacity: 1; transform: none; }
@media (hover: none) { .joi-forget { opacity: 1; transform: none; } }
.joi-forget:hover { color: var(--joi-pink); }
.joi-forget:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 1px; opacity: 1; }
.joi-save {
  display: grid;
  place-content: center;
  justify-items: center;
  gap: 5px;
  width: 60px;
  height: 60px;
  background: transparent;
  color: var(--joi-ink-3);
  box-shadow: inset 0 0 0 1px rgb(255 255 255 / .12);
  font: 7px/1 var(--joi-px);
  letter-spacing: .14em;
  text-transform: uppercase;
}
.joi-save::after { display: none; }
.joi-save svg { width: 16px; height: 16px; }
@media (hover: hover) and (pointer: fine) { .joi-save:hover { color: var(--joi-cyan); box-shadow: inset 0 0 0 1px rgb(92 242 255 / .45); filter: none; } }
.joi-chip {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  height: 30px;
  padding: 0 10px;
  border: 0;
  border-radius: 10px;
  background: rgb(255 255 255 / .06);
  color: var(--joi-ink-2);
  font: 11px/1 var(--joi-mono);
  cursor: pointer;
  transition: background 120ms, color 120ms, transform 160ms var(--joi-ease);
}
.joi-chip svg { width: 14px; height: 14px; }
.joi-chip:active { transform: scale(.96); }
.joi-chip:focus-visible { outline: 2px solid var(--joi-cyan); outline-offset: 1px; }
@media (hover: hover) and (pointer: fine) { .joi-chip:hover { background: rgb(255 255 255 / .1); color: var(--joi-ink); } }
.joi-done { margin-left: auto; padding: 0 14px; background: var(--joi-cyan); color: #0B0916; box-shadow: 0 0 12px rgb(92 242 255 / .3); }
@media (hover: hover) and (pointer: fine) { .joi-done:hover { background: #8CF6FF; color: #0B0916; } }
/* v7: Put back (what she wore before she changed herself, or before you asked) and, in the Looks tab, Keep this look
   (she won't change it on her own) */
.joi-looks-bar { display: flex; flex-wrap: wrap; gap: 6px; margin: 0 0 12px; }
.joi-looks-bar .joi-chip { height: 26px; }
.joi-looks-bar .joi-share { margin-left: 0; }
.joi-looks-bar .joi-keep + .joi-share, .joi-looks-bar .joi-keep[hidden] + .joi-share { margin-left: auto; }
.joi-keep[aria-pressed="true"] { background: rgb(92 242 255 / .12); color: var(--joi-cyan); box-shadow: inset 0 0 0 1px rgb(92 242 255 / .35); }
.joi-chip[hidden] { display: none; }

.joi-sr {
  position: absolute !important;
  width: 1px;
  height: 1px;
  margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
  border: 0;
}

@media (prefers-reduced-motion: reduce) {
  .joi *, .joi.is-snapping { animation: none !important; transition: none !important; }
  .joi-scan { display: none; }
}
