/* Hand-rolled drag and drop — the engine is sortable_controller.js. While a
   drag is in flight the pressed row stays in the list as a .drag-gap slot and
   a .drag-card clone of it rides under the pointer. */

.handle {
  cursor: grab;
  /* The drag begins here: the browser must not turn the gesture into a page
     scroll, a text selection, or a long-press callout. */
  touch-action: none;
  -webkit-user-select: none;
  user-select: none;
  -webkit-touch-callout: none;
  /* Grow the touch target to ~44px without shifting layout */
  padding: 0.625rem;
  margin: -0.625rem;
}

.handle:active {
  cursor: grabbing;
}

/* The handle is a real tab stop, so it needs to look like one. */
.handle:focus-visible {
  outline: 2px solid rgb(59 130 246); /* blue-500 */
  outline-offset: 0;
  border-radius: 0.375rem;
}

/* Mid-drag, nothing on the page should select or show its own cursor. */
body.dragging,
body.dragging * {
  cursor: grabbing;
  -webkit-user-select: none;
  user-select: none;
}

/* The clone riding under the pointer. Its inline transform tracks the
   pointer, so the lift and drop effects live on separate properties — scale
   and shadow — that transition independently of it. */
.drag-card {
  position: fixed;
  z-index: 100;
  pointer-events: none;
  background-color: rgb(255 255 255);
  border-radius: 0.75rem;
  box-shadow: 0 1px 3px rgb(0 0 0 / 0.15);
  transition:
    scale 150ms ease,
    box-shadow 150ms ease;
}

.dark .drag-card {
  background-color: rgb(31 41 55); /* gray-800 */
}

/* Crossing a block boundary swaps the card between root and nested sizing
   (the data-parent-id attribute toggles); ease the type between the two. */
.drag-card .exercise-name,
.drag-card .exercise-mode {
  transition: font-size 150ms ease;
}

.drag-card--lifted {
  scale: 1.03;
  box-shadow:
    0 12px 24px -6px rgb(0 0 0 / 0.25),
    0 4px 8px rgb(0 0 0 / 0.1);
}

/* A block travels as a chip: just its header, children folded away. The
   footer selector repeats .workout__block to out-rank the :has(.item) reveal
   in empty_states.css, which this file follows alphabetically. */
.drag-card--block [data-parent-id],
.drag-card--block .workout__block .workout__block-footer {
  display: none;
}

/* The slot the card will land on. The row keeps its size in the list — its
   content just steps out of sight behind the outline. */
.drag-gap {
  position: relative;
}

.drag-gap > * {
  visibility: hidden;
}

.drag-gap::after {
  content: "";
  position: absolute;
  inset: 0.25rem 0;
  border-radius: 0.75rem;
  border: 2px dashed rgb(147 197 253); /* blue-300 */
  background-color: rgb(239 246 255 / 0.6); /* blue-50 */
}

.dark .drag-gap::after {
  border-color: rgb(30 64 175); /* blue-800 */
  background-color: rgb(30 58 138 / 0.3); /* blue-900 */
}

/* An exercise held over a block lights the whole block up as the target. */
.workout__block.drag-into {
  outline: 2px solid rgb(96 165 250); /* blue-400 */
  outline-offset: 6px;
  border-radius: 0.5rem;
}

/* While a block is being dragged every block folds to its header, so even a
   long workout fits on screen and every drop slot is close by. Specificity
   note: the footer rule must out-rank .workout__block:has(.item) in
   empty_states.css, which this file follows alphabetically. */
.dragging-block .workout__block [data-parent-id],
.dragging-block .workout__block .workout__block-footer {
  display: none;
}
