/**
 * <slot-grid> canonical styles — Phase 2 of the surface-architecture migration.
 *
 * Single owner of the slot-grid container CSS. Replaces the three
 * pre-migration grid containers:
 *   - .storyboard-strip  (Detail page, 200px tiles, flex nowrap)        → data-mode="detail"
 *   - .summary-strip     (Summary page, 160px tiles, overflow-x scroll) → data-mode="summary"
 *   - .cv-concept-slots  (Canvas ConceptNode, 160px tiles, no scroll)   → data-mode="canvas"
 *
 * Token fallbacks per spec §5.2 so the primitive renders correctly when
 * loaded standalone (e.g. on the dev fixture page that doesn't load
 * styles.css).
 *
 * SURFACE CSS DOES NOT TARGET SLOT-TILE FROM HERE — per spec §5.4 the
 * grid sets the tile's effective width via flex sizing rules on its own
 * children. The slot-tile primitive's intrinsic width:100% then fills
 * whatever space the grid allots to it.
 */

/* ============================================================
 * Host element — block-level container. The inner content box
 * (.slot-grid__content) carries the layout rules. The host stays
 * neutral so surfaces can apply layout positioning (e.g. flex
 * inside a parent panel) without conflicting with the inner box.
 * ============================================================ */
slot-grid {
  display: block;
  position: relative;
  width: 100%;
  box-sizing: border-box;
}

slot-grid__content,
.slot-grid__content {
  display: flex;
  flex-wrap: nowrap;
  align-items: flex-start;
  box-sizing: border-box;
  /* Default gap; modes override below. */
  gap: 12px;
}

/* ============================================================
 * Detail mode — 200px tiles, 14px gap, no scroll, flex nowrap.
 * Mirrors the pre-migration `.storyboard-strip` rules from styles.css
 * (lines 1464-1482). The padding-top: 0 is intentional — slot-tile's
 * own padding-top: 28px (per Phase 1) already reserves room for the
 * menu protrusion; the grid doesn't need to add more.
 * ============================================================ */
slot-grid[data-mode="detail"] > .slot-grid__content {
  gap: 14px;
  justify-content: flex-start;
}
slot-grid[data-mode="detail"] slot-tile {
  width: 200px;
  max-width: 200px;
  min-width: 60px;
  flex: 0 1 200px;
}
@media (max-width: 1400px) {
  slot-grid[data-mode="detail"] slot-tile { flex-basis: 170px; max-width: 170px; }
}
@media (max-width: 1100px) {
  slot-grid[data-mode="detail"] slot-tile { flex-basis: 140px; max-width: 140px; }
}

/* ============================================================
 * Summary mode — 160px tiles, 12px gap, overflow-x: auto for
 * horizontal scroll when slot count exceeds visible width.
 *
 * padding-top: 28px is intentional even though slot-tile reserves
 * its own 28px padding-top — the host margin is what protects the
 * menu's downward nudge transform (translateY(2px) on hover) from
 * being clipped at the strip's TOP edge by the implicit overflow-y:
 * hidden that comes with overflow-x: auto. CSS spec: setting overflow
 * on one axis forces the other axis to non-visible. The extra padding
 * gives the menu the buffer it needs inside the strip's scroll
 * container.
 *
 * scroll-padding-left: 8px keeps the leftmost tile from sticking
 * to the edge when snap-scrolling (no snap is set yet, but the
 * padding is harmless and visually nicer).
 * ============================================================ */
slot-grid[data-mode="summary"] {
  overflow-x: auto;
  overflow-y: visible;
  padding-top: 28px;
  padding-bottom: 4px;
  scrollbar-width: thin;
  scroll-padding-left: 8px;
}
slot-grid[data-mode="summary"] > .slot-grid__content {
  gap: 12px;
  flex-wrap: nowrap;
}
slot-grid[data-mode="summary"] slot-tile {
  width: 160px;
  max-width: 160px;
  min-width: 160px;
  flex: 0 0 160px;
}

/* ============================================================
 * Canvas mode — 160px tiles, 12px gap, no scroll (React Flow
 * viewport handles the canvas-level zoom + pan). padding-top: 0
 * because the React Flow node's own padding above the grid
 * (.cv-concept-head bottom + grid container padding) already
 * gives the menu room; an extra 28px here would push the slots
 * too far from the concept header.
 *
 * The grid's flex layout still works fine for React Flow — RF
 * doesn't care what the node's inner structure is; it just
 * reads the outer node's bounding box for the wire endpoints.
 * Inside the node, we're free to use flex.
 * ============================================================ */
slot-grid[data-mode="canvas"] > .slot-grid__content {
  gap: 12px;
  flex-wrap: nowrap;
  padding: 0;
}
slot-grid[data-mode="canvas"] slot-tile {
  width: 160px;
  max-width: 160px;
  min-width: 160px;
  flex: 0 0 160px;
}

/* ============================================================
 * Drag-state hooks — Phase 7 / Wave 18B.
 *
 *   - body.is-dragging-slot   : global drag-in-progress signal.
 *     Owned by slot_grid.js. slot_tile.css uses it to suppress
 *     hover-play on non-source tiles (pointer-events: none rule
 *     in slot_tile.css §drag-state). Added to the document body
 *     when the source tile crosses the 5px activation threshold.
 *
 *   - slot-grid.is-drag-active : THIS grid has an in-progress drag.
 *     Used to disable scroll-snap / overflow scrolling during the
 *     gesture (otherwise the source tile's translateX transform
 *     would fight the scroll container in Summary mode), and to
 *     change cursor affordances.
 *
 *   - slot-tile--is-dragging-source / --is-drop-target : tile-level
 *     classes set by the drag engine. Their visual rules live in
 *     slot_tile.css so the tile owns its own drag visuals.
 *
 * The drop indicator (30%-alpha outline showing where the slot
 * will land, per spec §5.3.2) is realised by the sibling shift +
 * cursor-following source as a CSS-only stand-in: where the
 * source vacates, the sibling shifts open a tile-width gap.
 * There is no separate ghost DOM element, by design (per spec
 * §5.3.1 walk-back from the earlier clone idiom).
 * ============================================================ */
slot-grid.is-drag-active {
  cursor: grabbing;
  /* Disable text/image selection during drag — pointer captures
     the gesture but selection drag is a separate browser gesture
     that can still kick in if the cursor crosses a text node. */
  user-select: none;
  -webkit-user-select: none;
}
/* Wave 18C: in Summary mode (the only mode with overflow-x: auto on
   the host), keep the host scrollable during drag so the engine's
   edge-autoscroll loop can advance scrollLeft when the pointer enters
   the 30px edge zone. Overflow-y stays visible so the menu's hover
   nudge doesn't get clipped. The source tile's translateX is applied
   inside slot-grid__content; the host's scrollLeft is orthogonal, so
   the "transform fights scroll" concern from spec §5.3.3 does not
   apply (stride math reads snapshot rects, not live rects). */
slot-grid[data-mode="summary"].is-drag-active {
  overflow-x: auto;
  overflow-y: visible;
}
/* Detail + canvas: keep overflow visible during drag (no autoscroll
   needed; spec §5.3.3 invariant width). */
slot-grid[data-mode="detail"].is-drag-active,
slot-grid[data-mode="canvas"].is-drag-active {
  overflow: visible;
}
slot-grid.is-drag-active slot-tile {
  /* Source has its own grabbing cursor via slot_tile.css.
     Other tiles get default while drag is in progress (the
     pointer-events: none rule on the body class already
     prevents hover, so cursor here is mostly informational). */
  cursor: default;
}
