/* ─── Switch + Switcher — shared component styles ─────────────────────────────
   Single source of truth for component CSS.
   Values: site/tokens.css (--ds-switch-* tokens)
   Consumers: site/preview/switcher.html + src/components/Switch/Switch.tsx
              + src/components/Switcher/Switcher.tsx
   Naming: ds- prefix replaces CSS Modules scoping
   States: data-attributes only
     Switch:   data-size / data-checked / data-disabled / data-hovered /
               data-pressed / data-error / data-focus-visible
     Switcher: data-size / data-variant / data-checked / data-disabled /
               data-hovered / data-pressed / data-error
   ─────────────────────────────────────────────────────────────────────────── */

/* ═══════════════════════════════════════════════════════════════════════════
   SWITCH — pill toggle control (button element)
   ═══════════════════════════════════════════════════════════════════════════ */

/* ── Root — the button element ──────────────────────────────────────────── */

.ds-switch {
  display: inline-flex;
  align-items: center;
  gap: var(--ds-switch-md-gap);
  background: transparent;
  border: none;
  padding: 0;
  cursor: pointer;
  border-radius: calc(var(--ds-switch-track-r-md) + var(--ds-switch-thumb-inset));
  outline: none;
  user-select: none;
  -webkit-tap-highlight-color: transparent;
}

.ds-switch[data-size='sm'] {
  gap: var(--ds-switch-sm-gap);
  border-radius: calc(var(--ds-switch-track-r-sm) + var(--ds-switch-thumb-inset));
}

.ds-switch[data-disabled] {
  cursor: not-allowed;
}

/* ── Focus ring ─────────────────────────────────────────────────────────── */

.ds-switch[data-focus-visible] {
  box-shadow: var(--ds-focus-ring);
}

/* ── Track — pill-shaped background ────────────────────────────────────── */

.ds-switch-track {
  position: relative;
  width: var(--ds-switch-track-w-md);
  height: var(--ds-switch-track-h-md);
  border-radius: var(--ds-switch-track-r-md);
  background: var(--ds-surface-0);
  border: 1.5px solid var(--ds-nba-border);
  transition:
    background var(--ds-dur-2) var(--ds-ease),
    border-color var(--ds-dur-2) var(--ds-ease),
    border-width var(--ds-dur-2) var(--ds-ease);
  display: flex;
  align-items: center;
  flex-shrink: 0;
}

:is(.ds-switch, .ds-switcher)[data-size='sm'] .ds-switch-track {
  width: var(--ds-switch-track-w-sm);
  height: var(--ds-switch-track-h-sm);
  border-radius: var(--ds-switch-track-r-sm);
}

/* Track states — :is(.ds-switch, .ds-switcher) покрывает оба контекста:
   standalone Switch (.ds-switch[state]) и Switcher (site-демо кладёт трек голым
   под .ds-switcher[state]; в React трек ещё и под .ds-switch). */

/* Track states — unchecked [off] */

:is(.ds-switch, .ds-switcher)[data-hovered]:not([data-checked]) .ds-switch-track {
  border-color: var(--ds-nba-border);
  background: var(--ds-nba-20);
}

:is(.ds-switch, .ds-switcher)[data-pressed]:not([data-checked]) .ds-switch-track {
  border-color: var(--ds-nba-border);
  background: var(--ds-nba-40);
}

/* Track — checked [on] */

:is(.ds-switch, .ds-switcher)[data-checked] .ds-switch-track {
  background: var(--ds-neutral-fill);
  border-width: 0;
}

:is(.ds-switch, .ds-switcher)[data-checked][data-hovered] .ds-switch-track {
  background: var(--ds-neutral-fill-hover);
}

:is(.ds-switch, .ds-switcher)[data-checked][data-pressed] .ds-switch-track {
  background: var(--ds-neutral-fill-pressed);
}

/* Track — disabled [off] */

:is(.ds-switch, .ds-switcher)[data-disabled] .ds-switch-track {
  background: transparent;
  border-color: var(--ds-nba-border-disabled);
}

/* Track — disabled [on] */

:is(.ds-switch, .ds-switcher)[data-disabled][data-checked] .ds-switch-track {
  background: var(--ds-nba-15);
  border-width: 0;
}

/* Track — error [off] — red border 2px */

:is(.ds-switch, .ds-switcher)[data-error]:not([data-checked]) .ds-switch-track {
  border-width: 2px;
  border-color: var(--ds-neg-default);
  background: var(--ds-surface-0);
}

:is(.ds-switch, .ds-switcher)[data-error][data-hovered]:not([data-checked]) .ds-switch-track {
  border-width: 2px;
  border-color: var(--ds-neg-hover);
  background: var(--ds-nba-20);
}

/* Track — error [on] — красный залитый трек (Figma 338-27792: error+checked = neg fill) */

:is(.ds-switch, .ds-switcher)[data-error][data-checked] .ds-switch-track {
  background: var(--ds-neg-default);
  border-width: 0;
}

/* ── Thumb ───────────────────────────────────────────────────────────────── */

.ds-switch-thumb {
  position: absolute;
  left: var(--ds-switch-thumb-inset-md);
  top: 50%;
  transform: translateY(-50%);
  width: var(--ds-switch-thumb-md);
  height: var(--ds-switch-thumb-md);
  border-radius: 50%;
  background: var(--ds-neutral-fill);
  box-shadow: var(--ds-switch-thumb-shadow);
  transition:
    transform var(--ds-dur-2) var(--ds-ease-spring),
    width var(--ds-dur-1) var(--ds-ease);
  will-change: transform;
}

:is(.ds-switch, .ds-switcher)[data-size='sm'] .ds-switch-thumb {
  left: var(--ds-switch-thumb-inset-sm);
  width: var(--ds-switch-thumb-sm);
  height: var(--ds-switch-thumb-sm);
}

/* Thumb — checked: invert to stay visible against dark fill track */

:is(.ds-switch, .ds-switcher)[data-checked] .ds-switch-thumb {
  background: var(--ds-surface-0);
}

/* Thumb travel [md]: track-w-md - thumb-md - 2 x inset-md = 40 - 12 - 12 = 16px */

:is(.ds-switch, .ds-switcher)[data-checked] .ds-switch-thumb {
  transform: translateY(-50%)
    translateX(
      calc(
        var(--ds-switch-track-w-md) - var(--ds-switch-thumb-md) -
          2 * var(--ds-switch-thumb-inset-md)
      )
    );
}

/* Thumb travel [sm]: track-w-sm - thumb-sm - 2 x inset-sm = 32 - 10 - 10 = 12px */

:is(.ds-switch, .ds-switcher)[data-size='sm'][data-checked] .ds-switch-thumb {
  transform: translateY(-50%)
    translateX(
      calc(
        var(--ds-switch-track-w-sm) - var(--ds-switch-thumb-sm) -
          2 * var(--ds-switch-thumb-inset-sm)
      )
    );
}

/* Thumb — disabled */

:is(.ds-switch, .ds-switcher)[data-disabled] .ds-switch-thumb {
  background: var(--ds-neutral-fill);
  opacity: 0.4;
  box-shadow: none;
}

/* ═══════════════════════════════════════════════════════════════════════════
   SWITCHER — label wrapper for Switch (ghost + container variants)
   ═══════════════════════════════════════════════════════════════════════════ */

/* ── Root — the label element ───────────────────────────────────────────── */

.ds-switcher {
  display: inline-flex;
  align-items: flex-start;
  gap: var(--ds-switch-md-gap);
  cursor: pointer;
  user-select: none;
  border-radius: var(--ds-switch-cont-r-md);
  transition: background var(--ds-dur-2) var(--ds-ease);
}

.ds-switcher[data-size='sm'] {
  gap: var(--ds-switch-sm-gap);
  border-radius: var(--ds-switch-cont-r-sm);
}

.ds-switcher[data-disabled] {
  cursor: not-allowed;
}

/* ── Placement — где находится контрол относительно лейбла ──────────────────
   default: switch leading (слева), label справа.
   data-label-position='left': label слева, switch у правого края (space-between
   обеспечивается label-col flex:1 в row-reverse). Источник: Figma 338-27792. */
.ds-switcher[data-label-position='left'] {
  flex-direction: row-reverse;
}

/* ── Container variant — adds background + padding ───────────────────────── */

.ds-switcher[data-variant='container'] {
  padding: var(--ds-switch-cont-py-md) var(--ds-switch-cont-px-md);
  background: var(--ds-surface);
}

.ds-switcher[data-variant='container'][data-size='sm'] {
  padding: var(--ds-switch-cont-py-sm) var(--ds-switch-cont-px-sm);
}

/* Container hover — unchecked */
.ds-switcher[data-variant='container'][data-hovered]:not([data-disabled]):not([data-checked]) {
  background: var(--ds-nba-20);
}

/* Container pressed — unchecked */
.ds-switcher[data-variant='container'][data-pressed]:not([data-disabled]):not([data-checked]) {
  background: var(--ds-nba-40);
}

/* Container checked — resting */
.ds-switcher[data-variant='container'][data-checked] {
  background: var(--ds-nba-15);
}

/* Container checked — hover */
.ds-switcher[data-variant='container'][data-checked][data-hovered]:not([data-disabled]) {
  background: var(--ds-nba-20);
}

/* Container checked — pressed */
.ds-switcher[data-variant='container'][data-checked][data-pressed]:not([data-disabled]) {
  background: var(--ds-nba-40);
}

/* Container disabled */
.ds-switcher[data-variant='container'][data-disabled] {
  background: var(--ds-nba-15);
}

/* ── Label column (text + caption stack) ────────────────────────────────── */

.ds-switcher-label-col {
  display: flex;
  flex-direction: column;
  gap: var(--ds-switch-core-gap);
  flex: 1 0 0;
  min-width: 0;
}

/* ── Label row (text + icon help) ───────────────────────────────────────── */

.ds-switcher-label-row {
  display: flex;
  align-items: center;
  gap: var(--ds-switch-label-gap-md);
  padding: 0 var(--ds-switch-label-px-md);
}

.ds-switcher[data-size='sm'] .ds-switcher-label-row {
  gap: var(--ds-switch-label-gap-sm);
  padding: 0 var(--ds-switch-label-px-sm);
}

/* ── Label text ─────────────────────────────────────────────────────────── */

.ds-switcher-label-text {
  flex: 1 0 0;
  min-width: 0;
  font-size: var(--ds-switch-md-fs);
  line-height: var(--ds-switch-md-lh);
  font-weight: 500;
  color: var(--ds-text-primary);
}

.ds-switcher[data-size='sm'] .ds-switcher-label-text {
  font-size: var(--ds-switch-sm-fs);
  line-height: var(--ds-switch-sm-lh);
}

.ds-switcher[data-disabled] .ds-switcher-label-text {
  color: var(--ds-disabled-text);
}

/* Error = control-only (track/border red). Label + caption остаются обычного
   цвета — единый контракт form-control семьи (Radio/Checkbox НЕ красят лейбл).
   НЕ возвращать сюда color: neg — это была выдуманная регрессия (2026-06-11). */

/* ── Help icon ──────────────────────────────────────────────────────────── */

.ds-switcher-icon-help {
  display: flex;
  align-items: flex-start;
  padding: var(--ds-switch-icon-py-md) 0;
  flex-shrink: 0;
  color: var(--ds-text-secondary);
}

.ds-switcher[data-size='sm'] .ds-switcher-icon-help {
  padding: var(--ds-switch-icon-py-sm) 0;
}

.ds-switcher[data-disabled] .ds-switcher-icon-help {
  color: var(--ds-disabled-text);
}

/* ── Caption ────────────────────────────────────────────────────────────── */

.ds-switcher-caption {
  display: block;
  padding: 0 var(--ds-switch-caption-px-md);
  font-size: var(--ds-switch-caption-fs);
  line-height: var(--ds-switch-caption-lh);
  font-weight: 400;
  color: var(--ds-text-secondary);
}

.ds-switcher[data-size='sm'] .ds-switcher-caption {
  padding: 0 var(--ds-switch-caption-px-sm);
}

.ds-switcher[data-disabled] .ds-switcher-caption {
  color: var(--ds-disabled-text);
}

/* ── Dark mode overrides ────────────────────────────────────────────────── */

[data-theme="dark"] :is(.ds-switch, .ds-switcher)[data-hovered]:not([data-checked]) .ds-switch-track,
[data-theme="dark"] :is(.ds-switch, .ds-switcher)[data-error][data-hovered]:not([data-checked]) .ds-switch-track {
  background: var(--ds-nba-40);
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) :is(.ds-switch, .ds-switcher)[data-hovered]:not([data-checked]) .ds-switch-track,
  :root:not([data-theme="light"]) :is(.ds-switch, .ds-switcher)[data-error][data-hovered]:not([data-checked]) .ds-switch-track {
    background: var(--ds-nba-40);
  }
}

/* ── Reduced motion ─────────────────────────────────────────────────────── */

@media (prefers-reduced-motion: reduce) {
  .ds-switch-track,
  .ds-switch-thumb {
    transition-duration: 0.01ms !important;
    animation-duration: 0.01ms !important;
  }
}
