【React】项目1:待办事项列表(Todo App)

50 阅读1分钟

功能需求:

  • 添加待办事项

  • 点击任务完成/未完成切换

  • 删除任务

目标:掌握组件、props、useState、useEffect、事件处理、本地存储保存数据(localStorage


🧱 第一步:初始化项目【动手试试才能掌握!】

✅ 如果你使用的是 命令行+VSCode,请在终端中运行:

npx create-react-app todo-app
cd todo-app
npm start

这会创建一个新的 React 项目,并在浏览器中打开开发环境。

📁 第二步:项目结构规划

我们把功能分为几个部分:

  • App.jsx:主组件
  • TodoInput.jsx:输入框组件
  • TodoList.jsx:展示任务列表
  • TodoItem.jsx:单个任务组件

🧑‍💻 第三步:开始编写代码

🔹 1. 编辑 App.jsx(主逻辑)

import React, { useState } from 'react';
import TodoInput from './components/TodoInput';
import TodoList from './components/TodoList';

function App() {
  const [todos, setTodos] = useState([]);

  const addTodo = (text) => {
    const newTodo = { id: Date.now(), text, completed: false };
    setTodos([newTodo, ...todos]);
  };

  const toggleTodo = (id) => {
    setTodos(todos.map(todo =>
      todo.id === id ? { ...todo, completed: !todo.completed } : todo
    ));
  };

  const deleteTodo = (id) => {
    setTodos(todos.filter(todo => todo.id !== id));
  };

  return (
    <div className="container">
      <h1>我的待办事项</h1>
      <TodoInput onAdd={addTodo} />
      <TodoList todos={todos} onToggle={toggleTodo} onDelete={deleteTodo} />
    </div>
  );
}

export default App;

🔹 2. 创建 components/TodoInput.jsx

import React, { useState } from 'react';

function TodoInput({ onAdd }) {
  const [text, setText] = useState('');

  const handleSubmit = (e) => {
    e.preventDefault();
    if (text.trim() === '') return;
    onAdd(text);
    setText('');
  };

  return (
    <form onSubmit={handleSubmit}>
      <input
        value={text}
        onChange={(e) => setText(e.target.value)}
        placeholder="添加任务..."
      />
      <button type="submit">添加</button>
    </form>
  );
}

export default TodoInput;

🔹 3. 创建 components/TodoList.jsx

import React from 'react';
import TodoItem from './TodoItem';

function TodoList({ todos, onToggle, onDelete }) {
  return (
    <ul>
      {todos.map(todo => (
        <TodoItem
          key={todo.id}
          todo={todo}
          onToggle={onToggle}
          onDelete={onDelete}
        />
      ))}
    </ul>
  );
}

export default TodoList;

🔹 4. 创建 components/TodoItem.jsx

import React from 'react';

function TodoItem({ todo, onToggle, onDelete }) {
  return (
    <li
      style={{
        textDecoration: todo.completed ? 'line-through' : 'none',
        cursor: 'pointer'
      }}
    >
      <span onClick={() => onToggle(todo.id)}>{todo.text}</span>
      <button onClick={() => onDelete(todo.id)}>删除</button>
    </li>
  );
}

export default TodoItem;

🎨 简单样式建议(可选)

index.css 或 App 的外层添加一点样式:

.container {
  max-width: 500px;
  margin: 50px auto;
  text-align: center;
}

input {
  padding: 10px;
  width: 70%;
  margin-right: 10px;
}

button {
  padding: 10px;
}

完成✅【npm start可以启动项目】