<script lang="ts">
  import type { RackSlot } from '../lib/placement';
  import { BLANK } from '../lib/placement';
  import { valueForLetter } from '../lib/alphabet';
  import type { Variant } from '../lib/model';

  let {
    slots,
    variant,
    selected,
    ondown,
  }: {
    slots: RackSlot[];
    variant: Variant;
    selected: number | null;
    ondown: (e: PointerEvent, index: number) => void;
  } = $props();

  // Used slots are hidden (the rack shifts left, freeing room on the right for the
  // MakeMove control); the slot still exists in the model for per-tile recall.
  const visible = $derived(slots.filter((s) => !s.used));
</script>

<div class="rack">
  {#each visible as slot (slot.index)}
    <button
      class="tile"
      class:selected={selected === slot.index}
      data-rack-index={slot.index}
      onpointerdown={(e) => ondown(e, slot.index)}
    >
      <span class="letter">{slot.letter === BLANK ? '' : slot.letter}</span>
      {#if slot.letter !== BLANK}<span class="val">{valueForLetter(variant, slot.letter)}</span>{/if}
    </button>
  {/each}
</div>

<style>
  .rack {
    display: flex;
    gap: 5px;
    align-items: center;
    /* Reserve one tile's height so an empty rack (e.g. a finished game) keeps the
       footer the same size as during play — no layout jump between states. */
    min-height: min(12.5vw, 46px);
  }
  .tile {
    position: relative;
    flex: 0 0 auto;
    width: min(12.5vw, 46px);
    aspect-ratio: 1;
    background: var(--tile-bg);
    color: var(--tile-text);
    border: none;
    border-radius: 5px;
    box-shadow: inset 0 -3px 0 var(--tile-edge);
    font-weight: 700;
    font-size: 1.4rem;
    touch-action: none;
    user-select: none;
  }
  .tile.selected {
    outline: 3px solid var(--accent);
    outline-offset: -3px;
  }
  .letter {
    position: absolute;
    top: 8%;
    left: 14%;
  }
  .val {
    position: absolute;
    right: 4px;
    bottom: 1px;
    font-size: 0.7rem;
    font-weight: 600;
  }
</style>
