Simple To Do app
TL;DR
Similar to my simple calculator web app, a To Do app I’ve seen pop up on a lot of lists of things to build. I use Google Keep extensively for lists on a daily basis so I figured it’d be a fun thing to make. As I like Google Keep’s functionality I decided to try and mirror some of it, although I’m sure most to do list apps do a very similar thing. It’s built in HTML, CSS and vanilla Javascript of course. You can try it out below, and you check out the code on my GitHub here.
Here’s a list of functionality I included at various stages, I’ll write more about these further on if you want to read it:
- Add Item button.
- Event listeners to handle the cross button to delete To Do items and the checkboxes.
- When the user presses enter, like on Google Keep (and probably most other list apps) a new To Do item is generated and focus is moved to the new item.
- LocalStorage in the browser means the To Do items persist on page refresh. The To Do items get stringified and then parsed on page load if you’ve already written some To Do items.
- The script file loads only on this page, and it looks for a div element with the correct ID to generated the To Do list initially and then populate it with any To Do items found in LocalStorage.
There’s probably some other things I’d like to add to it if I kept working on it. Maybe a way to have multiple lists in small dashboard (as I’m writing, that actually sounds fun and a challenge). Also, the checkbox isn’t actually a checkbox so I’d change that as it’s always best to use native HTML elements where you can. I may also include a “Delete All Completed Items” button just because I’ve tried to mirror some of the functionality that Google Keep has, and perhaps some buttons to alter text such as bold and heading options perhaps as I use those in Google Keep a lot.
A bit more detail
The first build of this To Do List app started out with an HTML file that included the title, first to do item and the add item button. That gave me a place to start building the functions that handled things like the checkbox, deleting a to do item with the cross button, adding in functionality to have a new to do item populate when the user pressed enter/return, and handling the Add Item button.
Adding a new To Do item
A lot of the process of building the To Do List app felt mostly like setting event listeners and doing relatively simple things with them. For example, adding a To Do item was initially just down to the Add Item button. Then, I added an event listener for “keydown” to create a new To Do item when the user pressed enter/return. To begin with I had two separate functions for creating the new To Do item. That was a bit messy and not DRY so I rewrote it a little so I was just using one function for creating a new To Do item.
Later, when I included LocalStorage into the mix I had to rewrite my function for adding a new To Do item so it could be used when starting the app as well. Rather than a hard coded To Do item in the HTML, I wanted the script to create all the To Do items including if a to do list was found in LocalStorage. That meant using the checked status and any to do item text and inputting that into the To Do item being generated. I’ve not used template literals much in the past but this was a good opportunity to rewrite the builtToDoItem() function to use template literals; it made the code much cleaner rather than creating a bunch of different HTML elements and using appendChild() in the right order.
Challenges when enqueuing the script in this WordPress website
The first challenge I had was that the images used in the To Do app were not loading. I’d used relative paths of course in the initial build, but that meant the script was looking for the images in the wrong place. I found the wp_localize_script WordPress function, which was something I don’t think I’ve needed before, and used that to pass the correct theme name to the script where it could be used. I didn’t want my To Do app to stop working correctly when loading the local HTML file; initially, every time I wanted to set the source for an image I was checking if the path had been passed from WordPress. That meant a lot more code but I ended writing a helper function I could use each time called getAssetPath() which I could pass the relative path to I’d been using initially. That function just checks if we have the theme path passed from WordPress and plugs it in or just returns the original relative path if I happened to be loading the To Do App on the local HTML file.
The other main challenge I faced was the buildToDoItem() not running at all on page load. From reading, this probably was due to timing and possibly by the time I was setting the event listener “DOMContentLoaded”, the content was already loaded and wasn’t triggering. What solved it was checking the readyState and assigning the event listener if the readyState was “loading”, else just to run the initApp() wrapper function that gets things going.
Using LocalStorage
I’ve never used LocalStorage before; I’ve never really had the need to. I’m not 100% sure I would need to again as any commercial project would most likely use a database for storage rather than relying on the browser’s storage. But that’s the point; creating a little web app and learning some things on the way. It was relatively straight forward with the usual problem solving along the way. For example, to begin with I wanted to have each item stored as it’s own key value pair in the LocalStorage. The issue there was how to create the keys reliably that could then be called upon to populate the To Do List when the page loaded. After a bit of reading, I realised something that I’d probably dealt with years ago on other projects as I’ve used JSON.stringify() before; it’s better to store one key value pair as an array of to do items. That made parsing it much easier as you can just loop through after running JSON.parse().
In conclusion
There’s a whole bunch of things I’ve learned along the way with this. Things I knew before and I’ve rediscovered. Things I’ve not used before or very little and feel much more confident with now. I won’t list all the little problems I’ve solved along the way; most of them by using console.log() to see if certain things were firing or if the data I that was assigned to a variable was actually what I was expecting.
There’s a few things I’d change, or perhaps will add in future. Mainly, I don’t like that I’ve used an image inside a button for the checkbox instead of just using a checkbox. I’d also use template literals for the buildToDoContainer() function as that would clean up the code like it did for buildToDoItem(). I’d like to add functionality for multiple lists, clicking into each one to bring it up in full. Also, some more CSS transitions/better movement for adding items and maybe even a way to reorder items within the list. Overall though it’s been a really fun little project and one I’ll probably continue to tinker with.