I'm currently working on a to do list project using React and Typescript. Right now I am able to add a new to do item using a form and delete each to do item. Each to do item has a checkbox with a boolean value. What I would like to do is filter each to do item as "Done" when I click on the checkbox.
I have a Done (const DoneTasks) button on my page. Once it is clicked a copy of my App appears. Within the html components I want all my checked to do items to be stored on this page and filter out of the default App page.
I believe I have to useMemo for checked value, but I am not sure where to use it?
CODE SANDBOX: https://codesandbox.io/s/to-do-list-mkr29l
App.tsx
To Do Item Interface
interface ToDo {
title: string;
priority: 1 | 2;
description: string;
checked: true | false;
}
To Do Item function with checkbox prop
function ToDoItem(props: {
onCheckBoxCheck: any;})
{const checkBoxCheck = (event: any) => {
const checkBox = event.currentTarget.checked;
const newCheckBoxValue = checkBox;
console.log(checkBox);
props.onCheckBoxCheck(newCheckBoxValue);
};
return (
<div
className="to-do-item"
data-priority={props.toDo.priority}
id="to-do-item">
<div className="checkbox-title-container">
<div className="check-title-div">
<div>
<input
type="checkbox"
id="checkbox"
onChange={checkBoxCheck}
checked={props.toDo.checked}
/>
</div>
</div>
);
}
const initialTodosString = localStorage.getItem("toDoList");
const initialTodos = initialTodosString
? JSON.parse(initialTodosString)
: [myToDo1, myToDo2];
App function with hooks, I think I should add useMemo in here?
function App(): JSX.Element {
const [toDos, setToDos] = useState<ToDo[]>(initialTodos);
const [addingToDo, setAddingToDo] = useState(false);
const [showingDoneTasks, setShowDoneTasks] = useState(false);
// Do I add useMemo here for checked value?
useEffect(
function () {
localStorage.setItem("toDoList", JSON.stringify(toDos));
},
[toDos]
);
showDone function
function showDone()
{setShowDoneTasks(true)}
//Done tasks function that returns html elements (I have included buttons in here)
const DoneTasks = () => (
</div>
<div className="status-container">
<button className="activeButton">Active</button>
<button className="doneButton" onClick={showDone}>Done
</button>
</div>
</div>
);
if(showingDoneTasks){
return <DoneTasks />
};
App components (I kept buttons with To Do items and checkbox function below)
return (
<div className="App">
<div className="status-container">
<button className="activeButton">Active</button>
<button className="doneButton" onClick={showDone}>Done
</button>
</div>
</div>
{toDos.map((toDoItem: ToDo) => (
<ToDoItem
onDeleteToDo={function () {
const updatedToDos = toDos.filter((x) => x !== toDoItem);
setToDos(updatedToDos);
}}
onCheckBoxCheck={function(checked: true | false) {
const updatedToDos = toDos.map((x) =>
x === toDoItem ? ({ ...x, checked } as any) : x,
);
setToDos(updatedToDos);}}
It's hard to read the code above, but you created multiple states/components to track down the filtered todos.
Regarding your question about memos, you're right; that's where you need to add the memo since it's the parent component that "holds" your todos state.
But, I would like to add some points to your implementation and make it more readable and easy to manage. Others may have different opinions, but I want to share my thoughts.
Process:
Create a "todos" state that manages the display of the Todo items. You can filter the display based on statuses like "done" or "not done."
Create a
useRefthat holds the initial state of the todos. This will be used to display if no status filter is made. This also helps prevent the component from being re-render when modified. Of course, you can use the useEffect when the .ref as a dependency when you want to save the updated the todos value.Please let me know if it still needs to be clarified. I'd be happy to help.
Take note:
useMemountil you notice that you need to.useMemois used for expensive computation. Still, it's not expensive in your case.useMemoalso has some performance issues. So, use this with caution.Reference: https://kentcdodds.com/blog/usememo-and-usecallback