先看效果图
一 添加
let [todo,setTodo] = useState('')
let [todos,setTodos] = useState(todoList)
// 输入框事件
const addtodo=useCallback(()=>{
setisDown(false)
if(todo){
// value是值 isDown是否完成
setTodos([...todos,{value:todo,isDown:false}])
}
setTodo('')
},[todo])
// 键盘回车
const keyDown=(e)=>{
if(e.keyCode===13){
addtodo(e.target.value)
}
}
<div className="app">
<div className="app-header">
<img src={note} className="app-logo" alt="logo" />
<p>To-Do List</p>
</div>
<h1>~ Today I need to ~</h1>
<div className="app-input">
<input placeholder="添加待办事项" onKeyDown={(e)=>{keyDown(e)}} value={todo} onChange={(e)=>{ setTodo(e.target.value)}} />
<button className={isDown ? "down" : "up"} onMouseDown={()=>{setisDown(true)}} onMouseUp={addtodo}><span>添加</span></button>
</div>
)
二、渲染
<ul className="app-list">
{
todos.map((item,index)=>{
return <li key={index} className={item.isDone ? "done" : ""}>
<div className="checkbox" onClick={() => toggleCheck(index)}>
<img
style={{ display: item.isDone ? "block" : "none" }}
src={checkedImg}
alt="check"
/>
</div>
<span>{item.value} </span>
<button onClick={()=>{removeList(index)}}>x</button>
</li>
})
}
</ul>
三、删除
// 删除某个事项
const removeList = useCallback((i)=>{
todos.splice(i,1)
setTodos([...todos])
})
四、已完成
// 切换是否完成
const toggleCheck = useCallback((i)=>{
todos[i].isDone = !todos[i].isDone
setTodos([...todos ])
})
统计完成和未完成
// 计算完成的
let done = useMemo(()=>{
let doneList=[]
todos.forEach(item=>{
if(item.isDone){
doneList.push(item)
}
})
return doneList.length
},[todos])
// 未完成 noDone
let noDone = useMemo(()=>{
let doneList=[]
todos.forEach(item=>{
if(!item.isDone){
doneList.push(item)
}
})
return doneList.length
},[todos])
// 删除全部已完成
const remove = useCallback(()=>{
todos.forEach((item,index)=>{
if(item.isDone){
todos.splice(index,done)
setTodos([...todos])
}
})
})
<div className="Statistics">
<span>任务事项:{todos.length} </span>
<span>已完任务事项: {done}</span>
<span>待办任务事项: {noDone}</span>
<span onClick={remove}>清空已完成</span>
</div>
源码
https://gitee.com/hewweibo_admin/react-todolist