Fixes the reported breadboard wiring UX ("requerimos un vocabulario"):
Vocabulary implemented (breadboardOccupancy.ts, pure + unit-tested):
- 1 hole = 1 wire. A hole already holding a visible wire can't start a
new one — clicking it SELECTS that wire. This is the core fix: wires
running hole-to-hole across the board were impossible to select
because the pin overlays swallowed every click and silently started a
new wire (so the top horizontal rail wire was un-deletable).
- Same 5-hole strip / rail = one net. When a new wire end lands in an
occupied hole (a seated leg or another wire), it shifts to the
NEAREST FREE hole of the same group — electrically identical, the
real-world "bridge to the next hole in the row". Never crosses strips.
Two selection bugs behind the symptom:
- Click on a wire lying over the breadboard BODY now selects the wire
instead of opening the breadboard's 830-hole property dialog (that
list popping over everything was the "se sobrepone la lista de todos
los puntos" report). Guarded so the bubbled canvas click doesn't
re-toggle the fresh selection.
- Click on a hole occupied by a wire selects the wire (handlePinClick),
so wires anchored in holes are reachable at all.
Jumper colors (like a real kit — a board of identical green wires is
unreadable, "se ven todos verdes"):
- Power-rail holes mandate red (tp./bp. = +) / black (tn./bn. = −).
- Other breadboard holes get a random jumper-palette color on manual
draw; red and black are reserved for rails.
- jumperColorForId gives agent/deterministic callers a stable per-wire
color across reloads.
Tests: breadboard-occupancy.test.ts (12) — findWireAtHole (skips seating
wires, topmost wins), resolveFreeHole (same-strip shift, no cross-strip,
rail shift, passthrough), color policy (rails, palette determinism,
red/black reserved).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>