我试图设置事件监听器,但只有在setTimeout中设置它们才能正常工作。
不能工作:
WebApp.setController('jobs', function() {
WebApp.setView('header', 'header');
WebApp.setView('nav', 'nav');
WebApp.setView('jobs', 'main');
var jobs = document.querySelectorAll('.jobs-category');
for(let i = 0; i < jobs.length; i++)
{
console.log('events added');
jobs[i].addEventListener("dragover", function( event ) {
console.log('drag over');
event.preventDefault();
});
jobs[i].addEventListener('drop', function(event) {
event.preventDefault();
console.log('dropped');
}, false);
}
});
工作:
WebApp.setController('jobs', function() {
WebApp.setView('header', 'header');
WebApp.setView('nav', 'nav');
WebApp.setView('jobs', 'main');
window.setTimeout(function() {
var jobs = document.querySelectorAll('.jobs-category');
for(let i = 0; i < jobs.length; i++)
{
console.log('events added');
jobs[i].addEventListener("dragover", function( event ) {
console.log('drag over');
event.preventDefault();
});
jobs[i].addEventListener('drop', function(event) {
event.preventDefault();
console.log('dropped');
}, false);
}
}, 1);
});
(只有setTimout不同/另外)
setController()保存函数并在请求路由时执行它。
setView()将HTML5模板绑定到DOM:
var Template = document.querySelector('#' + Name);
var Clone = document.importNode(Template.content, true);
var CloneElement = document.createElement('div');
CloneElement.appendChild(Clone);
CloneElement = this.replacePlaceholders(CloneElement);
document.querySelector(Element).innerHTML = CloneElement.innerHTML;
为什么这只能在setTimeout中使用?我认为javascript是同步的。
添加:这是一个单页应用,在DOM准备好后就已经加载了。
答案 0 :(得分:0)
document.addEventListener("DOMContentLoaded", function(event) {
//do work
});
您最有可能在html内容之前加载JS文件。在DOM准备就绪之前,您无法运行Javascript函数。
答案 1 :(得分:0)
页面中的Javascript在哪里?
我的猜测是,当您尝试注册该事件时,HTML还没有准备好,这就是为什么它只适用于setTimeout
。
尝试在页面底部(HTML之后)包含您的javascript或者收听页面加载事件。有关如何执行此操作的信息,请参阅此问题 - $(document).ready equivalent without jQuery。
根据您对同步javascript的假设 - 是的(主要是)它也是浏览器呈现页面的方式(除非使用async
加载脚本)。这意味着javascript之后的HTML将无法使用。
更新 - 根据您对使用单页应用的评论,您必须收听加载完成/完成/成功事件。另一种绕过它的方法是监听父元素上的事件(总是在那里)。
希望这有帮助。