/* Brand accent: logo violet as the link color (overriding Material's default
   indigo); red is the hover/active accent. Bootstrap keeps its own violet
   further down so the two families stay distinct. */
[data-md-color-primary="white"] {
  --ixm-accent: #3f0da8;
  --ixm-accent-ink: #fff;
  --ixm-accent-tint: #e9e3f7;
  --bootstrap-accent: #712cf9;
  --bootstrap-accent-tint: #f1ebfe;
  --md-typeset-a-color: var(--ixm-accent);
  --md-accent-fg-color: #e0001f;
  --md-accent-fg-color--transparent: #e000191a;
}

[data-md-color-primary="white"][data-md-color-scheme="slate"] {
  --ixm-accent: #b9a7e6;
  --ixm-accent-ink: #1e2129;
  --ixm-accent-tint: #241a45;
  --bootstrap-accent: #a67cff;
  --bootstrap-accent-tint: #2b1c57;
  --md-typeset-a-color: var(--ixm-accent);
  --md-accent-fg-color: #ff5c6f;
  --md-accent-fg-color--transparent: #ff5c6f1a;
}

/* Every h1 is serif at full ink (Material's default is dimmed sans) —
   H2-H6 stay sans. Georgia is a system face, no webfont needed. */
:root {
  --ixm-font-serif: georgia, "Times New Roman", serif;
}

.md-typeset h1 {
  color: var(--md-default-fg-color);
  font-family: var(--ixm-font-serif);
  /* Georgia ships no 300 weight, so Material's light h1 would synthesize. */
  font-weight: 400;
}

/* Keep the site title in the header visible on scroll instead of Material's
   default crossfade to the current page title. */
.md-header__title--active .md-header__topic {
  z-index: 1;
  transform: translateX(0);
  pointer-events: auto;
  opacity: 1;
}

.md-header__title--active .md-header__topic + .md-header__topic {
  pointer-events: none;
  opacity: 0;
}

/* Homepage hero: large serif display heading, matching Canvas Builder's
   docs homepage treatment (Material's default h1 is small and muted). */
.md-typeset .ixm-hero h1 {
  margin-bottom: 0.625rem;
  letter-spacing: -0.01em;
  color: var(--md-typeset-color);
  font-family: var(--ixm-font-serif);
  font-size: 4.25rem;
  font-weight: 400;
  line-height: 1.05;
}

/* At narrow widths 4.25rem breaks "IXM"/"Blocks" mid-word instead of at the
   space — same defect and fix as bootstrap_components' docs homepage. */
@media screen and (max-width: 44.9375em) {
  .md-typeset .ixm-hero h1 {
    font-size: 2.75rem;
  }
}

/* Material's .md-button has no margin at this width, so the two hero
   buttons nearly touched. Same fix/value as Canvas Builder's .cb-hero. */
.md-typeset .ixm-hero .md-button {
  margin: 1.5rem 0.5rem 0 0;
}

/* Material's hover/focus points every .md-button at --md-accent-fg-color
   (our red) — wrong for the primary CTA, which should stay purple. */
.md-typeset .md-button--primary:hover,
.md-typeset .md-button--primary:focus {
  color: var(--ixm-accent-ink);
  border-color: var(--ixm-accent);
  background-color: var(--ixm-accent);
}

/* Outlined red, filling solid on hover — both pass WCAG AA (~5:1) in light
   and dark. Uses --ixm-accent-ink for hover text; --md-primary-bg-color
   resolves near-black here and made it unreadable. */
.md-typeset .md-button--danger {
  color: var(--md-accent-fg-color);
  border-color: var(--md-accent-fg-color);
}

.md-typeset .md-button--danger:hover,
.md-typeset .md-button--danger:focus {
  color: var(--ixm-accent-ink);
  border-color: var(--md-accent-fg-color);
  background-color: var(--md-accent-fg-color);
}

.md-typeset .ixm-cards-4 {
  grid-template-columns: repeat(4, 1fr);
}

@media screen and (max-width: 76.25em) {
  .md-typeset .ixm-cards-4 {
    grid-template-columns: repeat(2, 1fr);
  }
}

@media screen and (max-width: 44.9375em) {
  .md-typeset .ixm-cards-4 {
    grid-template-columns: 1fr;
  }
}

/* Components page: section headers with a badged icon, and card art with a
   tinted backdrop behind each component's custom icon graphic. */
.md-typeset .component-section-title {
  display: flex;
  align-items: center;
  gap: 0.6rem;
}

.md-typeset .component-section-title .twemoji {
  --md-icon-size: 1.5rem;

  box-sizing: content-box;
  padding: 0.4rem;
  color: var(--ixm-accent);
  border-radius: 0.5rem;
  background: var(--ixm-accent-tint);
}

.md-typeset .component-section-subtitle {
  margin-top: -0.6rem;
  color: var(--md-default-fg-color--light);
}

/* Prop/slot/variant reference tables: full width, and the name column never
   wraps (`with_controls`, `content_alignment`) while the description does. */
.md-typeset .component-reference-table .md-typeset__scrollwrap,
.md-typeset .component-reference-table .md-typeset__table {
  display: block;
}

.md-typeset .component-reference-table table {
  width: 100%;
}

.md-typeset .component-reference-table th:first-child,
.md-typeset .component-reference-table td:first-child {
  white-space: nowrap;
}

/* Token map diagram: an abstract two-column schematic of the Split layout —
   the layout with the richest token surface — tagging each region with the
   CSS custom property that controls it. Not to scale, not real component
   markup; a legend, not a pixel-accurate render (the live demo above already
   covers that). */
.md-typeset .token-diagram {
  margin: 1.5rem 0;
}

.md-typeset .token-diagram__frame {
  display: flex;
  flex-wrap: wrap;
  overflow: hidden;
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.75rem;
  background: var(--md-default-bg-color);
}

.md-typeset .token-diagram__content {
  display: flex;
  flex: 1 1 16rem;
  flex-direction: column;
  align-items: flex-start;
  gap: 0.5rem;
  padding: 1.25rem;
}

.md-typeset .token-diagram__media {
  display: flex;
  flex: 1 1 12rem;
  align-items: center;
  justify-content: center;
  min-height: 9rem;
  padding: 1rem;
  text-align: center;
  background: repeating-linear-gradient(135deg, var(--md-default-fg-color--lightest) 0 10px, transparent 10px 20px);
}

.md-typeset .token-diagram__line {
  width: 95%;
  height: 0.55rem;
  border-radius: 0.2rem;
  background: var(--md-default-fg-color--lightest);
}

.md-typeset .token-diagram__line--title {
  width: 80%;
  height: 0.9rem;
}

.md-typeset .token-diagram__cta {
  padding: 0.35rem 0.75rem;
  border: 1px solid var(--md-default-fg-color--light);
  border-radius: 0.375rem;
  font-size: 0.8rem;
}

.md-typeset .token-diagram__tag {
  display: inline-flex;
  align-items: center;
  gap: 0.25rem;
  color: var(--ixm-accent);
  font-size: 0.75rem;
}

.md-typeset .token-diagram__tag--push {
  margin-top: auto;
  padding-top: 0.5rem;
}

.md-typeset .token-diagram__caption {
  display: flex;
  flex-wrap: wrap;
  column-gap: 1.25rem;
  row-gap: 0.4rem;
  margin: 0.75rem 0 0;
  color: var(--md-default-fg-color--light);
  font-size: 0.8rem;
}

.md-typeset .token-diagram__caption .token-diagram__tag {
  display: inline;
}

/* Colour chip in a component's "Tokens used by this component" table —
   background is set per-row via an inline style, since the color itself is
   the point being shown. */
.md-typeset .token-swatch {
  display: inline-block;
  width: 0.9rem;
  height: 0.9rem;
  vertical-align: middle;
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.2rem;
}

.md-typeset .component-card-art {
  display: block;
  box-sizing: border-box;
  width: 100%;
  height: 7.5rem;
  margin-bottom: 0.75rem;
  padding: 1.25rem;
  object-fit: contain;
  border-radius: 0.75rem;
  background: var(--ixm-accent-tint);
}

/* The Bootstrap Components section wears Bootstrap's colour, not ours. */
.md-typeset .component-section-title--bootstrap .twemoji {
  color: var(--bootstrap-accent);
  background: var(--bootstrap-accent-tint);
}

.md-typeset .bootstrap-cards .component-card-art {
  background: var(--bootstrap-accent-tint);
}

.md-typeset .grid.cards > ul > li:has(.component-card-art),
.md-typeset .grid.cards > ul > li:has(.component-card-icon),
.md-typeset .grid.cards > ul > li:has(.component-card-icon-badge) {
  position: relative;
  display: flex;
  flex-direction: column;
}

/* Every card's title link stretches over the whole tile — bootstrap_components'
   generic selector, no class needed on the link itself. */
.md-typeset .grid.cards > ul > li:has(.component-card-art) a::after,
.md-typeset .grid.cards > ul > li:has(.component-card-icon) a::after,
.md-typeset .grid.cards > ul > li:has(.component-card-icon-badge) a::after {
  position: absolute;
  content: "";
  inset: 0;
}

/* Start here: flat SVG badge icons, self-contained (their own tinted square
   is baked into the artwork), so no extra background wrapper here. */
.md-typeset .component-card-icon {
  display: block;
  width: 3.25rem;
  height: 3.25rem;
  margin-bottom: 0.75rem;
}

/* Material-icon badge for cards with no bespoke SVG — bootstrap_components'
   pattern, tinted with our own light/dark accent tokens. */
.md-typeset .component-card-icon-badge {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 3.25rem;
  height: 3.25rem;
  margin-bottom: 0.75rem;
  color: var(--ixm-accent);
  border-radius: 0.75rem;
  background: var(--ixm-accent-tint);
}

.md-typeset .component-card-icon-badge .twemoji {
  --md-icon-size: 1.75rem;
}

/* "New" flag on a card tile — sits above the stretched title link (z-index)
   so it stays readable, not clickable in its own right. */
.md-typeset .component-card-badge {
  position: absolute;
  z-index: 1;
  top: 0.75rem;
  right: 0.75rem;
  padding: 0.15rem 0.5rem;
  border-radius: 0.375rem;
  color: var(--ixm-accent-ink);
  font-size: 0.65rem;
  font-weight: 700;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  background: var(--ixm-accent);
}

/* Canvas-placeable mark: a quiet icon on the tile (opposite "New"), a pill
   under the component page title. Non-placeable components show nothing. */
.md-typeset .canvas-badge {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  color: var(--ixm-accent);
}

.md-typeset .grid.cards .canvas-badge {
  position: absolute;
  z-index: 1;
  top: 0.75rem;
  left: 0.75rem;
  justify-content: center;
  width: 1.6rem;
  height: 1.6rem;
  border-radius: 999px;
  background: var(--md-default-bg-color);
  box-shadow: 0 0 0 1px var(--md-default-fg-color--lightest);
}

.md-typeset .canvas-badge--page {
  padding: 0.2rem 0.65rem;
  border-radius: 999px;
  font-size: 0.75rem;
  font-weight: 600;
  background: var(--ixm-accent-tint);
}

/* Interior page hero: smaller serif treatment, plus an eyebrow stating an
   actual fact rather than restating the title. */
.md-typeset .ixm-eyebrow {
  display: block;
  margin-bottom: 0.5rem;
  letter-spacing: 0.02em;
  color: var(--md-default-fg-color--light);
  font-size: 0.8rem;
  font-weight: 700;
}

.md-typeset .ixm-page-hero h1 {
  margin: 0 0 0.75rem;
  letter-spacing: -0.01em;
  font-family: var(--ixm-font-serif);
  font-size: 3rem;
  font-weight: 400;
  line-height: 1.08;
}

.md-typeset .ixm-page-hero .ixm-lede {
  max-width: 46rem;
  color: var(--md-default-fg-color--light);
  font-size: 1.05rem;
}

/* The single fact readers care about most before running an upgrade,
   promoted from a buried admonition to the hero's own voice. */
.md-typeset .ixm-pull-quote {
  max-width: 42rem;
  margin: 1.5rem 0;
  padding: 0.25rem 0 0.25rem 1.25rem;
  color: var(--md-typeset-color);
  border-left: 3px solid var(--ixm-accent);
  font-family: var(--ixm-font-serif);
  font-size: 1.5rem;
  font-weight: 400;
  line-height: 1.4;
}

/* Vertical timeline for genuinely sequential content (the three upgrade
   commands), numbered by icon rather than the list's own marker. */
.md-typeset .ixm-steps {
  margin: 1.5rem 0;
}

.md-typeset .ixm-steps > ul {
  margin: 0;
  padding: 0;
  list-style: none;
}

.md-typeset .ixm-steps > ul > li {
  position: relative;
  min-height: 2.25rem;
  padding: 0 0 1.75rem 3.25rem;
}

.md-typeset .ixm-steps > ul > li:last-child {
  padding-bottom: 0;
}

.md-typeset .ixm-steps > ul > li:not(:last-child)::after {
  position: absolute;
  top: 2.4rem;
  bottom: 0;
  left: 1.1rem;
  width: 2px;
  content: "";
  background: var(--md-default-fg-color--lightest);
}

.md-typeset .ixm-steps > ul > li > p:first-child {
  height: 0;
  margin: 0;
}

.md-typeset .ixm-step-num {
  position: absolute;
  top: 0;
  left: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 2.25rem;
  height: 2.25rem;
  color: var(--ixm-accent-ink);
  border-radius: 50%;
  background: var(--ixm-accent);
  font-family: -apple-system, system-ui, Roboto, Helvetica, Arial, sans-serif;
  font-size: 1.05rem;
  font-weight: 700;
}

/* Breaking-change cards: same shape as the components page, red-tinted to
   read as caution against the other badges. */
.md-typeset .ixm-cards-3 {
  grid-template-columns: repeat(3, 1fr);
}

@media screen and (max-width: 59.9375em) {
  .md-typeset .ixm-cards-3 {
    grid-template-columns: repeat(2, 1fr);
  }
}

@media screen and (max-width: 44.9375em) {
  .md-typeset .ixm-cards-3 {
    grid-template-columns: 1fr;
  }
}

.md-typeset .ixm-cards-2 {
  grid-template-columns: repeat(2, 1fr);
}

@media screen and (max-width: 44.9375em) {
  .md-typeset .ixm-cards-2 {
    grid-template-columns: 1fr;
  }
}

/* Two-panel comparison (theme tokens vs. component tokens): an echo of the
   homepage's light/dark theming-split graphic, done here in text. */
.md-typeset .ixm-split {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1.25rem;
  margin: 1.5rem 0;
}

@media screen and (max-width: 44.9375em) {
  .md-typeset .ixm-split {
    grid-template-columns: 1fr;
  }
}

.md-typeset .ixm-split > div {
  /* Grid items default to min-width: auto, so a long code line won't shrink
     to the column and overflows the page instead of scrolling in its own <code>. */
  min-width: 0;
  padding: 1.25rem;
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.75rem;
}

.md-typeset .ixm-split code {
  font-size: 0.8rem;
}

/* Live component demos: an iframe loading a real, standalone render of the
   component (docs/demos/*.html). docs/javascripts/demo-viewport.js wraps the
   plain <iframe class="component-demo-frame"> authored in the markdown with
   the toolbar/frame-wrap structure below, renders it at a real device width
   so its own media queries evaluate truthfully, then scales it to fit. */
.md-typeset .component-demo {
  margin: 1.25rem 0;
  border-radius: 0.75rem;
  box-shadow: 0 1px 2px rgb(0 0 0 / 4%), 0 8px 20px rgb(0 0 0 / 7%);
}

/* The canvas the previewed page sits on — spans the full width of the
   surrounding .tabbed-block content. Only the bottom corners round; the
   toolbar above forms the top of the same card. */
.md-typeset .component-demo__frame-wrap {
  position: relative; /* anchors the fullscreen button in its top-right. */
  min-height: 4rem;
  padding: 1.5rem;
  overflow: hidden;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-top: 0;
  border-radius: 0 0 0.75rem 0.75rem;
}

/* Acts on the preview, not on the component's configuration, so it sits over
   the canvas rather than in the toolbar with the prop controls. Sized and
   coloured like the share button it sits diagonally opposite. */
.md-typeset .component-demo__fullscreen-btn {
  position: absolute;
  top: 0.5rem;
  right: 0.5rem;
  z-index: 2;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 1.75rem;
  height: 1.75rem;
  color: var(--md-default-fg-color--light);
  cursor: pointer;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.4rem;
  transition: color 0.15s ease, background-color 0.15s ease;
}

.md-typeset .component-demo__fullscreen-btn svg {
  width: 0.9rem;
  height: 0.9rem;
}

.md-typeset .component-demo__fullscreen-btn:hover {
  color: var(--ixm-accent);
  background: var(--ixm-accent-tint);
}

.md-typeset .component-demo__fullscreen-btn:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

/* Expanded: the demo is pinned over the viewport (see buildFullscreenButton
   in demo-viewport.js for why this isn't the Fullscreen API). The toolbar
   stays usable, so a component can be reconfigured while expanded. */
.md-typeset .component-demo.is-expanded {
  position: fixed;
  inset: 0;
  z-index: 20; /* over Material's header (z-index 2) and sidebars. */
  display: flex;
  flex-direction: column;
  margin: 0;
  overflow: auto;
  background: var(--md-default-bg-color);
  border-radius: 0;
}

.md-typeset .component-demo.is-expanded .component-demo__frame-wrap {
  flex: 1;
  border-right: 0;
  border-bottom: 0;
  border-left: 0;
  border-radius: 0;
}

/* The page behind it must not scroll under the pinned demo. */
body.component-demo-expanded {
  overflow: hidden;
}

/* Wraps a .component-demo (built by demo-viewport.js) and a
   .component-demo__usage panel into one continuous card — toolbar, canvas,
   generated code — instead of the demo reading as a live preview followed by
   an unrelated code sample below it. Elevation/margin move here from
   .component-demo itself, which drops both when nested inside this. */
.md-typeset .component-demo-block {
  margin: 1.25rem 0;
  border-radius: 0.75rem;
  box-shadow: 0 1px 2px rgb(0 0 0 / 4%), 0 8px 20px rgb(0 0 0 / 7%);
}

.md-typeset .component-demo-block .component-demo {
  margin: 0;
  box-shadow: none;
}

.md-typeset .component-demo-block .component-demo__frame-wrap {
  border-bottom: 0;
  border-radius: 0;
}

.md-typeset .component-demo__usage {
  overflow: hidden;
  background: var(--md-code-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0 0 0.75rem 0.75rem;
}

.md-typeset .component-demo__usage-header {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 0.75rem;
  padding: 0.5rem 0.9rem;
  border-bottom: 1px solid var(--md-default-fg-color--lightest);
  color: var(--md-default-fg-color--light);
  font-size: 0.75rem;
  font-weight: 600;
}

.md-typeset .component-demo__usage-label {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
}

/* A quiet pulse rather than a static dot — the cheapest possible signal that
   this panel is wired to the toggles above, not a plain static code sample. */
.md-typeset .component-demo__live-dot {
  width: 0.4rem;
  height: 0.4rem;
  border-radius: 50%;
  background: var(--ixm-accent);
  animation: component-demo-pulse 2s ease-in-out infinite;
}

@media (prefers-reduced-motion: reduce) {
  .md-typeset .component-demo__live-dot {
    animation: none;
  }
}

@keyframes component-demo-pulse {
  0%, 100% {
    opacity: 1;
  }

  50% {
    opacity: 0.35;
  }
}

.md-typeset .component-demo__usage-actions {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  font-weight: 500;
}

.md-typeset .component-demo__usage-actions a {
  color: var(--ixm-accent);
}

.md-typeset .component-demo__usage .highlight {
  margin: 0;
}

.md-typeset .component-demo__usage pre {
  margin: 0;
}

.md-typeset .component-demo__usage pre > code {
  background: transparent;
}

/* A single docked toolbar above the canvas — a demo's own prop controls
   (adopted from inside the iframe by demo-viewport.js once it loads, same
   origin so this is a plain DOM move) on the left, the Mobile/Tablet/Desktop
   switcher on the right. Shaded a step darker than the white canvas below it
   (the same neutral mkdocs-material reserves for code blocks) so it reads as
   the demo's chrome, not more of the rendered page. Normal flow, not
   overlaid, so it never covers the previewed content. */
/* nowrap here, not on .component-demo__props — the viewport switcher stays
   pinned in the top-right corner no matter how many prop controls a demo
   has; props wrap onto their own additional lines underneath it instead of
   ever pushing the switcher down with them. */
.md-typeset .component-demo__toolbar {
  display: flex;
  flex-wrap: nowrap;
  align-items: flex-start;
  gap: 0.75rem;
  padding: 0.4rem 0.75rem;
  background: var(--md-code-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.75rem 0.75rem 0 0;
}

/* Grows to fill the bar, which is what pushes the viewport track to the far
   right without needing justify-content — and what keeps the track flush
   against the right edge even when a demo has no props of its own to fill
   the space with. min-width: 0 lets it actually shrink/wrap in a nowrap
   flex parent instead of forcing the toolbar wider. */
.md-typeset .component-demo__props {
  display: flex;
  flex: 1 1 auto;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.6rem;
  min-width: 0;
  padding: 0.15rem 0;
  font-size: 0.65rem;
  font-weight: 500;
  color: var(--md-default-fg-color);
}

/* The seam between props and the viewport track lives on props' own edge,
   not as padding/border on the track — the track's padding is also the
   coordinate space .component-demo__toolbar-thumb's `left` is measured
   from, so padding added there shifts the buttons without shifting the
   thumb, throwing its width/offset math off. */
.md-typeset .component-demo__props:not(:empty) {
  padding-right: 0.5rem;
  border-right: 1px solid var(--md-default-fg-color--lightest);
}

.md-typeset .component-demo__props label {
  display: flex;
  align-items: center;
  gap: 0.4rem;
  white-space: nowrap;
  cursor: pointer;
}

/* Same [hidden]-vs-display:flex fix as .demo-dock__group above, needed here
   too since reverse-field is a plain label, not a group. */
.md-typeset .component-demo__props label[hidden] {
  display: none;
}

.md-typeset .component-demo__props input[type="checkbox"],
.md-typeset .component-demo__props input[type="radio"] {
  accent-color: var(--ixm-accent);
}

.md-typeset .component-demo__props input:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

.md-typeset .component-demo__props .demo-select {
  padding: 0.15rem 0.35rem;
  color: var(--md-default-fg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.35rem;
  background: var(--md-default-bg-color);
  font: inherit;
  font-size: 0.65rem;
}

.md-typeset .component-demo__props .demo-select:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

/* A demo's own sub-grouping (e.g. the Library radio pair, hidden until
   "Multiple slides" is checked) — restores the divider that only existed in
   the demo's standalone stylesheet before adoptDemoProps() moved it out of
   the iframe and out of that stylesheet's reach. */
.md-typeset .component-demo__props .demo-dock__group {
  display: flex;
  align-items: center;
  gap: 0.35rem;
  padding-left: 0.5rem;
  border-left: 1px solid var(--md-default-fg-color--lightest);
  color: var(--md-default-fg-color--light);
}

/* No seam before the very first control (Layout) — the divider only makes
   sense between groups. */
.md-typeset .component-demo__props .demo-dock__group:first-child {
  padding-left: 0;
  border-left: 0;
}

/* An author display rule beats the UA [hidden] default regardless of
   specificity, so the display: flex above would otherwise always win and
   show a hidden group (e.g. Library before "Multiple slides" is checked). */
.md-typeset .component-demo__props .demo-dock__group[hidden] {
  display: none;
}

/* A button that opens a checkbox panel and stays open across multiple
   selections, closing only on an outside click — see demo-viewport.js.
   Lives inside a .demo-dock__group for the same divider/spacing as the
   Variant and Theme selects beside it. */
.md-typeset .component-demo__props .demo-options {
  position: relative;
}

.md-typeset .component-demo__props .demo-options__trigger {
  display: inline-flex;
  align-items: center;
  gap: 0.3rem;
  padding: 0.15rem 0.35rem;
  color: var(--md-default-fg-color);
  cursor: pointer;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.35rem;
  font: inherit;
  font-size: 0.7rem;
}

/* Matches the native arrow every <select> beside it already has — a button
   opening a panel has no such built-in affordance, so it needs its own. */
.md-typeset .component-demo__props .demo-options__trigger::after {
  content: "";
  width: 0.4em;
  height: 0.4em;
  border-right: 0.12em solid currentcolor;
  border-bottom: 0.12em solid currentcolor;
  transform: rotate(45deg) translateY(-15%);
  transition: transform 0.2s ease;
}

.md-typeset .component-demo__props .demo-options__trigger[aria-expanded="true"]::after {
  transform: rotate(-135deg) translateY(-15%);
}

.md-typeset .component-demo__props .demo-options__trigger:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

.md-typeset .component-demo__props .demo-options__panel {
  position: absolute;
  top: calc(100% + 0.35rem);
  left: 0;
  z-index: 30;
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
  min-width: 9rem;
  padding: 0.6rem 0.75rem;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.5rem;
  box-shadow: var(--md-shadow-z2, 0 0.2rem 0.5rem rgb(0 0 0 / 20%));
}

.md-typeset .component-demo__props .demo-options__panel[hidden] {
  display: none;
}

/* Sits a shade lighter than the toolbar's own chrome — a recessed well the
   thumb slides inside, the same relationship the canvas below has to the
   toolbar above it. A small gap between buttons keeps hover states from
   reading as one continuous strip; the thumb below no longer assumes even
   spacing (it reads each button's own offsetLeft/offsetWidth), so the gap
   doesn't need any matching adjustment there. */
.md-typeset .component-demo__toolbar-track {
  position: relative;
  display: flex;
  flex: none;
  gap: 0.2rem;
  padding: 0.2rem;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.6rem;
  box-shadow: inset 0 1px 2px rgb(0 0 0 / 8%);
}

.md-typeset .component-demo__toolbar-thumb {
  position: absolute;
  top: 0.2rem;
  bottom: 0.2rem;
  left: 0;
  z-index: 0;
  background: var(--ixm-accent);
  border-radius: 0.4rem;
  box-shadow: 0 1px 3px rgb(0 0 0 / 25%);
  transition: transform 0.2s ease;
}

/* Icon-only and fixed-size, deliberately — icon+label pills of differing
   label lengths ("Mobile" vs "Desktop") gave buttons unequal widths despite
   flex: 1 1 0 (flex-basis: 0 doesn't override a nowrap label's own min
   content width), which broke the thumb's single shared width/offset math.
   Fixed square buttons sidestep that entirely. */
.md-typeset .component-demo__viewport-btn {
  position: relative;
  z-index: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 1.75rem;
  height: 1.75rem;
  color: var(--md-default-fg-color--light);
  cursor: pointer;
  background: none;
  border: 0;
  border-radius: 0.4rem;
  transition: color 0.15s ease, background-color 0.15s ease;
}

.md-typeset .component-demo__viewport-btn svg {
  width: 0.9rem;
  height: 0.9rem;
}

/* Preview actions (Statistic's Replay) sit between the props and the device
   switcher and carry the hairline, so they stay on the first row. */
.md-typeset .component-demo__toolbar:has(> [data-dock-end]) .component-demo__props {
  padding-right: 0;
  border-right: 0;
}

.md-typeset .component-demo__toolbar > [data-dock-end] {
  display: flex;
  align-items: center;
  align-self: stretch;
  padding-right: 0.85rem;
  border-right: 1px solid var(--md-default-fg-color--lightest);
}

.md-typeset .demo-icon-btn {
  display: flex;
  gap: 0.3rem;
  align-items: center;
  justify-content: center;
  height: 1.75rem;
  padding: 0 0.5rem;
  font: inherit;
  color: var(--md-default-fg-color--light);
  cursor: pointer;
  background: var(--md-default-bg-color);
  border: 1px solid var(--md-default-fg-color--lightest);
  border-radius: 0.4rem;
  transition: color 0.15s ease;
}

.md-typeset .demo-icon-btn:hover,
.md-typeset .demo-icon-btn:focus-visible {
  color: var(--ixm-accent);
}

.md-typeset .demo-icon-btn svg {
  width: 0.9rem;
  height: 0.9rem;
}

.md-typeset .component-demo__viewport-btn:hover:not(.is-active) {
  color: var(--ixm-accent);
  background: var(--ixm-accent-tint);
}

.md-typeset .component-demo__viewport-btn.is-active {
  color: var(--ixm-accent-ink, #fff);
}

.md-typeset .component-demo__viewport-btn:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

/* Copies a URL with the demo's current toggle state as query params — a BA
   configuring a demo can link straight to it from a ticket. */
.md-typeset .component-demo__share-btn {
  display: flex;
  flex: none;
  align-items: center;
  justify-content: center;
  width: 1.75rem;
  height: 1.75rem;
  color: var(--md-default-fg-color--light);
  cursor: pointer;
  background: none;
  border: 0;
  border-radius: 0.4rem;
  transition: color 0.15s ease, background-color 0.15s ease;
}

.md-typeset .component-demo__share-btn svg {
  width: 0.9rem;
  height: 0.9rem;
}

.md-typeset .component-demo__share-btn:hover,
.md-typeset .component-demo__share-btn.is-copied {
  color: var(--ixm-accent);
  background: var(--ixm-accent-tint);
}

.md-typeset .component-demo__share-btn:focus-visible {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}

/* Same idea as Material's own "Copied to clipboard" bubble on a code block's
   copy button — a small fixed-position label anchored above whatever button
   triggered it, faded in/out with opacity only (transform stays constant,
   doing the centring/offset, so it never fights the fade). Appended straight
   to <body> by demo-viewport.js (so position: fixed is never clipped by an
   ancestor's overflow), which puts it outside .md-typeset — deliberately
   unscoped here rather than styled as typeset content. */
.component-demo__toast {
  position: fixed;
  z-index: 100;
  padding: 0.3rem 0.6rem;
  color: var(--md-default-bg-color);
  background: var(--md-default-fg-color);
  border-radius: 0.25rem;
  font-size: 0.7rem;
  font-weight: 500;
  white-space: nowrap;
  opacity: 0;
  transition: opacity 0.15s ease;
  transform: translate(-50%, -100%);
  pointer-events: none;
}

.component-demo__toast.is-visible {
  opacity: 1;
}

.md-typeset .component-demo-frame {
  display: block;
  max-width: none; /* mkdocs-material clamps iframe/img to 100% by default;
                       demo-viewport.js needs the real device width to size
                       and scale against, not one already clamped to the
                       container. */
  /* Transparent: the demo page paints its own themed ground, and a white
     frame behind a dark one showed as a light arc at the rounded corners. */
  background: transparent;
  border: 0;
  border-radius: 0.5rem;
  box-shadow: 0 1rem 2.5rem rgb(0 0 0 / 30%);

  /* width/height/margin/transform are set per selected device by
     demo-viewport.js: centered at 1:1 scale (fits the canvas), flush left
     when scaled down to fit (fills it exactly, no gap). The canvas behind it
     is the same white, so the shadow (not a color change) is what reads as
     "a distinct surface" at every scale, not just the narrower ones. */
}

/* Tab sets nested inside another tab (e.g. Banner | Slide inside Reference)
   get the same segmented-pill look as the live demo's viewport switcher
   above (.component-demo__toolbar-track / __viewport-btn), instead of
   Material's default underline tabs — so a reader can tell at a glance
   they're a different level of navigation from the page-level tabs. The
   ".tabbed-content .tabbed-set" selector only matches tab sets that live
   inside another tab's content, so top-level tabs are untouched. Capped at
   4 tabs (current usage is 2); raise the nth-child count if a nested set
   ever needs more. */
.md-typeset .tabbed-content .tabbed-set > .tabbed-labels {
  /* Blockified back to `flex` because it's itself a flex item inside the
     column-direction .tabbed-set above — align-self, not display, is what
     stops it stretching to that parent's full width. */
  align-self: flex-start;
  gap: 0.1rem;
  padding: 0;
  margin: 0.625rem 0 1rem;
  box-shadow: none;
}

.md-typeset .tabbed-content .tabbed-set > .tabbed-labels:before {
  display: none; /* replaces Material's sliding underline indicator */
}

/* Material moves a linked tab's own padding/font-size onto the inner <a>
   (and zeroes the <label> itself) — style the <a>, not the <label>, or the
   override lands on a box Material already emptied out. */
.md-typeset .tabbed-content .tabbed-set > .tabbed-labels > label > a {
  padding: 0.2rem 0.6rem;
  color: var(--md-default-fg-color--light);
  border-radius: 0.3rem;
  font-size: 0.6rem;
  font-weight: 600;
  transition: color 0.15s ease, background-color 0.15s ease;
}

.md-typeset .tabbed-content .tabbed-set > .tabbed-labels > label > a:hover {
  color: var(--ixm-accent);
  background: var(--ixm-accent-tint);
}

.md-typeset .tabbed-content .tabbed-set > input:nth-child(1):checked ~ .tabbed-labels > :nth-child(1) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(2):checked ~ .tabbed-labels > :nth-child(2) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(3):checked ~ .tabbed-labels > :nth-child(3) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(4):checked ~ .tabbed-labels > :nth-child(4) > a {
  color: var(--ixm-accent-ink);
  background: var(--ixm-accent);
}

.md-typeset .tabbed-content .tabbed-set > input:nth-child(1):checked ~ .tabbed-labels > :nth-child(1) > a:hover,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(2):checked ~ .tabbed-labels > :nth-child(2) > a:hover,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(3):checked ~ .tabbed-labels > :nth-child(3) > a:hover,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(4):checked ~ .tabbed-labels > :nth-child(4) > a:hover {
  color: var(--ixm-accent-ink);
  background: var(--ixm-accent);
}

/* Material shows focus via the underline indicator we just hid; give the
   nested pill an outline instead so keyboard focus stays visible. */
.md-typeset .tabbed-content .tabbed-set > input:nth-child(1).focus-visible ~ .tabbed-labels > :nth-child(1) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(2).focus-visible ~ .tabbed-labels > :nth-child(2) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(3).focus-visible ~ .tabbed-labels > :nth-child(3) > a,
.md-typeset .tabbed-content .tabbed-set > input:nth-child(4).focus-visible ~ .tabbed-labels > :nth-child(4) > a {
  outline: 2px solid var(--ixm-accent);
  outline-offset: 2px;
}
