如何保存动态创建表单的值?Todo App遇Null读取错误
解决动态编辑输入框的null错误与值保存问题
错误根源
- 页面初始化时,
edit-input元素还没通过renderTodos()动态生成,所以const newInput = document.querySelector('.edit-input ');获取到的是null,后续尝试给null绑定事件就会抛出“无法读取null的值”的错误。 - 你错误地给
<input>元素绑定了submit事件——submit是表单专属事件,输入框本身没有这个事件。
修复步骤
1. 清理无效代码
- 删除代码开头的
const newInput = document.querySelector('.edit-input '); - 删除
document.body.addEventListener('click')里这段无效逻辑:
if (el.classList.contains('edit-input')) { newInput.addEventListener('submit', (e) => { ev.preventDefault(); saveTodo(); }); }
2. 修正编辑功能的事件逻辑
你已经通过回车事件处理了保存,但可以补充焦点丢失时自动保存的逻辑,同时统一事件委托:
// 回车保存(保留原有逻辑并修正参数) document.body.addEventListener('keyup', (ev) => { const el = ev.target; if (el.classList.contains('edit-input') && ev.keyCode === 13) { todos[el.parentNode.id].value = el.value; localStorage.setItem('todos', JSON.stringify(todos)); renderTodos(); } }); // 新增:失去焦点时自动保存 document.body.addEventListener('blur', (ev) => { const el = ev.target; if (el.classList.contains('edit-input')) { todos[el.parentNode.id].value = el.value; localStorage.setItem('todos', JSON.stringify(todos)); renderTodos(); } }, true);
3. 修复其他潜在问题
- 修正渲染时的语法错误:
renderTodos()里的<p>标签class属性写法有误,改成:
<p class="text ${todo.checked ? LINE_THROUGH : ''}" data-action="check">${todo.value}</p>
- 统一删除逻辑:原代码删除功能分散,新增专门的删除函数并绑定到事件委托:
function deleteTodo(todoId) { todos = todos.filter((_, index) => index !== todoId); localStorage.setItem('todos', JSON.stringify(todos)); renderTodos(); } // 修正list的click事件处理 list.addEventListener('click', (event) => { const { target } = event; const parentElement = target.parentNode; if (parentElement.className !== 'todo') return; const todo = parentElement; const todoId = Number(todo.id); const { action } = target.dataset; action === 'check' && checkTodo(todoId); action === 'delete' && deleteTodo(todoId); }); // 移除document.body click事件里的删除逻辑,保留编辑切换即可 document.body.addEventListener('click', (ev) => { const el = ev.target; if (el.classList.contains('edit-task')) { const parent = el.parentNode; parent.querySelector('.trash-btnn').classList.toggle('hidden'); parent.querySelector('.fa-ellipsis-v').classList.toggle('hidden'); parent.querySelector('.text').classList.toggle('hidden'); parent.querySelector('.edit-input').classList.toggle('hidden'); } });
内容的提问来源于stack exchange,提问作者David630
相关产品推荐
相关产品推荐

