问题描述
HTML:
<div id="root">
<form class="todoForm">
<input class="input" placeholder="What do you need to do?" />
</form>
<div class="todos"></div>
<div class="footer">
<button class="All">All</button>
<button class="All">Active</button>
<button class="All">Completed</button>
</div>
</div>
CSS:
.todoForm {
margin-bottom: 20px;
}
.todos {
margin-bottom: 20px;
}
.todo {
margin-bottom: 10px;
}
.todoAndCheckBox {
display: flex
}
.checkBox {
border-radius: 50%;
outline: green;
}
JS:
class displayTodos {
constructor(root) {
this.root = root;
this.input = this.root.querySelector('.input');
this.form = this.root.querySelector('.todoForm');
// why does it work with keydown but not keyup
this.form.addEventListener('keydown',this.submitForm);
this.todos = this.root.querySelector('.todos');
this.state = {
todos: [
{
id: Math.random * 10000,text: 'Pie'
},{
id: Math.random * 10000,text: 'Soy milk'
}
]
}
this.display();
}
submitForm = (e) => {
if(e.key === 'Enter') {
e.preventDefault();
const typed = this.input.value;
const newTodo = {
id: Math.random * 10000,text: typed
}
const newTodos = [...this.state.todos,newTodo];
this.state.todos = newTodos;
this.display();
this.input.value = ''
}
}
display = () => {
while(this.todos.firstChild) {
this.todos.removeChild(this.todos.firstChild)
}
this.state.todos.forEach(todo => {
const todoAndCheckBox = document.createElement('div');
const todoDiv = document.createElement('div');
todoAndCheckBox.classList.add('todoAndCheckBox');
todoDiv.innerText = todo.text;
const checkBox = document.createElement('input');
checkBox.setAttribute('type','checkBox');
checkBox.classList.add('checkBox');
this.todos.appendChild(todoAndCheckBox);
todoAndCheckBox.appendChild(checkBox);
todoAndCheckBox.appendChild(todoDiv);
todoAndCheckBox.classList.add('todo')
})
}
}
const root = document.querySelector('#root');
const instance = new displayTodos(root);
在这一行:
this.form.addEventListener('keydown',this.submitForm);
我注意到,如果我将 keydown
更改为 keyup
或 keypress
,当我按下 Enter 键时,即使我有 e.preventDefault
,整个页面也会刷新。
我的问题是:
- 为什么页面/表单会以
e.preventDefault
刷新? - 为什么只有
keydown
有效(意味着它停止刷新表单),而不是keyup
或keypress
?
解决方法
提交表单事件已经被keydown触发了,如果你在keyup上使用e.preventDefault,那就太晚了。 您应该更改代码以绑定到 keydown 和 keyup。在 keydown 函数上,您可以调用 e.preventDefault(),在 keyup 函数上,您可以执行其他逻辑。
替代:
您可以使用此代码完全禁用表单提交:
<form onsubmit="return false;">
然后在您真正希望它发生时手动触发表单提交:
document.forms[0].submit();
以上假设您只有一个表单 - 如果您现在或将来有多个表单,您可能想要使用 css 选择器:
document.querySelector("#formid").submit();
另请注意,提交按钮将不再起作用,因此您需要将事件与其点击事件挂钩,以通过相同的代码提交。