5 - Deleting Notes
5.1 Delete Button

Delete Button

We'll create the delete button as it's own component which will handle all of the delete functionality for us. This component will wrap around the <Trash/> icon and will listen for click events.

Delete Component

This component will need to update our notes state as we delete notes, so let's ensure we can access the noteId and setNotes method when called by passing these down as props.

Before we handle any database updates, let's simply test this by filtering out the selected note from or state, so we can see that our UI updates correctly.

DeleteButton.jsx
import Trash from "../icons/Trash";
import { db } from "../appwrite/databases";
 
const DeleteButton = ({ noteId, setNotes }) => {
 
    const handleDelete = async (e) => {
        setNotes((prevState) =>
            prevState.filter((note) => note.$id !== noteId)
        );
    };
 
    return (
        <div onClick={handleDelete}>
            <Trash />
        </div>
    );
};

Replace the <Trash/> icon inside of the <NoteCard/> header with the new <DeleteButton/> and be sure to pass in the correct props.

NoteCard.jsx
<div
    className="card-header"
    //..
    >
    <DeleteButton noteId={note.$id} setNotes={setNotes} />
 

Ignoring mouse down events

When clicking the delete button we have an interesting situation where we are triggering two events at the same time.

As we click the delete button, we are not only firing off a click event, but a mousedown event as well, which inevitably triggers the mouseup event. This happens becauase the event bubbles out to it's parent components, therefore causing error messages in our console as we are sending a update request to our backend after a note has been deleted.

To stop the mousedown event from firing when we a user clicks on the delete button, we'll add a condition inside of our mouse down event which will check which element was clicked. If the elemnt was indead the card header, we will proceed. If not, we will ignore the event, preventing an update call from being sent on a deleted note.

We will find the class name and only continue mouse down if the target className is card-header

const mouseDown = (e) => {
    if (e.target.className === "card-header") {
 
        setZIndex(cardRef.current);
 
        mouseStartPos.x = e.clientX;
        mouseStartPos.y = e.clientY;
 
        document.addEventListener("mousemove", mouseMove);
        document.addEventListener("mouseup", mouseUp);
    }
};
 
 

Updating database

Now that we've taken care of updating our local state and ignoring certain events, we can officially update our database by deleting the selected note in the delete component.

const DeleteButton = ({ noteId, setNotes }) => {
 
    const handleDelete = async (e) => {
        db.notes.delete(noteId);
        setNotes((prevState) =>
            prevState.filter((note) => note.$id !== noteId)
        );
    };