Tablero Kanban: Búsqueda, Toast de Deshacer y Prioridades
hard⏱ 20 minreactlesson
APRENDE HACIENDOPon a prueba tu intuición3 pasos
Tablero Kanban: Búsqueda, Toast de Deshacer y Prioridades
Usa los ejemplos y la explicación de la lección para comprobar tu idea.
Reflexión personal. No se envía a ningún servicio de IA.ENEste enunciado todavía está solo en inglés; la traducción al español está en camino.
Código inicial Construye tres features sobre un tablero Kanban que ya funciona. La base ya incluye: cuatro columnas renderizadas desde un registro de columnas, alta de tarjetas hacia la columna elegida en el dropdown, drag-and-drop entre columnas (y reordenamiento dentro de una), edición inline de título/descripción, borrado y persistencia en localStorage.
El modelo de datos — dos estados unidos por el id de columna, sin datos de tareas duplicados. COLUMNS responde qué columnas existen, en qué orden y cómo se llaman; tasksByCol responde qué hay dentro de cada columna (sus keys deben coincidir con las de COLUMNS).
Tus tareas:
- TODO(A) — Búsqueda / Filtro: en tiempo real e insensible a mayúsculas, coincidiendo por título O descripción. No destructivo — nunca mutes
tasksByCol; deriva la vista visible con useMemo. Decide si los contadores muestran el conteo filtrado o el total.
- TODO(B) — Toast de borrado con Deshacer: el toast dura 5 segundos y luego el borrado es permanente. Deshacer restaura la tarjeta en la misma columna y en el mismo índice. Solo el último borrado es deshacible.
- TODO(C) — Prioridad: un badge low/medium/high en cada tarjeta; al hacer clic cicla el valor; las tarjetas nuevas nacen en medium.
Why this happens
El tablero tiene una única fuente de verdad: tasksByCol es dueño de la ubicación de las tarjetas. El resultado de la búsqueda debe ser una vista derivada (useMemo sobre tasksByCol + query) — guardarlo como un tercer estado se desincronizaría en cuanto una tarjeta se mueva. Borrar + Deshacer necesita exactamente un snapshot { task, columnId, index } y un id de timer: un borrado nuevo sobrescribe ambos, y justamente por eso "solo el último borrado es deshacible" sale gratis, sin contabilidad extra. El id del timer vive en un useRef porque no es estado de render — cambiarlo no debe re-renderizar. La prioridad es un ciclo puro sobre ["low", "medium", "high"], con medium por defecto al crear.