Solo estoy trabajando en una lista simple de tareas para practicar y me gustaría poder hacer clic en un elemento de mi lista para eliminarlo. Creo que lo tengo muy cerca, pero no puedo averiguar cómo obtener algún tipo de datos del li en el que se hizo clic para compararlo con mi matriz.
Aplicación.js
import { useState } from "react"; import "./App.css"; import Newtodo from "./NewTodo/NewTodo"; import TodoList from "./TodoList/TodoList"; let INITIAL_TODOS = [ { id: "e1", title: "Set up meeting", date: new Date(2021, 0, 14), index: 0 }, { id: "e2", title: "Doctor appointment", date: new Date(2021, 2, 14), index: 1, }, { id: "e3", title: "Work on project", date: new Date(2021, 1, 22), index: 2 }, { id: "e4", title: "Update resume", date: new Date(2021, 6, 14), index: 3 }, ]; const App = () => { const [todos, setTodos] = useState(INITIAL_TODOS); const deleteItem = (e) => { const newTodos = todos.filter((item) => item.index !== 1 /*This works properly with a hardcoded value(1) but how can this be done dynamically as e doesn't seem to have anything useful within it (like e.target.value)*/); setTodos(newTodos); }; return ( <div className="App"> <Newtodo /> <TodoList items={todos} handleDelete={deleteItem} /> </div> ); }; export default App;TodoList.js
import "./TodoList.css"; import Todo from "./Todo"; const TodoList = (props) => { return ( <div className="todo-list"> <ul> {props.items.map((todo, i) => ( <Todo index={i} key={todo.id} title={todo.title} date={todo.date} handleDelete={props.handleDelete} /> ))} </ul> </div> ); }; export default TodoList;Todo.js
import "./Todo.css"; const Todo = (props) => { const month = props.date.toLocaleString("en-US", { month: "long" }); const day = props.date.toLocaleString("en-US", { day: "2-digit" }); const year = props.date.getFullYear(); return ( <li onClick={props.handleDelete} className="todo-item"> <h2>{props.title}</h2> <span> {day}, {month}, {year} </span> </li> ); }; export default Todo;¡Cualquier ayuda o dirección sería muy apreciada!
Debe pasar el índice del elemento que desea eliminar. En el filtro del controlador de eliminación por elementos con índices que no son iguales al índice pasado
const deleteItem = (index) => { setTodos(todos => todos.filter((item, i) => i !== index)); };Y en el mapeo
const TodoList = (props) => { return ( <div className="todo-list"> <ul> {props.items.map((todo, i) => ( <Todo index={i} key={todo.id} title={todo.title} date={todo.date} handleDelete={() => props.handleDelete(i)} /> ))} </ul> </div> ); }; Puede ser mejor usar la propiedad id en su lugar.
const deleteItem = (id) => { setTodos(todos => todos.filter((item) => item.id !== id)); };...
const TodoList = (props) => { return ( <div className="todo-list"> <ul> {props.items.map((todo, i) => ( <Todo index={i} key={todo.id} title={todo.title} date={todo.date} handleDelete={() => props.handleDelete(todo.id)} /> ))} </ul> </div> ); }; Y para evitar la devolución de llamada anónima en el componente secundario, declare handleDelete como una función procesada.
const deleteItem = (id) => () => { setTodos(todos => todos.filter((item) => item.id !== id)); };...
const TodoList = (props) => { return ( <div className="todo-list"> <ul> {props.items.map((todo, i) => ( <Todo index={i} key={todo.id} title={todo.title} date={todo.date} handleDelete={props.handleDelete(todo.id)} /> ))} </ul> </div> ); };Primero debe pasar su id de tarea a handle delete y luego puede acceder a la id allí
{ props.items.map((todo, i) => ( <Todo index={i} key={todo.id} title={todo.title} date={todo.date} handleDelete={()=> props.handleDelete(todo.id)} /> ))}Accedes a la identificación aquí
const deleteItem = (todoId) => { const newTodos = todos.filter((item) => item.id !== todoId; setTodos(newTodos); };Agregue el atributo data-index en su Todo.js
<li data-index={props.index} onClick={props.handleDelete} className="todo-item"> <h2>{props.title}</h2> <span> {day}, {month}, {year} </span> </li> y borrarlo en deleteTodo
const deleteItem = (e) => { const newTodos = todos.filter((item) => +item.index !== +e.currentTarget.dataset.index) setTodos(newTodos); };