/* studio.css — Clean modern stylesheet for InkedStudio / InkedStudio module.
   Mobile-first, no build step, drop-in for any host page.
   CSS custom properties so the host can theme via :root vars. */

:root {
  /* Brand — InkedGirls palette (Pantone 1495 C + 185 C). Orange is the
     primary action colour (user bubbles, primary buttons, focus rings),
     red is the secondary / hot accent (jump links, gradient end-stop,
     badges). Surfaces stay light so the warm accents pop. */
  --studio-accent: #ff8b00;            /* primary action — InkedGirls orange (Pantone 1495 C) */
  --studio-accent-2: #ff000d;           /* secondary — InkedGirls red (Pantone 185 C) */
  --studio-accent-3: #ff000d;           /* tertiary — same red; legacy slot kept for chips/badges */
  --studio-accent-soft: #fff4e6;        /* orange-tinted hover/active bg */
  --studio-accent-2-soft: #ffeaea;      /* red-tinted hover/active bg */

  /* Surfaces — warm off-white so the brand orange/red sit forward */
  --studio-bg: #fffaf3;
  --studio-surface: #ffffff;
  --studio-surface-2: #faf6ef;
  --studio-border: #e8dccb;             /* warmer than zinc so it harmonises with orange */
  --studio-border-strong: #b8a78f;       /* visible-but-not-loud */
  --studio-border-accent: rgba(255, 139, 0, .35);

  /* Text */
  --studio-text: #1f1410;                /* warm near-black */
  --studio-text-muted: #6b5a4d;
  --studio-text-soft: #a89a8a;

  /* Status — semantic colours, NOT brand. Error stays a clear signal red
     so destructive actions don't compete with the brand red accent. */
  --studio-success: #059669;
  --studio-warn: #d97706;
  --studio-error: #dc2626;

  /* Radius / shadow — slightly tighter + heavier for a tougher look */
  --studio-radius: 12px;
  --studio-radius-sm: 6px;
  --studio-shadow-sm: 0 1px 2px rgba(15, 23, 42, .08);
  --studio-shadow: 0 6px 24px rgba(15, 23, 42, .10);
  --studio-shadow-lg: 0 16px 48px rgba(15, 23, 42, .14);

  /* Layout */
  --studio-max-width: 1320px;
  --studio-header-h: 56px;
}

/* ---------- reset / base ---------- */
*, *::before, *::after { box-sizing: border-box; }
html, body { scroll-behavior: smooth; }

.inked-studio,
.inked-studio * {
  font-family: 'Avenir Next', Avenir, 'Helvetica Neue', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
  line-height: 1.5;
}

.inked-studio {
  display: block;
  width: 100%;
  max-width: var(--studio-max-width);
  /* v77: chat and gallery each render in their own card. The outer
     .inked-studio is a plain block with a small bottom margin so
     the gallery card has breathing room before the page edge. The
     page itself scrolls; cards stay in document flow. */
  margin: 0 auto 16px;
  background: transparent;
  border: 0;
  border-radius: 0;
  box-shadow: none;
  color: var(--studio-text);
}
/* On mobile, drop the bottom margin so the gallery card sits tight. */
@media (max-width: 720px) {
  .inked-studio {
    max-width: none;
    margin-bottom: 8px;
  }
}

/* ---------- header ---------- */
.is-header {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 10px 12px;
  padding: 12px 16px;
  border-bottom: 1px solid var(--studio-border);
  background: linear-gradient(135deg, var(--studio-accent-soft) 0%, var(--studio-accent-2-soft) 100%);
}

.is-header-title {
  display: flex;
  align-items: center;
  gap: 12px;
  margin: 0;
  font-size: 16px;
  font-weight: 700;
  letter-spacing: -.01em;
  flex: 1 1 auto;
  min-width: 0;
}
/* Inline brand logo. Replaces the textual h3 title. The SVG is
   proportional (viewBox 321.1×49.68) so height controls width.
   Sized to fit comfortably in the 56px header row on desktop and
   shrink slightly on mobile. */
.is-header-logo {
  display: block;
  height: 38px;
  width: auto;
  flex: 0 0 auto;
}
@media (max-width: 720px) {
  .is-header-logo { height: 30px; }
}
/* v76: meta line tucked inside the title row — signed in + jump link +
   sign out. Stays on the same line as the title on desktop, wraps below
   on mobile. */
.is-header-meta {
  display: inline-flex;
  align-items: center;
  gap: 12px;
  margin-left: auto;
  font-size: 12px;
  font-weight: 500;
  color: var(--studio-text-muted);
  letter-spacing: 0;
  text-transform: none;
}
.is-header-meta strong {
  color: var(--studio-text);
  font-weight: 700;
}
.is-header-jump {
  font-weight: 600;
  color: var(--studio-accent);
  text-decoration: none;
  border-bottom: 1px dashed transparent;
}
.is-header-jump:hover { border-bottom-color: var(--studio-accent); }
.is-header-logout {
  color: var(--studio-text-muted);
  text-decoration: none;
}
.is-header-logout:hover { color: var(--studio-accent); }

.is-header-actions {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 6px;
  flex: 1 1 auto;
  justify-content: flex-end;
}

.is-btn-ghost {
  border-color: var(--studio-border);
  background: transparent;
  color: var(--studio-text-muted);
  font-weight: 600;
}
.is-btn-ghost:hover {
  border-color: var(--studio-accent);
  color: var(--studio-accent);
  background: var(--studio-accent-soft);
}
.is-chat-history .is-caret {
  font-size: 10px;
  transition: transform .15s ease;
}
.is-chat-history[aria-expanded="true"] .is-caret {
  transform: rotate(180deg);
}

.is-chat-menu {
  position: absolute;
  top: 56px;
  right: 16px;
  z-index: 50;
  width: 320px;
  max-height: 360px;
  overflow-y: auto;
  padding: 6px;
  background: var(--studio-surface);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  box-shadow: 0 12px 32px rgba(15, 23, 42, .12);
}
.is-chat-menu[hidden] { display: none; }
.is-chat-menu-empty {
  padding: 16px;
  font-size: 12px;
  color: var(--studio-text-muted);
  text-align: center;
}
.is-chat-menu-item {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 8px 10px;
  border-radius: var(--studio-radius-sm);
  cursor: pointer;
  transition: background .12s ease;
}
.is-chat-menu-item:hover {
  background: var(--studio-surface-2);
}
.is-chat-menu-item-active {
  background: var(--studio-accent-soft);
  border-left: 3px solid var(--studio-accent);
  padding-left: 7px;
}
.is-chat-menu-item-body {
  flex: 1;
  min-width: 0;
}
.is-chat-menu-item-title {
  font-size: 13px;
  font-weight: 600;
  color: var(--studio-text);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.is-chat-menu-item-meta {
  font-size: 11px;
  color: var(--studio-text-muted);
  margin-top: 2px;
}
.is-chat-menu-item-del {
  flex: 0 0 auto;
  width: 24px;
  height: 24px;
  padding: 0;
  border: 0;
  border-radius: 4px;
  background: transparent;
  color: var(--studio-text-muted);
  font-size: 14px;
  cursor: pointer;
  opacity: 0;
  transition: all .12s ease;
}
.is-chat-menu-item:hover .is-chat-menu-item-del {
  opacity: 1;
}
.is-chat-menu-item-del:hover {
  background: var(--studio-error);
  color: #fff;
}

/* Position the header relatively so the absolute-positioned chat menu anchors correctly. */
.is-header { position: relative; }

/* Inline media inside assistant chat bubbles (persisted generations). */
.is-msg-caption {
  font-size: 13px;
  color: var(--studio-text);
}
.is-bubble-assistant img,
.is-bubble-assistant video {
  margin-top: 8px;
  max-width: 100%;
  max-height: 480px;
  border-radius: var(--studio-radius-sm);
  display: block;
}

.is-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  height: 32px;
  padding: 0 12px;
  border: 1px solid var(--studio-border-strong);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  color: var(--studio-text);
  font-size: 13px;
  font-weight: 500;
  cursor: pointer;
  transition: all .15s ease;
  text-decoration: none;
  white-space: nowrap;
}
.is-btn:hover { background: var(--studio-surface-2); border-color: var(--studio-text-muted); }
.is-btn:focus-visible { outline: 2px solid var(--studio-accent); outline-offset: 2px; }

.is-btn-primary {
  background: var(--studio-accent);
  border-color: var(--studio-accent);
  color: #fff;
}
.is-btn-primary:hover { background: #e07a00; border-color: #e07a00; }

/* Transient success/error states (used by Copy button feedback) */
.is-btn-success {
  background: rgba(34, 197, 94, 0.18) !important;
  border-color: rgba(34, 197, 94, 0.55) !important;
  color: #86efac !important;
}
.is-btn-error {
  background: rgba(239, 68, 68, 0.18) !important;
  border-color: rgba(239, 68, 68, 0.55) !important;
  color: #fca5a5 !important;
}

.is-btn-icon {
  width: 32px;
  padding: 0;
}

/* ---------- credits badge ---------- */
.is-credits {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 4px 10px;
  border-radius: 999px;
  background: #ecfdf5;
  border: 1px solid #bbf7d0;
  color: #047857;
  font-size: 12px;
  font-weight: 700;
}
.is-credits::before {
  content: '';
  width: 6px; height: 6px;
  border-radius: 50%;
  background: var(--studio-success);
}
.is-credits.is-error { background: #fef2f2; border-color: #fecaca; color: #b91c1c; }
.is-credits.is-error::before { background: var(--studio-error); }

/* ---------- help icon + tooltip (shared across the user area) ---------- */
/* A small "?" circle next to a label/button that, on hover or focus,
   reveals a popover with a short explanation of what the thing does.
   Usage:
     <label>Username <button type="button" class="is-help" data-help="..."
       aria-describedby="tip-username">?</button></label>
   The popover is rendered by JS on first hover/focus and positioned
   below/above the icon depending on available space. */
button.is-help,
.is-help,
.login-card .is-help,
.login-card button.is-help {
  /* Reset every default button styling inherited from page-scoped
     button rules. We use all: revert + high-specificity selectors
     so the help icon stays a small inline circle regardless of
     where it lives (login form, admin form, studio composer, etc.).
     The .login-card / .login-card button override below has higher
     specificity than the page-scoped .login-card button { width:100% }
     rule, which would otherwise win. */
  all: revert;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 16px;
  height: 16px;
  padding: 0;
  margin: 0 0 0 6px;
  border: 1px solid var(--studio-border-strong);
  border-radius: 50%;
  background: transparent;
  color: var(--studio-text-muted);
  font: 700 10px/1 -apple-system, system-ui, sans-serif;
  cursor: help;
  vertical-align: middle;
  flex: 0 0 auto;
  transition: all .12s ease;
  text-transform: none;
  letter-spacing: 0;
}
.is-help:hover,
.is-help:focus-visible,
.login-card .is-help:hover,
.login-card .is-help:focus-visible {
  color: var(--studio-accent);
  border-color: var(--studio-accent);
  outline: none;
  filter: none;
  background: transparent;
}
.is-help[aria-expanded="true"] {
  color: #fff;
  background: var(--studio-accent);
  border-color: var(--studio-accent);
}

/* Popover — created on demand by the JS, appended to <body> so it
   escapes any overflow:hidden container the trigger might be inside. */
.is-tooltip {
  position: absolute;
  z-index: 10000;
  max-width: 280px;
  padding: 10px 12px;
  border: 1px solid var(--studio-border-strong);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  color: var(--studio-text);
  font-size: 12px;
  line-height: 1.5;
  box-shadow: var(--studio-shadow-lg);
  pointer-events: auto;
}
.is-tooltip[hidden] { display: none; }
.is-tooltip::before {
  /* Arrow pointing up at the trigger. Positioned dynamically by JS. */
  content: '';
  position: absolute;
  top: -6px;
  left: 50%;
  transform: translateX(-50%) rotate(45deg);
  width: 10px;
  height: 10px;
  background: var(--studio-surface);
  border-top: 1px solid var(--studio-border-strong);
  border-left: 1px solid var(--studio-border-strong);
}
.is-tooltip.is-tooltip-above::before {
  top: auto;
  bottom: -6px;
  border-top: 0;
  border-left: 0;
  border-bottom: 1px solid var(--studio-border-strong);
  border-right: 1px solid var(--studio-border-strong);
}

/* Inline help icon — small "?" circle next to a label or button row.
   Sits inline with adjacent buttons; the margin-left pushes it past the
   last button in a flex row. */
.is-help.is-help-inline {
  margin-left: 2px;
  width: 16px;
  height: 16px;
}

/* ---------- body layout (stream + composer | gallery sidebar) ---------- */
/* v77: .is-body is itself a card. The page (`.inked-studio`) no longer
   carries a card chrome — each logical section (chat, gallery) is its
   own card with a 4px gradient left rail, matching the WOW Studio
   `.media-agent-card` style. The chat card has min-height set to
   the visible viewport minus the header + studio padding, so the
   chat always takes the full window and the gallery is always pushed
   below the fold (reached by scrolling). min-height:0 on flex children
   is preserved so .is-stream can scroll inside the card. */
.is-body {
  position: relative;
  display: flex;
  flex-direction: column;
  flex: 1 1 0;
  min-height: calc(100dvh - 110px);
  min-width: 0;
  overflow: hidden;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: linear-gradient(145deg, #ffffff 0%, #fff8ee 100%);
  box-shadow: var(--studio-shadow);
}
.is-body::before {
  position: absolute;
  inset: 0 auto 0 0;
  width: 4px;
  background: linear-gradient(180deg, var(--studio-accent) 0%, var(--studio-accent-2) 100%);
  content: "";
}
.is-main {
  display: flex;
  flex-direction: column;
  flex: 0 0 auto;
}
.is-composer {
  flex: 0 0 auto;
  background: var(--studio-surface);
  border-top: 1px solid var(--studio-border);
}
.is-main {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-direction: column;
  min-height: 0;
  /* v77: pin the stream at the top and the composer at the bottom of
     the chat card so the empty space sits between the welcome bubble
     (top) and the textarea/tools (bottom) instead of after them. */
  justify-content: space-between;
}

/* ---------- gallery sidebar (right column, "Your work") ---------- */
.is-gallery-sidebar {
  flex: 0 0 320px;
  display: flex;
  flex-direction: column;
  border-left: 1px solid var(--studio-border);
  background: var(--studio-surface);
  overflow: hidden;
}
.is-gallery-sidebar.is-gallery-empty {
  display: none;  /* hide the column entirely when there's nothing to show */
}
.is-gallery-head {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 12px 14px;
  border-bottom: 1px solid var(--studio-border);
  background: var(--studio-surface);
  flex: 0 0 auto;
}
.is-gallery-head h3 {
  margin: 0;
  font-size: 13px;
  font-weight: 700;
  color: var(--studio-text);
  letter-spacing: .02em;
  text-transform: uppercase;
  flex: 1;
  min-width: 0;
}
.is-gallery-head .count {
  font-size: 11px;
  color: var(--studio-text-muted);
}
.is-gallery-head .danger {
  font-size: 11px;
  padding: 4px 10px;
  background: rgba(239,68,68,.10);
  border: 1px solid rgba(239,68,68,.35);
  color: #b91c1c;
  border-radius: var(--studio-radius-sm);
  cursor: pointer;
  font-weight: 500;
}
.is-gallery-head .danger:hover { background: rgba(239,68,68,.20); }
.is-gallery-scroll {
  flex: 1;
  overflow-y: auto;
  padding: 12px;
}
.is-gallery-empty-msg {
  padding: 40px 14px;
  text-align: center;
  color: var(--studio-text-muted);
  font-size: 12px;
  line-height: 1.5;
}
.is-gallery-empty-msg strong {
  display: block;
  color: var(--studio-text);
  font-size: 13px;
  margin-bottom: 4px;
  font-weight: 600;
}
.is-gallery-group {
  margin-bottom: 16px;
}
.is-gallery-group:last-child { margin-bottom: 0; }
.is-gallery-group-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 8px;
  margin-bottom: 8px;
  padding-bottom: 6px;
  border-bottom: 1px dashed var(--studio-border);
  flex-wrap: wrap;
}
.is-gallery-group-title-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px;
  flex: 1 1 auto;
  min-width: 0;
}
.is-gallery-avatar {
  width: 24px;
  height: 24px;
  border-radius: 50%;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 11px;
  font-weight: 700;
  flex: 0 0 auto;
  color: #fff;
}
.is-gallery-chat-icon {
  background: transparent;
  border: 0;
  font-size: 14px;
  padding: 2px 4px;
  cursor: pointer;
  flex: 0 0 auto;
  border-radius: 4px;
  color: var(--studio-accent);
  transition: background .12s ease;
}
.is-gallery-chat-icon:hover {
  background: color-mix(in srgb, var(--studio-accent) 12%, transparent);
}
.is-gallery-group-actions {
  display: flex;
  align-items: center;
  gap: 6px;
  flex: 0 0 auto;
}
.is-gallery-group-head h4 {
  margin: 0;
  font-size: 12px;
  font-weight: 700;
  color: var(--studio-text);
  flex: 1;
  min-width: 0;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.is-gallery-group-head .meta {
  font-size: 10px;
  color: var(--studio-text-muted);
  letter-spacing: .04em;
  text-transform: uppercase;
  font-weight: 600;
}
.is-gallery-group-head button {
  background: transparent;
  border: 0;
  color: #b91c1c;
  font-size: 10px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .04em;
  cursor: pointer;
  padding: 4px 8px;
  border-radius: 6px;
}
.is-gallery-group-head button:hover { background: rgba(239,68,68,.10); }
.is-gallery-group-head button:disabled { opacity: .5; cursor: not-allowed; }
.is-gallery-group-head .is-gallery-delete-chat {
  flex: 0 0 auto;
}
.is-gallery-group-head .is-gallery-personality-chat {
  /* Sits between .meta and Delete on the group header. Lighter
     visual weight than Delete so it doesn't scream "destructive"
     when the user scans the sidebar. */
  flex: 0 0 auto;
  color: var(--studio-accent);
  background: transparent;
}
.is-gallery-group-head .is-gallery-personality-chat:hover {
  background: color-mix(in srgb, var(--studio-accent) 12%, transparent);
}
.is-gallery-group-head .is-gallery-personality-chat:disabled { opacity: .5; cursor: not-allowed; }
.is-gallery-group-title {
  /* The chat title — styled like a link, opens the chat in the studio.
     Width-bounded so a long name + counts + actions all fit on the
     narrow sidebar without ellipsis eating the model name. */
  flex: 0 1 auto;
  min-width: 0;
  max-width: 100%;
  margin: 0;
  padding: 4px 6px;
  background: transparent;
  border: 0;
  border-radius: 6px;
  color: var(--studio-text);
  font: inherit;
  font-size: 12px;
  font-weight: 700;
  text-align: left;
  text-transform: none;
  letter-spacing: 0;
  cursor: pointer;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  transition: background .12s ease, color .12s ease;
}
.is-gallery-group-subtitle {
  font-size: 10px;
  color: var(--studio-text-muted);
  font-weight: 500;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  flex: 0 1 auto;
  min-width: 0;
  max-width: 100%;
}
.is-gallery-group-title:hover {
  background: var(--studio-accent-soft);
  color: var(--studio-accent);
}
.is-gallery-group-title:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 2px;
}

.is-gallery-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 6px;
}
.is-gallery-thumb {
  position: relative;
  aspect-ratio: 1 / 1;
  border-radius: var(--studio-radius-sm);
  overflow: hidden;
  background: var(--studio-surface-2);
  border: 1px solid var(--studio-border);
  cursor: zoom-in;
  padding: 0;
}
.is-gallery-thumb:hover { border-color: var(--studio-accent); }

/* ---------- personality chat composer ---------- */
/* Replaces the image/video composer body when chat mode is on. The
   head shows a rotating avatar of the model + a name + an exit
   button. The textarea + Send button row mirrors the content
   composer so the rest of the studio code doesn't need to know
   which flavour it's looking at. */
.is-personality-head {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 10px;
  padding-bottom: 10px;
  border-bottom: 1px solid var(--studio-border);
}
.is-personality-avatar {
  width: 44px;
  height: 44px;
  border-radius: 50%;
  background: var(--studio-surface-2);
  border: 1px solid var(--studio-border);
  background-size: cover;
  background-position: center;
  flex: 0 0 auto;
  transition: opacity .3s ease;
}
.is-personality-meta {
  flex: 1;
  min-width: 0;
}
.is-personality-name {
  font-size: 14px;
  font-weight: 700;
  color: var(--studio-text);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.is-personality-sub {
  font-size: 12px;
  color: var(--studio-text-muted);
  margin-top: 2px;
  line-height: 1.45;
}
.is-personality-sub strong {
  color: var(--studio-text);
  font-weight: 600;
}
.is-personality-tip {
  display: inline;
}
/* Inline tip buttons inside the personality composer hint. They look
   like chips — clickable, accent-coloured, small — so the user can
   tap them to insert the example prompt and see what the image intent
   looks like. */
.is-tip-btn {
  background: color-mix(in srgb, var(--studio-accent) 10%, transparent);
  border: 1px solid color-mix(in srgb, var(--studio-accent) 30%, transparent);
  border-radius: 6px;
  color: var(--studio-accent);
  font: inherit;
  font-size: 11px;
  padding: 2px 7px;
  margin: 0 2px;
  cursor: pointer;
  white-space: nowrap;
  transition: background .12s ease, color .12s ease;
}
.is-tip-btn:hover {
  background: var(--studio-accent);
  color: #fff;
}
.is-tip-btn:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 1px;
}
.is-gallery-thumb video,
.is-gallery-thumb img {
  width: 100%; height: 100%;
  object-fit: cover;
  display: block;
}
.is-gallery-thumb.is-busy { opacity: .35; pointer-events: none; }

/* Play overlay — only shown on video thumbs so they read as "watch me"
   instead of just "this is a still frame". */
.is-gallery-play {
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(0,0,0,.25);
  color: rgba(255,255,255,.95);
  pointer-events: none;
  transition: background .12s ease;
}
.is-gallery-thumb:hover .is-gallery-play {
  background: rgba(0,0,0,.40);
}

/* ---------- lightbox (lives inside the sidebar) ---------- */
.is-lightbox {
  position: fixed;
  inset: 0;
  background: rgba(0,0,0,.85);
  display: none;
  align-items: center;
  justify-content: center;
  z-index: 100;
  padding: 32px;
}
.is-lightbox.is-lightbox-open { display: flex; }
.is-lightbox img, .is-lightbox video {
  max-width: 100%;
  max-height: 100%;
  border-radius: var(--studio-radius);
  box-shadow: 0 30px 60px rgba(0,0,0,.5);
}
.is-lightbox-figure {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 16px;
  margin: 0;
  max-width: 100%;
  max-height: 100%;
}
.is-lightbox-body {
  display: flex;
  align-items: center;
  justify-content: center;
  max-width: 100%;
  max-height: calc(100vh - 180px);
}
.is-lightbox-body img,
.is-lightbox-body video {
  max-height: calc(100vh - 180px);
}

/* When the gallery lightbox is open, hide the studio main area
   (chat stream + composer) so the operator sees only the image/video
   full screen — no chat history bleeding through below the
   lightbox. The sidebar stays visible so the operator can navigate
   to another chat without closing the lightbox first. */
body.is-gallery-lightbox-active .is-main { display: none; }
.is-lightbox-actions {
  display: flex;
  gap: 8px;
  align-items: center;
}
.is-lightbox-actions .is-btn {
  background: var(--studio-surface);
  color: var(--studio-text);
  border-color: var(--studio-border-strong);
}
.is-lightbox-actions .is-btn-primary {
  background: var(--studio-accent);
  color: #fff;
  border-color: var(--studio-accent);
}
.is-lightbox-actions .is-btn:hover {
  filter: brightness(1.05);
}
.is-lightbox-close {
  position: absolute;
  top: 16px;
  right: 16px;
  width: 40px;
  height: 40px;
  border: 0;
  border-radius: 999px;
  background: rgba(255,255,255,.18);
  color: #fff;
  font-size: 22px;
  cursor: pointer;
}
.is-lightbox-close:hover { background: rgba(255,255,255,.28); }

/* ---------- responsive: stack the sidebar below on small screens ---------- */
@media (max-width: 900px) {
  .is-body { flex-direction: column; }
  .is-gallery-sidebar {
    flex: 0 0 auto;
    border-left: 0;
    border-top: 1px solid var(--studio-border);
    max-height: 280px;
  }
}

/* ---------- stream ---------- */
.is-stream {
  /* v77: stream is now the flex item that grows. It fills the space
     between the welcome bubble (top, no flex grow) and the composer
     (bottom, no flex grow), and scrolls internally when chat content
     exceeds the card height. min-height:0 is required so the flex
     child can actually shrink below its content size and let the
     scrollbar appear instead of clipping bubbles at the card edge. */
  flex: 1 1 0;
  min-height: 0;
  overflow-y: auto;
  padding: 20px 20px 24px;
  display: flex;
  flex-direction: column;
  gap: 16px;
  background: var(--studio-bg);
  scroll-behavior: smooth;
}
.is-stream::-webkit-scrollbar { width: 10px; }
.is-stream::-webkit-scrollbar-track { background: transparent; }
.is-stream::-webkit-scrollbar-thumb {
  background: rgba(255,139,0,.35);
  border-radius: 999px;
  border: 2px solid transparent;
  background-clip: padding-box;
}
.is-stream::-webkit-scrollbar-thumb:hover { background: rgba(255,139,0,.60); background-clip: padding-box; }

.is-bubble {
  max-width: 85%;
  padding: 12px 16px;
  border-radius: var(--studio-radius);
  font-size: 14px;
  white-space: pre-wrap;
  overflow-wrap: anywhere;
  animation: is-bubble-in .25s ease-out;
}
.is-bubble-user {
  align-self: flex-end;
  background: var(--studio-accent);
  color: #fff;
  border-bottom-right-radius: 4px;
}

.is-bubble-assistant {
  align-self: flex-start;
  background: var(--studio-surface);
  border: 1px solid var(--studio-border);
  border-bottom-left-radius: 4px;
  padding: 12px 16px;
  max-width: min(880px, 88%);
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.is-bubble-assistant:has(.is-plan) {
  /* Let the bubble stretch to contain the plan card full-width */
  max-width: 100%;
}
.is-bubble-assistant > .is-plan {
  margin: 0;
}
/* Chips inside a bubble span the bubble's width instead of being capped at
   92% (the outer-stream rule is for the empty-state at the stream root). */
.is-bubble-assistant .is-suggestions {
  max-width: 100%;
  padding: 0;
}

/* Inline name-input row that appears inside the step-3 bubble when the
   user picks "Type your own". Sits below the chips and matches the
   existing input styling. */
.is-name-input {
  display: flex;
  gap: 8px;
  margin-top: 4px;
}
.is-name-input .is-input {
  flex: 1;
  height: 34px;
  padding: 0 10px;
  border: 1px solid var(--studio-border-strong);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  color: var(--studio-text);
  font: inherit;
  font-size: 13px;
}
.is-name-input .is-input:focus {
  outline: 2px solid var(--studio-accent);
  outline-offset: 1px;
  border-color: var(--studio-accent);
}
.is-name-input .is-btn {
  flex: 0 0 auto;
  height: 34px;
  padding: 0 14px;
}

/* Selected chip state for attribute picks. Filled accent + white text so the
   user can see at a glance which attribute they chose. */
.is-chip.is-chip-selected {
  background: var(--studio-accent);
  color: #fff;
  border-color: var(--studio-accent);
}
.is-chip.is-chip-selected:hover {
  background: #e07a00;
  border-color: #e07a00;
}

/* Attribute form: a labelled row of chips per attribute, with the Continue
   button at the bottom. Sits inside an assistant bubble (column flex). */
.is-attr-form {
  display: flex;
  flex-direction: column;
  gap: 12px;
  margin-top: 4px;
}
.is-attr-row {
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.is-attr-label {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--studio-text-muted);
}
.is-attr-form .is-suggestions {
  max-width: 100%;
  padding: 0;
}
.is-attr-continue {
  align-self: flex-start;
  margin-top: 4px;
}
/* The "Type your own" chip is an action, not a value pick — render it
   dashed so it reads as different from the value chips around it. */
.is-chip.is-chip-custom {
  border-style: dashed;
  color: var(--studio-text);
}
.is-chip.is-chip-custom.is-chip-selected {
  /* If the user has entered a custom value we still mark it selected so
     the user gets visual feedback that their custom name is "picked". */
  border-style: solid;
}
/* Inline name-input row that appears inside the basics form when the
   user picks "Type your own". Sits below the chips in the same row. */
.is-name-input {
  display: flex;
  gap: 8px;
  margin-top: 6px;
}
.is-name-input .is-input {
  flex: 1;
  height: 34px;
  padding: 0 10px;
  border: 1px solid var(--studio-border-strong);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  color: var(--studio-text);
  font: inherit;
  font-size: 13px;
}
.is-name-input .is-input:focus {
  outline: 2px solid var(--studio-accent);
  outline-offset: 1px;
  border-color: var(--studio-accent);
}
.is-name-input .is-btn {
  flex: 0 0 auto;
  height: 34px;
  padding: 0 14px;
}

@keyframes is-bubble-in {
  from { opacity: 0; transform: translateY(4px); }
  to   { opacity: 1; transform: translateY(0); }
}

/* v82: loading bubble — three pulsing dots + a status phrase so the user
   sees the assistant is mid-turn (slow upstream / image-gen). Sits in the
   same stream as the other assistant bubbles and is removed when the
   real response arrives. */
.is-loading-bubble {
  display: inline-flex;
  align-items: center;
  gap: 12px;
  padding: 2px 0;
}
.is-loading-text {
  font-size: 13px;
  color: var(--studio-text-muted);
  font-weight: 500;
}
.is-loading-dots {
  display: inline-flex;
  align-items: center;
  gap: 4px;
}
.is-loading-dots span {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--studio-accent);
  opacity: .35;
  animation: is-loading-dot 1.2s ease-in-out infinite;
}
.is-loading-dots span:nth-child(2) { animation-delay: .15s; }
.is-loading-dots span:nth-child(3) { animation-delay: .30s; }
@keyframes is-loading-dot {
  0%, 80%, 100% { opacity: .35; transform: scale(1); }
  40%           { opacity: 1;   transform: scale(1.15); }
}

/* v96: pending-job bubble — pinned in the stream while a generation
   request is in flight. Visually distinct from the welcome bubble
   (orange left rail, dashed top border) so the user can find it
   when they come back from chatting elsewhere. Replaced in-place
   by the result card when the fetch resolves. */
.is-card-assistant.is-card-pending-job,
.is-bubble-assistant.is-pending-job-bubble {
  border-left: 3px solid var(--studio-accent);
  background: linear-gradient(180deg, #fff8ee 0%, #fff5e6 100%);
  border-style: dashed;
}
.is-card-pending-job .is-card-pending-job-icon {
  display: inline-block;
  width: 14px;
  height: 14px;
  border-radius: 50%;
  border: 2px solid var(--studio-accent);
  border-top-color: transparent;
  animation: is-pending-job-spin .8s linear infinite;
  vertical-align: middle;
  margin-right: 8px;
}
@keyframes is-pending-job-spin {
  to { transform: rotate(360deg); }
}

/* ---------- empty-state suggestion chips ---------- */
.is-suggestions {
  align-self: flex-start;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  padding: 0 4px 4px;
  max-width: 92%;
}
.is-chip {
  display: inline-flex;
  align-items: center;
  height: 30px;
  padding: 0 14px;
  border: 1px solid var(--studio-accent);
  border-radius: 999px;
  background: var(--studio-surface);
  color: var(--studio-accent);
  font-size: 12px;
  font-weight: 600;
  cursor: pointer;
  transition: all .15s ease;
  white-space: nowrap;
}
.is-chip:hover {
  background: var(--studio-accent);
  color: #fff;
  border-color: var(--studio-accent);
}
.is-chip:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 2px;
}
/* In-flight state for chips that trigger an async action (Improve, image
   generation, etc.). The chip becomes a spinner so the user sees
   something happening instead of wondering if their click registered. */
.is-chip:disabled,
.is-chip.is-chip-busy {
  cursor: progress;
  position: relative;
  color: var(--studio-accent);
  background: var(--studio-accent-soft);
  border-color: var(--studio-accent);
  opacity: .8;
}
.is-chip.is-chip-busy::after {
  content: '';
  position: absolute;
  inset: 0;
  margin: auto;
  width: 12px;
  height: 12px;
  border: 2px solid var(--studio-accent);
  border-top-color: transparent;
  border-radius: 999px;
  animation: is-chip-spin .7s linear infinite;
}
@keyframes is-chip-spin { to { transform: rotate(360deg); } }
.is-chip-primary {
  background: var(--studio-accent);
  color: #fff;
  border-color: var(--studio-accent);
}
.is-chip-primary:hover {
  background: #e07a00;
  border-color: #e07a00;
}

/* ---------- empty-state welcome ---------- */
.is-empty-sub {
  font-size: 12px;
  color: var(--studio-text-muted);
  line-height: 1.5;
  margin-top: 6px;
}

/* ---------- draft plan card (preset-loaded or in-progress plan) ---------- */
.is-draft-header {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 0 4px 8px;
  font-size: 12px;
  color: var(--studio-text-muted);
}
.is-draft-header strong {
  color: var(--studio-text);
  font-weight: 700;
}
.is-draft-pill {
  display: inline-flex;
  align-items: center;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--studio-accent-soft);
  color: var(--studio-accent);
}
.is-plan-draft {
  margin-top: 0;
}

/* ---------- slash menu (floats above the composer) ---------- */
.is-slash-menu {
  position: fixed;
  z-index: 1080;
  max-height: min(22rem, 55vh);
  overflow-y: auto;
  padding: 6px;
  border: 1px solid rgba(13, 110, 253, .35);
  border-radius: 12px;
  background: #fff;
  box-shadow: 0 .75rem 2rem rgba(15, 23, 42, .18);
  font-family: inherit;
}
.is-slash-menu.d-none { display: none !important; }
.is-slash-group {
  padding: 6px 10px 2px;
  color: #64748b;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
}
.is-slash-option {
  display: grid;
  grid-template-columns: minmax(7rem, auto) 1fr;
  gap: 12px;
  width: 100%;
  padding: 8px 10px;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: #263246;
  text-align: left;
  font: inherit;
  font-size: 13px;
  cursor: pointer;
}
.is-slash-option:hover,
.is-slash-option.is-selected {
  background: rgba(255, 139, 0, .12);
}
.is-slash-option code {
  color: var(--studio-accent);
  font-weight: 700;
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12px;
  white-space: nowrap;
}
.is-slash-option span {
  color: #64748b;
  font-size: 12px;
}

/* ---------- /help inline card ---------- */
.is-help-card {
  align-self: stretch;
  margin: 0 4px;
  padding: 14px 16px;
  border: 1px solid #f5e2c5;
  border-radius: 12px;
  background: linear-gradient(145deg, rgba(255, 139, 0, .08), #fff 70%);
  font-size: 13px;
  box-shadow: 0 4px 14px rgba(15, 23, 42, .05);
}
.is-help-card-header {
  margin-bottom: 10px;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--studio-accent);
}
.is-help-card-body {
  display: grid;
  gap: 12px;
}
.is-help-group {
  display: grid;
  gap: 4px;
}
.is-help-group-title {
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: #64748b;
}
.is-help-cmd {
  display: grid;
  grid-template-columns: minmax(8rem, auto) 1fr;
  gap: 12px;
  padding: 3px 0;
  line-height: 1.4;
}
.is-help-cmd code {
  color: var(--studio-accent);
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12px;
  font-weight: 600;
}
.is-help-cmd span {
  color: #475569;
  font-size: 12px;
}

/* ---------- floating status pill (above composer) ---------- */
.is-status-floating {
  display: none;
  margin: 0 0 8px;
  padding: 8px 12px;
  border-radius: 8px;
  background: var(--studio-surface-2);
  border: 1px solid var(--studio-border);
  color: var(--studio-text);
  font-size: 12px;
  font-weight: 500;
  line-height: 1.4;
}
.is-status-floating.is-visible {
  display: block;
  animation: is-bubble-in .2s ease-out;
}

/* ---------- plan card (assistant response with prompt + settings) ---------- */
.is-plan {
  align-self: stretch;
  margin-top: 12px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: var(--studio-surface);
  overflow: hidden;
  /* Nested inside assistant bubble — keep visual weight light, no shadow */
  box-shadow: none;
}


.is-plan-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px 16px;
  background: linear-gradient(135deg, var(--studio-accent-soft), var(--studio-accent-2-soft));
  border-bottom: 1px solid var(--studio-border);
}
.is-plan-header h4 {
  margin: 0;
  font-size: 13px;
  font-weight: 700;
  color: var(--studio-text);
  letter-spacing: -.005em;
}
.is-plan-header .badge {
  font-size: 10px;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--studio-accent-soft);
  color: var(--studio-accent);
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
}

.is-plan-body { padding: 14px 16px; }

.is-prompt-text {
  font-size: 14px;
  line-height: 1.55;
  color: var(--studio-text);
  white-space: pre-wrap;
  overflow-wrap: anywhere;
  margin: 0 0 12px;
  padding: 12px;
  background: var(--studio-surface-2);
  border-radius: var(--studio-radius-sm);
  border: 1px dashed var(--studio-border);
}

.is-pills {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  margin-bottom: 14px;
}
.is-pill {
  font-size: 11px;
  font-weight: 600;
  padding: 4px 10px;
  border-radius: 999px;
  background: var(--studio-accent-soft);
  color: var(--studio-accent);
  letter-spacing: .02em;
}

.is-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-top: 14px;
}

/* ---------- status ---------- */
.is-status {
  align-self: flex-start;
  max-width: 85%;
  padding: 8px 14px;
  border-radius: 999px;
  background: var(--studio-surface-2);
  font-size: 12px;
  color: var(--studio-text-muted);
}
.is-status:empty { display: none; }

/* ---------- attachments ---------- */
.is-attachments {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  align-self: flex-end;
  max-width: 85%;
}
.is-attachment {
  position: relative;
  width: 80px; height: 80px;
  border-radius: var(--studio-radius-sm);
  overflow: hidden;
  background: var(--studio-text);
  border: 1px solid var(--studio-border);
}
.is-attachment img, .is-attachment video {
  width: 100%; height: 100%;
  object-fit: cover;
  display: block;
}
.is-attachment-remove {
  position: absolute;
  top: 4px; right: 4px;
  width: 22px; height: 22px;
  border: 0;
  border-radius: 50%;
  background: rgba(0,0,0,.7);
  color: #fff;
  cursor: pointer;
  font-size: 14px;
  line-height: 1;
}

/* ---------- composer ---------- */
.is-composer {
  flex: 0 0 auto;
  padding: 14px 16px;
  border-top: 1px solid var(--studio-border);
  background: var(--studio-surface);
}

/* ---------- AI-picked pill (primary surface for settings) ---------- */
.is-pick {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  width: 100%;
  padding: 8px 12px;
  margin-bottom: 10px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface-2);
  color: var(--studio-text);
  font: inherit;
  font-size: 12px;
  font-weight: 600;
  text-align: left;
  cursor: pointer;
  transition: all .15s ease;
}
.is-pick:hover {
  border-color: var(--studio-accent);
  background: var(--studio-accent-soft);
}
.is-pick:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 2px;
}
.is-pick-label {
  flex: 1;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.is-pick-caret {
  font-size: 11px;
  color: var(--studio-text-muted);
  transition: transform .15s ease;
}
.is-pick[aria-expanded="true"] .is-pick-caret {
  transform: rotate(180deg);
}

.is-composer-settings[hidden] { display: none; }

.is-composer-settings {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(110px, 1fr));
  gap: 8px;
  margin-bottom: 10px;
  align-items: end;
}
.is-composer-field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  min-width: 0;
}
.is-composer-field[hidden] { display: none; }
.is-composer-field > span {
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--studio-text-muted);
}
.is-composer-settings .is-pill-cost {
  align-self: end;
  justify-self: end;
}

.is-input-wrap {
  position: relative;
  border: 1px solid var(--studio-border-strong);
  border-radius: var(--studio-radius);
  background: var(--studio-surface);
  transition: border-color .15s ease, box-shadow .15s ease;
}
.is-input-wrap:focus-within {
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 3px rgba(255, 139, 0, .18);
}

.is-textarea {
  width: 100%;
  /* v76: fixed height per port/resolution. No auto-grow, no manual
     resize — keeps the composer compact and consistent everywhere. */
  height: 84px;
  min-height: 84px;
  max-height: 84px;
  padding: 12px 90px 12px 14px;
  border: 0;
  background: transparent;
  color: var(--studio-text);
  font: inherit;
  font-size: 14px;
  line-height: 1.5;
  resize: none;
  outline: 0;
}
.is-textarea::placeholder { color: var(--studio-text-soft); }

.is-composer-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-top: 10px;
  gap: 8px;
}

.is-composer-tools {
  display: flex;
  align-items: center;
  gap: 6px;
}

.is-send {
  min-width: 90px;
}

/* ---------- spinner ---------- */
.is-spinner {
  display: inline-block;
  width: 14px; height: 14px;
  border: 2px solid rgba(255,255,255,.3);
  border-top-color: #fff;
  border-radius: 50%;
  animation: is-spin .8s linear infinite;
}
.is-btn-primary .is-spinner { display: none; }
.is-btn-primary.is-loading .is-spinner { display: inline-block; }
.is-btn-primary.is-loading .is-label { display: none; }

@keyframes is-spin { to { transform: rotate(360deg); } }

/* ---------- result media ---------- */
.is-result {
  align-self: stretch;
  padding: 14px 16px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: var(--studio-surface);
}
.is-result img, .is-result video {
  display: block;
  width: 100%;
  max-width: 100%;
  border-radius: var(--studio-radius-sm);
  background: var(--studio-text);
}

/* ---------- responsive ---------- */
@media (max-width: 720px) {
  /* Header: title on its own row, meta + actions wrap below. */
  .is-header { padding: 10px 12px; gap: 8px; }
  .is-header-title { flex-wrap: wrap; row-gap: 6px; }
  .is-header-meta { margin-left: 0; width: 100%; justify-content: flex-start; flex-wrap: wrap; }
  .is-header-actions { width: 100%; justify-content: flex-start; }
  .is-header-actions .is-btn { padding: 6px 10px; font-size: 13px; }
  .is-header-actions .is-credits {
    flex: 1 1 auto;
    text-align: right;
  }
  .is-stream { padding: 12px; }
  .is-bubble { max-width: 92%; }
  .is-textarea { height: 80px; min-height: 80px; max-height: 80px; font-size: 15px; }
  .is-composer-row { flex-direction: column; align-items: stretch; }
  .is-send { width: 100%; }
  .is-plan-settings { grid-template-columns: 1fr; }
  .is-composer-settings { grid-template-columns: 1fr 1fr; }
  /* Composer: tighten padding on mobile. */
  .is-composer { padding: 10px 12px; }
  .is-composer-tools .is-btn { padding: 6px 10px; font-size: 13px; }
  /* Plan card chips wrap nicely on small screens. */
  .is-card-chips { gap: 6px; }
  .is-card-chips .is-chip { padding: 6px 10px; font-size: 12px; }
}

/* ---------- editable prompt inside plan card ---------- */
.is-prompt-edit {
  display: block;
  width: 100%;
  margin: 0 0 12px;
  padding: 10px 12px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface-2);
  color: var(--studio-text);
  font: inherit;
  font-size: 13px;
  line-height: 1.5;
  resize: vertical;
  min-height: 80px;
}
.is-prompt-edit:focus {
  outline: none;
  border-color: var(--studio-accent);
  background: var(--studio-surface);
  box-shadow: 0 0 0 3px rgba(255, 139, 0, .15);
}

/* ---------- settings grid inside plan card ---------- */
.is-plan-settings {
  display: grid;
  grid-template-columns: 1.4fr 1fr 1fr auto;
  gap: 10px;
  align-items: end;
  margin-bottom: 12px;
}
.is-plan-field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  min-width: 0;
}
.is-plan-field > span {
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--studio-text-muted);
}
.is-select {
  width: 100%;
  padding: 6px 8px;
  border: 1px solid var(--studio-border-strong);
  border-radius: 6px;
  background: var(--studio-surface);
  color: var(--studio-text);
  font: inherit;
  font-size: 13px;
}
.is-select:focus {
  outline: none;
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 3px rgba(255, 139, 0, .15);
}
.is-pill-cost {
  align-self: end;
  background: #fef3c7;
  color: #92400e;
  font-weight: 700;
}

/* ---------- result media (post-generation) ---------- */
.is-result {
  position: relative;
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 12px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: var(--studio-surface);
}
.is-result-meta {
  font-size: 11px;
  font-weight: 600;
  color: var(--studio-text-muted);
}
.is-result img,
.is-result video {
  display: block;
  width: 100%;
  max-width: 100%;
  max-height: 520px;
  border-radius: var(--studio-radius-sm);
  background: var(--studio-text);
  cursor: zoom-in;
  object-fit: contain;
}

/* ---------- video job placeholder (while polling) ---------- */
.is-result-job {
  min-height: 80px;
}
.is-job-status {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 14px;
  border: 1px dashed var(--studio-border-strong);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface-2);
  color: var(--studio-text);
  font-size: 13px;
  font-weight: 500;
}
.is-job-status .is-spinner {
  border-color: rgba(255, 139, 0, .3);
  border-top-color: var(--studio-accent);
}

/* ---------- reduced motion ---------- */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    transition-duration: 0.01ms !important;
  }
}

/* v76: removed the v71 .is-plan-card* and v72 .is-plan-bubble--{prompt,settings}
   blocks — both rendered via the dead _renderPlanCardElement() (removed in v76)
   or via the no-longer-applied .is-plan-bubble--* class selectors. Plan-bubbles
   now use the .is-card stack built in _renderAssistantCard. The .is-bubble
   styles just above remain for the welcome bubble. */


/* ---------- v72: full-width layout (no sidebar) ---------- */
/* The legacy v71 layout reserved the right ~280px for the gallery sidebar.
   v72 collapses the sidebar entirely and stretches the chat to full width,
   with a thin gallery strip below the composer (rendered conditionally). */
.is-body { width: 100%; max-width: none; }
.is-main { width: 100%; max-width: none; }

/* ---------- v72: bottom gallery strip ---------- */
/* v77: gallery is an INDEPENDENT card below the chat card. Its own
   border + radius + shadow, with the same gradient left-rail as the
   chat card. Padding is internal — the `.inked-studio` flex gap
   handles the gap between the two cards. */
.is-gallery-bottom {
  position: relative;
  width: 100%;
  padding: 22px 18px 28px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: linear-gradient(145deg, #ffffff 0%, #fff8ee 100%);
  box-shadow: var(--studio-shadow);
  overflow: hidden;
}
.is-gallery-bottom::before {
  position: absolute;
  inset: 0 auto 0 0;
  width: 4px;
  background: linear-gradient(180deg, var(--studio-accent) 0%, var(--studio-accent-2) 100%);
  content: "";
}
.is-gallery-heading {
  margin: 0 0 6px;
  font-size: 16px;
  font-weight: 800;
  letter-spacing: -.01em;
  color: var(--studio-text);
}
.is-gallery-help {
  margin: 0 0 14px;
  font-size: 13px;
  color: var(--studio-text-muted);
}
.is-gallery-help strong { color: var(--studio-accent); font-weight: 700; }
.is-gallery-list {
  display: grid;
  /* v91: bumped min so the 4:5 thumb + footer buttons fit comfortably.
      Each card is at least 220px wide on desktop, 160px on mobile. */
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 16px;
}
@media (max-width: 720px) {
  .is-gallery-list {
    grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
    gap: 10px;
  }
}
.is-gallery-bottom[hidden] { display: none; }
.is-gallery-card {
  width: 100%;
  min-width: 0;
  padding: 5px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  cursor: pointer;
  transition: border-color .15s, transform .05s;
  font: inherit;
  color: inherit;
  text-align: left;
}
.is-gallery-card:hover {
  border-color: var(--studio-accent);
  transform: translateY(-1px);
}
.is-gallery-label {
  font-size: 13px;
  font-weight: 600;
  color: var(--studio-text);
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.is-gallery-meta {
  font-size: 12px;
  color: var(--studio-text-muted);
  margin-top: 3px;
}
/* v76: asset gallery cards (per-asset thumbnails, NOT chat sessions).
   Reuses .is-gallery-card shell but adds a thumb slot + footer actions.
   v91: thumbs bumped to 4:5 aspect ratio so they feel less cramped.
   Animate + Custom Animate now live in the card footer (not on the
   thumb overlay) so they get proper sizing and the thumb stays clean. */
.is-gallery-asset {
  padding: 8px 8px 10px;
  text-align: left;
  font: inherit;
  color: inherit;
  position: relative;
  display: flex;
  flex-direction: column;
}
.is-gallery-asset-thumb {
  position: relative;
  width: 100%;
  aspect-ratio: 4 / 5;
  border-radius: var(--studio-radius-sm);
  overflow: hidden;
  background: #0f172a;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-bottom: 6px;
  cursor: zoom-in;
}
.is-gallery-asset-thumb img,
.is-gallery-asset-thumb video {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
/* v91: animate buttons moved out of the thumb overlay into the card
   footer. Two clearly differentiated buttons: primary (orange, solid)
   for the 1-click Animate, custom (gradient + sparkle) for the
   planner-routed Custom Animate. Both span the full card width so the
   user can't miss them. */
.is-gallery-asset-actions {
  display: flex;
  flex-direction: column;
  gap: 6px;
  margin-top: 8px;
}
.is-gallery-asset-action {
  font: inherit;
  font-size: 13px;
  font-weight: 600;
  padding: 8px 12px;
  border-radius: 10px;
  border: 0;
  cursor: pointer;
  white-space: nowrap;
  text-align: center;
  transition: transform .08s ease, box-shadow .12s ease, filter .12s ease;
  box-shadow: 0 1px 0 rgba(255,255,255,.4) inset, 0 1px 2px rgba(0,0,0,.06);
}
.is-gallery-asset-action:active { transform: translateY(1px); }
.is-gallery-asset-action:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 2px;
}
.is-gallery-asset-action--primary {
  background: linear-gradient(180deg, #ff9d3a, var(--studio-accent));
  color: #fff;
  text-shadow: 0 1px 0 rgba(0,0,0,.15);
}
.is-gallery-asset-action--primary:hover {
  filter: brightness(1.06);
  box-shadow: 0 0 0 3px var(--studio-accent-soft), 0 1px 2px rgba(0,0,0,.08);
}
.is-gallery-asset-action--custom {
  background: linear-gradient(135deg, #2c1810 0%, #4a2c1a 50%, #6b3a1f 100%);
  color: #ffd9b3;
  border: 1px solid rgba(255, 217, 179, .25);
  position: relative;
  overflow: hidden;
}
.is-gallery-asset-action--custom::before {
  content: '';
  position: absolute;
  inset: 0;
  background: linear-gradient(135deg, rgba(255,255,255,.08) 0%, transparent 50%, rgba(255,217,179,.06) 100%);
  pointer-events: none;
}
.is-gallery-asset-action--custom:hover {
  background: linear-gradient(135deg, #3a2014 0%, #5d3622 50%, #82482a 100%);
  border-color: rgba(255, 217, 179, .4);
}
.is-gallery-asset-action--custom span {
  position: relative;
  z-index: 1;
}
.is-gallery-asset-placeholder {
  font-size: 28px;
  opacity: 0.5;
  color: #fff;
}

/* ---------- v74: full-width stacked cards (WOW Studio style) ---------- */
/* Replaces the v73 bubble layout. Every message is a card that spans the
   stream width, with an eyebrow label ("You" / "Assistant") at the top. */

.is-card {
  width: 100%;
  flex-shrink: 0;
  margin: 0 0 14px;
  padding: 0;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  background: var(--studio-surface);
  box-shadow: 0 1px 2px rgba(0,0,0,.04);
  overflow: hidden;
}
.is-card-eyebrow {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 8px 14px;
  background: var(--studio-surface-2);
  border-bottom: 1px solid var(--studio-border);
  font-size: 11px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--studio-text-muted);
  font-weight: 700;
}
.is-card-eyebrow-kicker {
  display: inline-flex;
  align-items: center;
  height: 18px;
  padding: 0 8px;
  border-radius: 999px;
  background: var(--studio-accent-soft);
  color: var(--studio-accent);
  letter-spacing: .06em;
}
.is-card-body {
  padding: 12px 14px;
  font-size: 14px;
  line-height: 1.55;
  color: var(--studio-text);
  overflow-wrap: anywhere;
  white-space: pre-wrap;
}
.is-card-body.is-card-body-user {
  background: linear-gradient(180deg, var(--studio-surface), var(--studio-surface-2));
}
.is-card-assistant--prompt {
  border-left: 3px solid var(--studio-accent);
}
.is-card-assistant--prompt .is-card-body {
  font-style: italic;
  position: relative;
  padding-left: 26px;
}
.is-card-assistant--prompt .is-card-body::before {
  content: '✎';
  position: absolute;
  left: 12px;
  top: 12px;
  font-style: normal;
  opacity: .6;
}
.is-card-assistant--settings {
  background: var(--studio-surface-2);
}
.is-card-media {
  padding: 10px 14px 14px;
  position: relative;
}
.is-card-media img,
.is-card-media video {
  display: block;
  width: 100%;
  max-height: 480px;
  object-fit: contain;
  border-radius: var(--studio-radius-sm);
  background: #0f172a;
  cursor: zoom-in;
}
/* v97: header render-queue indicator. Small 🎬 chip with count that
   appears between the Chat button and the credits when 1+ videos are
   in flight. Pulses orange while rendering, flips green briefly when
   a video just resolved. Click jumps to the latest pending bubble. */
.is-header-rendering {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 12px;
  border: 1px solid var(--studio-border);
  border-radius: 999px;
  background: var(--studio-surface-2, rgba(255, 255, 255, 0.04));
  color: var(--studio-text);
  font-size: 12px;
  font-weight: 600;
  line-height: 1;
  cursor: pointer;
  transition: background-color .2s ease, border-color .2s ease, color .2s ease;
  position: relative;
}
.is-header-rendering[hidden] { display: none !important; }
.is-header-rendering-icon {
  font-size: 14px;
  line-height: 1;
}
.is-header-rendering-count {
  font-variant-numeric: tabular-nums;
  min-width: 14px;
  text-align: center;
}
.is-header-rendering--pulse {
  border-color: rgba(255, 139, 0, 0.55);
  color: var(--studio-accent, #ff8b00);
  background: rgba(255, 139, 0, 0.10);
  animation: is-header-rendering-pulse 1.4s ease-in-out infinite;
}
.is-header-rendering--pulse .is-header-rendering-icon {
  animation: is-header-rendering-spin 2s linear infinite;
  display: inline-block;
}
.is-header-rendering--ready {
  border-color: rgba(34, 197, 94, 0.55);
  color: #16a34a;
  background: rgba(34, 197, 94, 0.10);
}
@keyframes is-header-rendering-pulse {
  0%, 100% { box-shadow: 0 0 0 0 rgba(255, 139, 0, 0.35); }
  50%      { box-shadow: 0 0 0 6px rgba(255, 139, 0, 0.0); }
}
@keyframes is-header-rendering-spin {
  from { transform: rotate(0deg); }
  to   { transform: rotate(360deg); }
}
/* v97: brief highlight on a bubble when the user clicks the header
   indicator. Helps them spot which one the indicator was tracking
   when there's a long stream. */
.is-card-flash {
  animation: is-card-flash 1.4s ease-out;
}
@keyframes is-card-flash {
  0%   { box-shadow: 0 0 0 0 rgba(255, 139, 0, 0.65); }
  60%  { box-shadow: 0 0 0 8px rgba(255, 139, 0, 0.0); }
  100% { box-shadow: 0 0 0 0 rgba(255, 139, 0, 0.0); }
}

/* v97: ready-modal — pops when a video finishes while the user is in
   chat (so they don't miss it). Reuses the modal styling pattern from
   the history + save modals but with a thumbnail strip on top. */
.is-ready-modal {
  position: fixed;
  inset: 0;
  z-index: 1100;
}
.is-ready-modal[hidden] { display: none !important; }
.is-ready-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(8, 12, 22, 0.62);
  backdrop-filter: blur(3px);
  -webkit-backdrop-filter: blur(3px);
}
.is-ready-panel {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  width: min(420px, 92vw);
  background: var(--studio-surface, #1a1d2a);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-lg, 14px);
  padding: 22px 22px 18px;
  box-shadow: 0 24px 60px rgba(0, 0, 0, 0.55);
  animation: is-ready-panel-in 240ms cubic-bezier(.2,.7,.3,1) both;
}
@keyframes is-ready-panel-in {
  from { transform: translate(-50%, -46%); opacity: 0; }
  to   { transform: translate(-50%, -50%); opacity: 1; }
}
.is-ready-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 8px;
}
.is-ready-title {
  margin: 0;
  font-size: 18px;
  font-weight: 700;
  color: var(--studio-text);
}
.is-ready-help {
  margin: 0 0 14px;
  font-size: 13px;
  color: var(--studio-text-muted);
  line-height: 1.5;
}
.is-ready-thumb {
  background: #0f172a;
  border-radius: var(--studio-radius-sm, 8px);
  overflow: hidden;
  aspect-ratio: 16 / 9;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-bottom: 16px;
}
.is-ready-thumb-video {
  width: 100%;
  height: 100%;
  object-fit: contain;
  display: block;
}
.is-ready-actions {
  display: flex;
  gap: 10px;
  justify-content: flex-end;
}

/* v97: play-button overlay on top of inline videos. Always visible so
   the user has a single obvious way to open the video fullscreen even
   when the inline player is broken (black box, codec issue, autoplay
   blocked). Sits above the video but is small enough that the native
   play/pause controls underneath are still reachable. */
.is-card-media-video {
  cursor: pointer;
}
.is-card-media-play {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 10px 16px;
  border: none;
  border-radius: 999px;
  background: rgba(15, 23, 42, 0.78);
  color: #fff;
  font: 600 13px/1 var(--studio-font, inherit);
  letter-spacing: .01em;
  cursor: pointer;
  backdrop-filter: blur(4px);
  -webkit-backdrop-filter: blur(4px);
  transition: transform .15s ease, background-color .15s ease;
  z-index: 2;
  pointer-events: auto;
}
.is-card-media-play:hover,
.is-card-media-play:focus-visible {
  background: rgba(255, 139, 0, 0.92);
  transform: translate(-50%, -50%) scale(1.04);
  outline: none;
}
.is-card-media-play-icon {
  font-size: 16px;
  line-height: 1;
}
.is-card-media-play-label {
  white-space: nowrap;
}
.is-card-chips {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  padding: 0 14px 14px;
}

/* History modal */
.is-history-modal {
  position: fixed;
  inset: 0;
  z-index: 1000;
  display: flex;
  align-items: stretch;
  justify-content: flex-end;
}
.is-history-modal[hidden] { display: none; }
.is-history-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(15, 23, 42, .45);
  backdrop-filter: blur(2px);
}
.is-history-panel {
  position: relative;
  width: min(520px, 92vw);
  background: var(--studio-surface, #fff);
  display: flex;
  flex-direction: column;
  box-shadow: -8px 0 24px rgba(15,23,42,.18);
}
.is-history-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 18px;
  border-bottom: 1px solid var(--studio-border);
}
.is-history-title {
  margin: 0;
  font-size: 16px;
  font-weight: 700;
}
.is-history-help {
  margin: 0;
  padding: 12px 18px;
  font-size: 12px;
  color: var(--studio-text-muted);
  border-bottom: 1px solid var(--studio-border);
}
.is-history-list {
  flex: 1;
  overflow-y: auto;
  padding: 8px 12px 16px;
}
.is-history-empty {
  padding: 24px 16px;
  font-size: 13px;
  color: var(--studio-text-muted);
  text-align: center;
}
.is-history-error { color: #b91c1c; }
.is-history-row {
  display: block;
  width: 100%;
  text-align: left;
  padding: 12px 14px;
  margin-bottom: 6px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  cursor: pointer;
  transition: border-color .15s, background .15s;
}
.is-history-row:hover {
  border-color: var(--studio-accent);
  background: var(--studio-surface-2);
}
.is-history-row-text {
  font-size: 14px;
  color: var(--studio-text);
  line-height: 1.4;
  overflow-wrap: anywhere;
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
  overflow: hidden;
  margin-bottom: 4px;
}
.is-history-row-meta {
  font-size: 11px;
  color: var(--studio-text-muted);
  letter-spacing: .02em;
}

/* Save Chat modal — title prompt + preview, similar slide-in from right */
.is-save-modal {
  position: fixed;
  inset: 0;
  z-index: 1100;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 24px;
}
.is-save-modal[hidden] { display: none; }
.is-save-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(15, 23, 42, .55);
  backdrop-filter: blur(2px);
}
.is-save-panel {
  position: relative;
  width: min(440px, 100%);
  max-height: calc(100vh - 48px);
  background: var(--studio-surface);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-lg, 14px);
  box-shadow: 0 18px 48px rgba(15,23,42,.30);
  padding: 22px 22px 18px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.is-save-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 4px;
}
.is-save-title {
  margin: 0;
  font-size: 17px;
  font-weight: 700;
  color: var(--studio-text);
}
.is-save-help {
  margin: 0;
  font-size: 13px;
  line-height: 1.5;
  color: var(--studio-text-muted);
}
.is-save-label {
  font-size: 12px;
  font-weight: 600;
  color: var(--studio-text-muted);
  letter-spacing: .04em;
  text-transform: uppercase;
}
.is-save-name {
  font: inherit;
  font-size: 15px;
  padding: 10px 12px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm, 8px);
  background: var(--studio-surface);
  color: var(--studio-text);
  outline: none;
  transition: border-color .15s, box-shadow .15s;
}
.is-save-name:focus {
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 3px rgba(255, 139, 0, .15);
}
.is-save-preview {
  margin: 0;
  font-size: 12px;
  color: var(--studio-text-muted);
  background: var(--studio-surface-2);
  border-radius: var(--studio-radius-sm, 8px);
  padding: 8px 10px;
}
.is-save-actions {
  display: flex;
  justify-content: flex-end;
  gap: 8px;
  margin-top: 4px;
}

/* Saved chats modal — list of saved chats, click to load */
.is-saved-modal {
  position: fixed;
  inset: 0;
  z-index: 1100;
  display: flex;
  align-items: stretch;
  justify-content: flex-end;
}
.is-saved-modal[hidden] { display: none; }
.is-saved-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(15, 23, 42, .45);
  backdrop-filter: blur(2px);
}
.is-saved-panel {
  position: relative;
  width: min(440px, 100%);
  max-height: 100vh;
  background: var(--studio-surface);
  border-left: 1px solid var(--studio-border);
  box-shadow: -10px 0 30px rgba(15,23,42,.18);
  padding: 22px 22px 22px;
  display: flex;
  flex-direction: column;
  gap: 12px;
  overflow-y: auto;
}
.is-saved-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
}
.is-saved-title {
  margin: 0;
  font-size: 17px;
  font-weight: 700;
}
.is-saved-help {
  margin: 0;
  font-size: 13px;
  line-height: 1.5;
  color: var(--studio-text-muted);
}
.is-saved-list {
  display: flex;
  flex-direction: column;
  gap: 8px;
  margin-top: 4px;
}
.is-saved-empty {
  padding: 20px;
  text-align: center;
  font-size: 13px;
  color: var(--studio-text-muted);
  border: 1px dashed var(--studio-border);
  border-radius: var(--studio-radius-sm);
}
.is-saved-error { color: #b91c1c; border-color: rgba(185,28,28,.3); }
.is-saved-row {
  display: block;
  width: 100%;
  text-align: left;
  font: inherit;
  color: inherit;
  padding: 12px 14px;
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  background: var(--studio-surface);
  cursor: pointer;
  transition: border-color .15s, background .15s;
}
.is-saved-row:hover {
  border-color: var(--studio-accent);
  background: var(--studio-surface-2);
}
.is-saved-row-title {
  font-size: 14px;
  font-weight: 600;
  color: var(--studio-text);
  line-height: 1.4;
  overflow-wrap: anywhere;
  margin-bottom: 4px;
}
.is-saved-row-meta {
  font-size: 11px;
  color: var(--studio-text-muted);
}

/* ---------- Lightbox modal (asset full-size viewer) ---------- */
.is-lightbox {
  position: fixed;
  inset: 0;
  z-index: 1200;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 24px;
}
.is-lightbox[hidden] { display: none; }
.is-lightbox-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(15, 23, 42, .82);
  backdrop-filter: blur(4px);
  cursor: zoom-out;
}
.is-lightbox-panel {
  position: relative;
  max-width: min(1100px, 100%);
  max-height: 100%;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 8px;
}
/* Anchor for the absolutely-positioned close button. */
.is-lightbox-close {
  position: absolute;
  top: -10px;
  right: -10px;
  width: 36px;
  height: 36px;
  border-radius: 50%;
  background: rgba(255,255,255,.95);
  border: 0;
  font-size: 18px;
  font-weight: 600;
  cursor: pointer;
  box-shadow: 0 4px 12px rgba(0,0,0,.30);
  color: #0f172a;
  z-index: 5;
}
.is-lightbox-media {
  max-width: 100%;
  max-height: calc(100vh - 130px);
  border-radius: var(--studio-radius);
  box-shadow: 0 24px 64px rgba(0,0,0,.40);
  background: #0f172a;
  display: block;
}
.is-lightbox-media.is-video { background: #000; }
.is-lightbox-meta {
  font-size: 13px;
  color: rgba(255,255,255,.85);
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
  justify-content: center;
}
.is-lightbox-meta strong { color: #fff; font-weight: 600; }
.is-lightbox-animate {
  font: inherit;
  font-size: 13px;
  font-weight: 600;
  padding: 6px 12px;
  border-radius: 999px;
  background: var(--studio-accent);
  color: #fff;
  border: 0;
  cursor: pointer;
}
.is-lightbox-animate:disabled { opacity: .5; cursor: wait; }
.is-lightbox-close {
  position: absolute;
  top: -8px;
  right: -8px;
  width: 36px;
  height: 36px;
  border-radius: 50%;
  background: rgba(255,255,255,.95);
  border: 0;
  font-size: 18px;
  font-weight: 600;
  cursor: pointer;
  box-shadow: 0 4px 12px rgba(0,0,0,.30);
  color: #0f172a;
  z-index: 2;
}
.is-lightbox-close:hover { background: #fff; }

/* ====================================================================== */
/* v78 — model-creation onboarding + per-model gallery                     */
/* ====================================================================== */

/* Welcome bubble heading + sub-text. The heading is the v78 framing ("Welcome
   to InkedStudio2."), larger than the old `.is-empty-sub` helper. */
.is-welcome-bubble {
  padding: 22px 24px 18px;
}
.is-welcome-heading {
  font-size: 18px;
  font-weight: 700;
  color: var(--studio-text);
  letter-spacing: -.01em;
  margin-bottom: 6px;
}
.is-welcome-sub {
  font-size: 13px;
  color: var(--studio-text-muted);
  line-height: 1.55;
  margin-bottom: 14px;
}
.is-welcome-hint {
  font-size: 12px;
  font-style: italic;
  color: var(--studio-text-muted);
  opacity: .8;
  margin-top: 6px;
  line-height: 1.4;
}

/* v80: chat-style onboarding composer — single multiline textarea,
   no chips. The submit button sits below the textarea. */
.is-onboarding-row {
  display: flex;
  gap: 8px;
  align-items: stretch;
}
.is-onboarding-row--solo {
  /* Textarea + Send button share the same row with bottom alignment.
     The Send button sits at the bottom-right of the textarea so it
     stays visually anchored to the user's typing. */
  display: flex;
  align-items: flex-end;
  gap: 8px;
}
.is-onboarding-textarea {
  flex: 1 1 auto;
  width: 100%;
  min-height: 80px;
  resize: vertical;
  font: inherit;
  font-size: 14px;
  line-height: 1.5;
  padding: 10px 12px;
  background: var(--studio-surface-2);
  color: var(--studio-text);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius-sm);
  outline: none;
  transition: border-color .15s ease, box-shadow .15s ease;
  font-family: inherit;
}
.is-onboarding-textarea:focus {
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 3px var(--studio-accent-soft);
}

/* Onboarding Send button — sits at the bottom-right of the textarea row
   (align-items: flex-end on .is-onboarding-row--solo). */
.is-btn.is-onboarding-submit {
  flex: 0 0 auto;
  padding: 0 18px;
  height: auto;
  display: inline-flex;
  align-items: center;
  gap: 6px;
}

/* Sex chips (Male / Female). Larger than the standard suggestion chips so
   they read as the primary choice on the welcome screen. */
.is-chip.is-chip-sex {
  font-size: 14px;
  font-weight: 600;
  padding: 9px 18px;
  border-radius: 999px;
  background: linear-gradient(135deg, var(--studio-accent), var(--studio-accent-2));
  color: #fff;
  border: 0;
  cursor: pointer;
  transition: filter .15s ease, transform .12s ease;
}
.is-chip.is-chip-sex:hover {
  filter: brightness(1.06);
  transform: translateY(-1px);
}
.is-chip.is-chip-sex:disabled {
  opacity: .6;
  cursor: wait;
  transform: none;
}

/* Onboarding composer — chip row + free-text input. Replaces the regular
   textarea while onboarding is active. */
.is-composer-onboarding {
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 16px 18px 14px;
}
.is-composer-onboarding[hidden] { display: none; }

/* Dead legacy selectors from the chip-based onboarding — no longer in the
   DOM but kept here as a safety net so they never accidentally render. */
.is-onboarding-chips,
.is-onboarding-input { display: none !important; }

.is-onboarding-status {
  margin: 0;
  font-size: 12px;
  color: var(--studio-text-muted);
  min-height: 16px;
}

/* Assistant card carrying an onboarding question — slightly tinted so it
   reads as part of the guided flow, not a free-form reply. */
.is-card-assistant.is-card-onboarding-question {
  border-color: var(--studio-accent-2);
  background: linear-gradient(180deg, var(--studio-surface), var(--studio-accent-2-soft));
}
.is-card-assistant.is-card-onboarding-question .is-card-body {
  font-weight: 500;
}
/* User card carrying an onboarding pick — visually subdued, just enough
   chrome to confirm the answer landed. */
.is-card-user.is-card-onboarding-answer .is-card-body-user {
  background: var(--studio-accent-soft);
  border: 1px solid var(--studio-accent);
  font-size: 14px;
}

/* Plan-bubbles carry kind='plan-bubble' for the splice matcher. They render
   identically to a regular assistant card — the chips + variant class
   carry the visual weight. The class is a hook for future styling. */
.is-card-assistant.is-card-plan-bubble { /* no extra visual rules yet */ }

/* Regular composer (hidden during onboarding). */
.is-composer-normal[hidden] { display: none; }

/* Per-model gallery modal. Mirrors the lightbox/saved-modal layout. */
.is-model-gallery-modal {
  position: fixed;
  inset: 0;
  z-index: 1100;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 24px;
}
.is-model-gallery-modal[hidden] { display: none; }
.is-model-gallery-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(15, 23, 42, .62);
  backdrop-filter: blur(3px);
}
.is-model-gallery-panel {
  position: relative;
  z-index: 1;
  width: 100%;
  max-width: 980px;
  max-height: 86vh;
  background: var(--studio-surface);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  box-shadow: var(--studio-shadow-lg);
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
.is-model-gallery-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 18px 22px 12px;
  border-bottom: 1px solid var(--studio-border);
}
.is-model-gallery-title {
  margin: 0;
  font-size: 18px;
  font-weight: 700;
  color: var(--studio-text);
  letter-spacing: -.01em;
}
.is-model-gallery-help {
  margin: 0;
  padding: 10px 22px 14px;
  font-size: 12px;
  color: var(--studio-text-muted);
  border-bottom: 1px solid var(--studio-border);
}
.is-model-gallery-grid {
  flex: 1 1 auto;
  overflow-y: auto;
  padding: 18px 22px 22px;
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(170px, 1fr));
  gap: 12px;
}

/* "See all →" button at the tail of the gallery strip. */
.is-gallery-more {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font: inherit;
  font-size: 13px;
  font-weight: 600;
  padding: 10px 18px;
  border-radius: var(--studio-radius-sm);
  background: transparent;
  color: var(--studio-accent);
  border: 1px dashed var(--studio-accent);
  cursor: pointer;
  transition: background .15s ease, color .15s ease, border-color .15s ease;
}
.is-gallery-more:hover {
  background: var(--studio-accent-soft);
  border-style: solid;
}

/* Gallery empty state (shown until the first generation lands). */
.is-gallery-empty {
  padding: 28px 16px;
  text-align: center;
  font-size: 13px;
  color: var(--studio-text-muted);
  grid-column: 1 / -1;
}

/* ============================================================== */
/* v79: model-card index. Replaces the per-model asset strip — the  */
/* gallery section now shows one card per model (latest thumb + name */
/* + asset count). Active model is highlighted; clicking switches.   */
/* ============================================================== */
.is-models-list {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
  gap: 16px;
}
@media (max-width: 720px) {
  .is-models-list {
    grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
    gap: 12px;
  }
}

.is-model-card {
  display: flex;
  flex-direction: column;
  align-items: stretch;
  text-align: left;
  font: inherit;
  padding: 0;
  background: var(--studio-surface);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius);
  box-shadow: var(--studio-shadow-sm);
  overflow: hidden;
  cursor: pointer;
  transition: transform .12s ease, box-shadow .12s ease, border-color .12s ease;
}
.is-model-card:hover {
  transform: translateY(-2px);
  box-shadow: var(--studio-shadow-md);
  border-color: var(--studio-accent-2);
}
.is-model-card:focus-visible {
  outline: none;
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 3px var(--studio-accent-soft);
}
.is-model-card--active {
  border-color: var(--studio-accent);
  box-shadow: 0 0 0 1px var(--studio-accent), var(--studio-shadow-md);
}
.is-model-card--active::before {
  content: '';
  display: block;
  height: 3px;
  background: linear-gradient(90deg, var(--studio-accent), var(--studio-accent-2));
}

.is-model-card-thumb {
  position: relative;
  width: 100%;
  aspect-ratio: 1 / 1;
  background: linear-gradient(145deg, var(--studio-surface-2), var(--studio-accent-soft));
  overflow: hidden;
  display: flex;
  align-items: center;
  justify-content: center;
}
.is-model-card-thumb img,
.is-model-card-thumb video {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
.is-model-card-kind {
  position: absolute;
  top: 6px;
  right: 6px;
  width: 22px;
  height: 22px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 999px;
  background: rgba(15, 23, 42, .55);
  color: #fff;
  font-size: 12px;
  line-height: 1;
}

.is-model-card-placeholder {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 6px;
  color: var(--studio-text-muted);
  font-size: 12px;
}
.is-model-card-placeholder-sym {
  font-size: 32px;
  line-height: 1;
  opacity: .55;
}
.is-model-card-placeholder-hint { opacity: .65; }

.is-model-card-meta {
  display: flex;
  flex-direction: column;
  gap: 6px;
  padding: 10px 12px 12px;
}
.is-model-card-name {
  font-size: 14px;
  font-weight: 700;
  color: var(--studio-text);
  letter-spacing: -.005em;
  line-height: 1.2;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.is-model-card-sub {
  display: flex;
  align-items: center;
  gap: 6px;
  font-size: 12px;
  color: var(--studio-text-muted);
}
.is-model-card-sex {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 18px;
  height: 18px;
  border-radius: 999px;
  font-size: 11px;
  line-height: 1;
}
.is-model-card-sex-male {
  background: rgba(8, 145, 178, .12);
  color: #0891b2;
}
.is-model-card-sex-female {
  background: rgba(255, 139, 0, .14);
  color: #c2410c;
}
.is-model-card-sex-other {
  background: var(--studio-accent-2-soft);
  color: var(--studio-accent-2);
}
.is-model-card-count {
  font-variant-numeric: tabular-nums;
}
.is-model-card-viewing {
  margin-left: auto;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .04em;
  text-transform: uppercase;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--studio-accent);
  color: #fff;
}

/* v79: delete buttons (gallery + model cards, lightbox). Hidden until
   hover/focus so the gallery stays clean. */
.is-gallery-asset-delete,
.is-model-card-delete {
  position: absolute;
  top: 6px;
  left: 6px;
  width: 22px;
  height: 22px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 999px;
  background: rgba(15, 23, 42, .65);
  color: #fff;
  border: 0;
  cursor: pointer;
  font-size: 13px;
  line-height: 1;
  opacity: 0;
  transition: opacity .12s ease, background .12s ease, transform .12s ease;
}
.is-gallery-asset-delete:hover,
.is-model-card-delete:hover {
  background: var(--studio-error, #dc2626);
  transform: scale(1.1);
}
.is-gallery-card:hover .is-gallery-asset-delete,
.is-gallery-card:focus-within .is-gallery-asset-delete,
.is-model-card:hover .is-model-card-delete,
.is-model-card:focus-within .is-model-card-delete {
  opacity: 1;
}

/* v86: per-model chat button on the gallery card. Sits at the bottom-right
   of the thumbnail so it doesn't fight the kind badge (top-right) or the
   delete × (top-left). Always visible — chat is a primary action. */
.is-model-card-chat {
  position: absolute;
  bottom: 6px;
  right: 6px;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 4px 10px;
  border-radius: 999px;
  background: rgba(15, 23, 42, .75);
  color: #fff;
  border: 0;
  cursor: pointer;
  font: inherit;
  font-size: 12px;
  font-weight: 600;
  line-height: 1.2;
  white-space: nowrap;
  transition: background .12s ease, transform .12s ease;
}
.is-model-card-chat:hover {
  background: var(--studio-accent);
  transform: translateY(-1px);
}
.is-model-card-chat:focus-visible {
  outline: 2px solid var(--studio-accent);
  outline-offset: 2px;
}

/* Lightbox delete — always visible in the meta row. */
.is-lightbox-delete {
  font: inherit;
  font-size: 13px;
  font-weight: 600;
  padding: 6px 14px;
  border-radius: 999px;
  background: transparent;
  color: var(--studio-error, #dc2626);
  border: 1px solid var(--studio-error, #dc2626);
  cursor: pointer;
  transition: background .12s ease, color .12s ease;
}
.is-lightbox-delete:hover {
  background: var(--studio-error, #dc2626);
  color: #fff;
}

/* ============================================================== */
/* v86 — companion chat: layout shell, side panel, chat-message UX */
/* ============================================================== */

/* The body main axis flips to row when the chat side panel is open.
   Default (no chat) stays column so stream + composer stack as before. */
.is-body .is-main {
  /* default: column flex — unchanged from v77 */
  flex-direction: column;
}
.is-chat-col {
  /* When the side panel is hidden, this is the only child of .is-main
     and gets the full width. Holds the existing flex-column layout
     (stream on top, composer at bottom) so chat mode feels like the
     studio we already know. */
  display: flex;
  flex-direction: column;
  flex: 1 1 auto;
  min-width: 0;
  min-height: 0;
  justify-content: space-between;
}

/* The side panel — sits as a horizontal header strip above the chat
   stream when chat mode is open. Replaces the v86 left-sidebar design:
   takes less vertical space and gives the conversation the full row
   width. Hidden by default via the [hidden] attribute on the <aside>. */
.is-chat-sidepanel {
  width: 100%;
  flex: 0 0 auto;
  display: flex;
  flex-direction: row;
  align-items: center;
  gap: 14px;
  padding: 10px 14px;
  border-right: 0;
  border-bottom: 1px solid var(--studio-border);
  background: linear-gradient(180deg, #fff5ec 0%, #ffe7d4 100%);
  overflow: hidden;
  /* Slide-in animation when entering chat mode. Cheap transform — no
     layout cost. The exit animation is implicit (hidden hides the
     panel instantly which matches the rest of the modal logic). */
  animation: is-chat-sidepanel-in 220ms cubic-bezier(.2,.7,.3,1) both;
}
.is-chat-sidepanel[hidden] {
  display: none !important;
}
@keyframes is-chat-sidepanel-in {
  from { transform: translateY(-6px); opacity: 0; }
  to   { transform: translateY(0); opacity: 1; }
}

.is-chat-sidepanel-portrait {
  width: 48px;
  height: 48px;
  border-radius: 50%;
  overflow: hidden;
  background: #fff;
  box-shadow: 0 2px 6px rgba(0,0,0,0.08);
  display: flex;
  align-items: center;
  justify-content: center;
  position: relative;
  flex-shrink: 0;
}
.is-chat-sidepanel-portrait img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
.is-chat-sidepanel-avatar-fallback {
  font: 700 20px/1 'Avenir Next', Avenir, sans-serif;
  color: var(--studio-accent, #ff8b00);
  background: linear-gradient(145deg, #fff 0%, #fff8ee 100%);
  width: 100%;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
}
.is-chat-sidepanel-name {
  font-weight: 700;
  font-size: 15px;
  color: #2a1410;
  text-align: left;
  margin: 0;
  white-space: nowrap;
  flex-shrink: 0;
}
.is-chat-sidepanel-nick {
  font-size: 12px;
  color: #a35c00;
  background: rgba(255, 200, 130, 0.35);
  padding: 2px 10px;
  border-radius: 999px;
  flex-shrink: 0;
}
.is-chat-sidepanel-nick[hidden] { display: none; }
.is-chat-sidepanel-meta {
  font-size: 12px;
  color: #6b4a3a;
  text-align: left;
  line-height: 1.4;
  margin: 0;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  flex: 1 1 auto;
  min-width: 0;
}
.is-chat-sidepanel-actions {
  margin-top: 0;
  margin-left: auto;
  width: auto;
  display: flex;
  flex-direction: row;
  gap: 6px;
  flex-shrink: 0;
}
.is-chat-sidepanel-exit {
  width: auto;
  white-space: nowrap;
}

/* Welcome / welcome-back bubble at the top of the chat thread. */
.is-chat-welcome-bubble {
  align-self: flex-start;
  max-width: 80%;
  background: linear-gradient(145deg, #fff5ec 0%, #ffe7d4 100%);
  border: 1px solid var(--studio-border);
  border-radius: var(--studio-radius, 14px);
  padding: 14px 18px;
  box-shadow: 0 2px 8px rgba(255, 139, 0, 0.06);
}
.is-chat-welcome-bubble--returning {
  background: linear-gradient(145deg, #fff 0%, #fff8ee 100%);
  border-color: rgba(255, 139, 0, 0.3);
}
.is-chat-welcome-heading {
  font-weight: 700;
  font-size: 15px;
  margin-bottom: 6px;
  color: #2a1410;
}
.is-chat-welcome-sub {
  font-size: 13px;
  color: #6b4a3a;
  line-height: 1.5;
}

/* Chat-message styling — slightly tighter bubbles than the onboarding
   flow to keep the thread scannable. Both user and assistant cards
   get this class via _render{User,Assistant}Card. */
.is-card-chat-message {
  max-width: 84%;
}
.is-card-chat-message .is-card-body {
  font-size: 14px;
  line-height: 1.55;
}
.is-card-chat-message .is-card-media img,
.is-card-chat-message .is-card-media video {
  max-height: 320px;
  width: auto;
  border-radius: 12px;
  cursor: pointer;
}

/* Compliance refusal — distinct background + accent so the user can
   see at a glance that this wasn't the model being difficult, it was
   the safety gate rejecting the prompt. */
.is-card-compliance-refusal {
  background: linear-gradient(145deg, #fff0ec 0%, #ffe1d8 100%);
  border: 1px solid rgba(220, 80, 50, 0.25);
}
.is-card-compliance-refusal .is-card-body {
  color: #6e1a0a;
}

/* Redirect → "Open in Studio" button area. */
.is-card-actions {
  margin-top: 10px;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}
.is-chat-redirect-open {
  background: linear-gradient(180deg, var(--studio-accent, #ff8b00) 0%, #f57a00 100%);
  color: #fff;
  border: 0;
  font-weight: 700;
  padding: 8px 16px;
  border-radius: 999px;
  cursor: pointer;
  box-shadow: 0 2px 8px rgba(255, 139, 0, 0.35);
  transition: transform 120ms ease, box-shadow 120ms ease;
}
.is-chat-redirect-open:hover {
  transform: translateY(-1px);
  box-shadow: 0 4px 14px rgba(255, 139, 0, 0.5);
}
.is-chat-redirect-open:active {
  transform: translateY(0);
  box-shadow: 0 1px 4px rgba(255, 139, 0, 0.4);
}

/* v87 — name-conflict chips + suggestion row.
   Primary conflict decision (Use X / Pick new name) is bolder than the
   secondary suggestions so the user sees the primary choice first.
   The whole block sits inside an .is-card-onboarding-question bubble so
   it inherits the soft yellow/orange palette already on that variant. */
.is-chip-conflict {
  font-weight: 700;
  padding: 8px 14px;
  border-radius: 999px;
  background: linear-gradient(180deg, #ff9a3c 0%, #ff7a00 100%);
  color: #fff;
  border: 0;
  box-shadow: 0 2px 6px rgba(255, 122, 0, 0.3);
  cursor: pointer;
  transition: transform 120ms ease, box-shadow 120ms ease;
}
.is-chip-conflict:hover {
  transform: translateY(-1px);
  box-shadow: 0 4px 12px rgba(255, 122, 0, 0.45);
}
.is-chip-conflict:disabled {
  opacity: 0.5;
  cursor: default;
  transform: none;
  box-shadow: none;
}
.is-chip-conflict-suggest {
  font-weight: 600;
  padding: 6px 12px;
  border-radius: 999px;
  background: #fff;
  color: #6b3a00;
  border: 1px dashed rgba(255, 139, 0, 0.55);
  cursor: pointer;
  transition: background 120ms ease, border-color 120ms ease;
}
.is-chip-conflict-suggest:hover {
  background: #fff8ee;
  border-color: var(--studio-accent, #ff8b00);
  border-style: solid;
}
.is-card-name-suggestions {
  margin-top: 10px;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 6px;
}
.is-card-name-suggestions-label {
  font-size: 12px;
  color: #a35c00;
  font-weight: 600;
  letter-spacing: 0.02em;
}
.is-card-name-suggestions .is-card-chips {
  gap: 6px;
}
