Welcome to the Treehouse Community
Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.
Looking to learn something new?
Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.
Start your free trialMatthew Cahn
6,301 PointsNew tasks don't bind properly. What's wrong?
New tasks get added to the todo list but the checkbox, edit, and delete buttons don't work.
I get the following errors:
Uncaught TypeError: Cannot set property 'onclick' of null app.js:115
bindTaskEvents app.js:115
addTask app.js:60
Here's the code:
Line 60:
bindTaskEvents(listItem, taskComplete);
Line 115:
editButton.onclick = editTask;
Matthew Cahn
6,301 PointsHere's all my code:
// Problem: User interaction doesn't provide desired results
// Solution: add interactivity so the user can manage daily tasks
var taskInput = document.getElementById("new-task"); //new-task
var addButton = document.getElementsByTagName("button")[0]; //first button
var incompleteTaskHolder = document.getElementById("incomplete-tasks"); //incomplete-tasks
var completedTasksHolder = document.getElementById("completed-tasks"); //completed-tasks
//New Task List Item
var createNewTaskElement = function(taskString) {
//Create list item
var listItem = document.createElement("li");
//Checkbox input
var checkBox = document.createElement("input"); //checkbox
//Label
var label = document.createElement("label");
//Input (text)
var editInput = document.createElement("input"); //text
//Button.edit
var editButton = document.createElement("button");
//Button.delete
var deleteButton = document.createElement("button");
//Each element needs modifying
checkBox.type = "checkbox";
editInput.type = "text";
editButton.innerText = "Edit";
editButton.className = "Edit";
deleteButton.innerText = "Delete";
deleteButton.className = "Delete";
label.innerText = taskString;
//Each element needs appending
listItem.appendChild(checkBox);
listItem.appendChild(label);
listItem.appendChild(editInput);
listItem.appendChild(editButton);
listItem.appendChild(deleteButton);
return listItem;
}
// Add a new task
var addTask = function () {
console.log("Add task...");
//Create a new li with the text from #new-task
var listItem = createNewTaskElement(taskInput.value);
//Append list item to incompleteTaskHolder
incompleteTaskHolder.appendChild(listItem);
bindTaskEvents(listItem, taskCompleted);
taskInput.value = "";
}
// Edit an existing task
var editTask = function () {
console.log("edit task...");
var listItem = this.parentNode;
var editInput = listItem.querySelector("input[type=text");
var label = listItem.querySelector("label");
var containsClass = listItem.classList.contains("editMode");
//if class of parent is .edit
if(containsClass){
//switch from .editMode
//Label text becomes inputs value
label.innerText = editInput.value;
} else {
//Switch to .editMode
//input value becomes labels text
editInput.value = label.innerText;
}
//Toggle .editMode on list item
listItem.classList.toggle("editMode");
}
// Delete an existing task
var deleteTask = function () {
console.log("Delete task...");
var listItem = this.parentNode;
var ul = listItem.parentNode;
// Remove parent li from ul
ul.removeChild(listItem);
}
// Mark a task as complete
var taskCompleted = function () {
console.log("Complete task...");
//Append task li to #completed-tasks
var listItem = this.parentNode;
completedTasksHolder.appendChild(listItem);
bindTaskEvents(listItem, taskIncomplete);
}
// Mark task as incomplete
var taskIncomplete = function () {
console.log("Incomplete task...");
//Append task li to #uncompleted-tasks
var listItem = this.parentNode;
incompleteTaskHolder.appendChild(listItem);
bindTaskEvents(listItem, taskCompleted);
}
var bindTaskEvents = function (taskListItem, checkBoxEventHandler) {
console.log("Bind list item events");
//select taskListItems children
var checkBox = taskListItem.querySelector("input[type='checkbox']");
var editButton = taskListItem.querySelector("button.edit");
var deleteButton = taskListItem.querySelector("button.delete");
//bind editTask to edit button
editButton.onclick = editTask;
//bind deleteTask to delete button
deleteButton.onclick = deleteTask;
//bind checkBoxEventHandler to checkbox
checkBox.onchange = checkBoxEventHandler;
}
var ajaxRequest = function() {
console.log("AJAX request");
}
//Set click handler to addTask button
addButton.addEventListener("click", ajaxRequest);
addButton.addEventListener("click", addTask);
//cycle over incompleteTasksHolder ul list items
for(var i = 0; i < incompleteTaskHolder.children.length; i++){
//bind events to list item's children (taskCompleted)
bindTaskEvents(incompleteTaskHolder.children[i], taskCompleted);
}
//cycle over incompleteTasksHolder ul list items
for(var i = 0; i < completedTasksHolder.children.length; i++){
//bind events to list item's children (taskIncomplete)
bindTaskEvents(completedTasksHolder.children[i], taskIncomplete);
}
2 Answers
wuworkshop
3,429 PointsI'm going to assume you're only checking in Chrome. I noticed the Teacher's Notes in that course you're referring to mentions some IE and FF cross-browser code that would need to be added if you want cross-browser compatibility.
I compared your JS to the project files for the course and figured out why you're getting that error. You have the wrong className
for the editButton
and deleteButton
variables. You have this:
editButton.innerText = "Edit";
editButton.className = "Edit";
deleteButton.innerText = "Delete";
deleteButton.className = "Delete";
But it should be this:
editButton.innerText = "Edit";
editButton.className = "edit";
deleteButton.innerText = "Delete";
deleteButton.className = "delete";
Your classes are lowercase in your HTML so you need to match it. That should fix your Chrome errors.
Matthew Cahn
6,301 PointsWow, that fixed everything! Thanks!
wuworkshop
3,429 Pointswuworkshop
3,429 PointsCould you show all your HTML and JavaScript code? Or perhaps put it in a Workspace and share the preview link? Or use JS Bin or something similar.