晚安stackoverflow。
我遇到了一个Javascript代码段的问题,它在JSFiddle中有效但在实际HTML上无效。
我有一个关于为什么它不起作用的要点,当调用以下行时:
while (list.firstChild) {
在那个时间点,list的值仍为null。所以它可能会在此时崩溃并烧毁。
然而,为什么它在小提琴中起作用?
我知道我可以通过在列表前面添加一个项目来解决这个问题,以避免使其变为空,但是,我更好奇为什么会出现差异(jsfiddle和html如何不同)以及如何将继续恢复jsfiddle功能。
这项工作的小提琴
我的Test.html无效
<script>
var list = document.getElementById('deliveryIdArray');
var names = [];
window.changeText2 = function() {
var deliveryIdentification = document.getElementById('deliveryIdentification').value;
names.push(deliveryIdentification);//simply add new name to array;
//array changed re-render list
renderList();
}
window.renderList = function(){
while (list.firstChild) {
list.removeChild(list.firstChild);
}
//create each li again
for(var i=0;i<names.length;i++){
var entry = document.createElement('li');
entry.appendChild(document.createTextNode(names[i]));
var removeButton = document.createElement('button');
removeButton.appendChild(document.createTextNode("X"));
removeButton.setAttribute('onClick','removeName('+i+')');
entry.appendChild(removeButton);
list.appendChild(entry);
}
}
window.removeName = function(nameindex){
names.splice(nameindex,1);
//array changed re-render list
renderList();
}
window.getDeliveries = function(){
return names;
}
</script>
<html>
<body>
<b>Number </b>
<input id = "deliveryIdentification" name = "deliveryIdentification" type = "text" size = "16" maxlength = "30">
<!-- Array Area Creation -->
<input type='button' onclick='changeText2()' value='Add' />
<ol id="deliveryIdArray">
</ol>
</body>
</html>
非常感谢任何和所有的帮助,祝你有个美好的夜晚!
答案 0 :(得分:1)
你的HTML格式不好。你也可以在最后编写javascript代码,或者你需要window.onLoad
函数来确保加载document
。
<html>
<body>
<b>Number </b>
<input id = "deliveryIdentification" name = "deliveryIdentification" type = "text" size = "16" maxlength = "30">
<!-- Array Area Creation -->
<input type='button' onclick='changeText2()' value='Add' />
<ol id="deliveryIdArray">
</ol>
</body>
<script>
var list = document.getElementById('deliveryIdArray');
var names = [];
window.changeText2 = function() {
var deliveryIdentification = document.getElementById('deliveryIdentification').value;
names.push(deliveryIdentification);//simply add new name to array;
//array changed re-render list
renderList();
}
window.renderList = function(){
while (list.firstChild) {
list.removeChild(list.firstChild);
}
//create each li again
for(var i=0;i<names.length;i++){
var entry = document.createElement('li');
entry.appendChild(document.createTextNode(names[i]));
var removeButton = document.createElement('button');
removeButton.appendChild(document.createTextNode("X"));
removeButton.setAttribute('onClick','removeName('+i+')');
entry.appendChild(removeButton);
list.appendChild(entry);
}
}
window.removeName = function(nameindex){
names.splice(nameindex,1);
//array changed re-render list
renderList();
}
window.getDeliveries = function(){
return names;
}
</script>
</html>
或者您可以在加载document
时注册处理程序事件:
<html>
<head>
<meta charset="utf-8">
<script>
document.addEventListener("DOMContentLoaded", init);
function init(){
var list = document.getElementById('deliveryIdArray');
var names = [];
window.changeText2 = function() {
var deliveryIdentification = document.getElementById('deliveryIdentification').value;
names.push(deliveryIdentification);//simply add new name to array;
//array changed re-render list
renderList();
}
window.renderList = function(){
while (list.firstChild) {
list.removeChild(list.firstChild);
}
//create each li again
for(var i=0;i<names.length;i++){
var entry = document.createElement('li');
entry.appendChild(document.createTextNode(names[i]));
var removeButton = document.createElement('button');
removeButton.appendChild(document.createTextNode("X"));
removeButton.setAttribute('onClick','removeName('+i+')');
entry.appendChild(removeButton);
list.appendChild(entry);
}
}
window.removeName = function(nameindex){
names.splice(nameindex,1);
//array changed re-render list
renderList();
}
window.getDeliveries = function(){
return names;
}
};
</script>
</head>
<body>
<b>Number </b>
<input id = "deliveryIdentification" name = "deliveryIdentification" type = "text" size = "16" maxlength = "30">
<!-- Array Area Creation -->
<input type='button' onclick='changeText2()' value='Add' />
<ol id="deliveryIdArray">
</ol>
</body>
</html>
答案 1 :(得分:1)
如果您查看JSFiddle页面的左侧,您会看到第二个下拉列表设置为&#34; onLoad&#34;。
这意味着在onload事件被触发之前你的JavaScript没有执行。
但是,当您将其作为HTML页面包含时,JavaScript会立即执行。这会中断,因为DOM没有准备好,因此你的getElement函数不会返回你期望的值。
您可以通过将下拉列表的值更改为&#34;无包装头&#34;来重现JsFiddle中的问题。并重新运行。
已经有great answers关于如何连接DOM以便在DOM加载后运行。
您还可以使用文档就绪事件而不是onload事件(等待加载图像之类的事件)。优点是您的JavaScipt可能会更快执行。
答案 2 :(得分:1)
有一个脚本错误:
Unable to get value of the property 'firstChild': object is null or undefined
将您的列表放在window.renderList
函数中,它将解决问题。
window.renderList = function(){
var list = document.getElementById('deliveryIdArray');
while (list.firstChild) {
list.removeChild(list.firstChild);
}
//create each li again
for(var i=0;i<names.length;i++){
var entry = document.createElement('li');
entry.appendChild(document.createTextNode(names[i]));
var removeButton = document.createElement('button');
removeButton.appendChild(document.createTextNode("X"));
removeButton.setAttribute('onClick','removeName('+i+')');
entry.appendChild(removeButton);
list.appendChild(entry);
}
}
答案 3 :(得分:1)
这是一个有趣的问题,
虽然这是我第一次看到人们把脚本标签输出html标签。
我的案例中的Web浏览器引擎(webkit)从上到下呈现html,
目前,脚本引擎执行var list = document.getElementById('deliveryIdArray');
dom元素deliveryIdArray dom树中不存在,因此,它无法找到元件。
将脚本标记放在文件底部后,您可以看到样本快乐地运行。
这就是为什么在js idiom中,人们喜欢将js放在html文件的底部, 或者您需要在DOMContentLoad事件中连接处理程序或使用jquery方式$(function(){});