Task Manager
Learn Python, JavaScript, Java and more with free interactive lessons, real projects and a built-in help dictionary. Beginner-friendly.
Part of the free JavaScript course at LearnCodingFast — hands-on lessons with examples you run in your browser, plus practice exercises and a quick quiz.
Intermediate-Advanced Project — Master DOM, Events, localStorage & OOP
🧠 Deep Project Overview
A Task Manager looks simple, but it secretly trains you on 95% of what front-end devs do every day:
- • Reading user input
- • Updating the DOM based on app state
- • Saving data so it survives page refreshes
- • Organizing logic in classes instead of spaghetti code
- • Handling edge cases (empty tasks, filters, invalid input)
Apps like Todoist, Microsoft To Do, ClickUp, Trello all start from this same idea: a list of items with state (done/not done, priority, tags, etc.). If you can build this project cleanly, you're already thinking like a real JS dev.
🧱 Step 1 – Understand the Structure
1. Input Area (.input-group)
- • Text box for task title
- • <select> for priority (low, medium, high)
- • "Add Task" button that calls addTask()
2. Filter Bar (.filters)
- • 4 filter buttons: All, Active, Completed, High Priority
- • They call filterTasks('...')
3. Task List (#taskList)
- • An empty <ul> where JavaScript injects <li> items
💡 Tip: When you build other projects (Notes app, Budget tracker, Habit tracker), reuse this same 3-zone layout: inputs → controls/filters → results list .
🧠 Step 2 – The Brain: TaskManager Class
- • tasks: an array of all task objects
- • currentFilter: which view is active (all, active, completed, high)
That's already proper data modeling – which is what you'll do with databases later.
💾 Step 3 – Saving and Loading with localStorage
localStorage only stores strings, so you convert:
- • Save → JSON.stringify(this.tasks)
- • Load → JSON.parse(saved)
If the app acts weird, open DevTools → Application tab → Local Storage → clear the 'tasks' key, then refresh.
This pattern (load → modify → save) is identical for: Notes apps, Shopping carts, Watch-later lists, "Recent code snippets" feature
➕ Step 4 – Adding Tasks
- • Input validation – don't accept empty strings
- • Unique IDs – Date.now() is an easy, unique-enough ID for small apps
- • Unshift vs push – unshift() puts new tasks at the top of the list
- • Refresh UI – every change calls saveTasks() then render()
- • Limit task length (e.g. max 120 characters) and show a little warning
- • Store a dueDate property
- • Store isStarred: true/false for favourites
✅ Step 5 – Completing and Deleting Tasks
- • find() to get one item from an array
- • filter() to remove items by creating a new array
- • Always treat the array like state → modify → save → re-render
- • Show confirm("Are you sure?") before deleting
- • Or add a "Trash" filter where deleted tasks go instead of fully disappearing
🔍 Step 6 – Filters and UI State
- • Keeping one source of truth: currentFilter
- • Styling the active button with a CSS class
- • Using .filter() to generate the current view
Instead of using onclick in HTML, you could attach event listeners in JS and use e.target directly. This is called event delegation – super useful for dynamic content.
🖼️ Step 7 – Rendering HTML from Data
- • Template literals for clean HTML
- • Using dynamic classes (completed, priority-high, etc.)
- • One .innerHTML = ... per render → avoids many DOM mutations
- 1. console.log(filtered) before you map
- 2. Check for JS errors in DevTools console
- 3. Make sure id="taskList" exists in the HTML
⌨️ Step 8 – Global Functions & Keyboard UX
This is already nice UX – users can quickly hit Enter instead of clicking.
- • Disable the Add button when input is empty
- • Focus the text input on page load
💻 Try It Yourself
Test the complete Task Manager app below. Study the code, modify it, and experiment with the features!
🧪 What to Practice / Extend
Here's how to use this project to become scary-good at JavaScript:
1. Add due dates
- • Add an <input type="date">
- • Store dueDate in the task object
- • Sort by dueDate in render() or create a "Due soon" filter
2. Inline editing
- • On click of task text, turn it into an <input>
- • On blur / Enter, update task.text, save, re-render
3. Search bar
- • Add <input id="search">
- • On input event, filter by both currentFilter + search query
4. Animations
- • Use CSS transitions on .task-item (opacity, transform)
- • Add a quick fade-in class when a task is created
5. Dark Mode
- • Toggle data-theme="dark" on <body>
- • Use CSS variables for colours and swap them per theme
🧾 Final Checklist for "Job-Ready" Level
- ☐ No errors in DevTools console
- ☐ Works on mobile (try Chrome's responsive mode)
- ☐ Handles 100+ tasks without feeling laggy
- ☐ All filters work correctly
- ☐ Data survives refresh and browser close
- ☐ Code is split into logical methods, not one giant function
- ☐ Important parts have comments explaining why, not just what