文本区域的下一个兄弟有什么问题?
What is wrong with the next sibling of the textarea?
当此脚本插入 HTML 文档时,会导致奇怪的行为。显示的 textarea 元素在 <br>
标签插入后丢失了它的值(我在 Chrome 42 中测试过):
var text = document.createElement("textarea");
document.body.appendChild(text);
text.value = "text";
alert("value presents");
document.body.innerHTML += "<br>"; //(*)
alert("value absents");
这是什么原因?
innerHTML
属性 是一把大锤。
通过调用 document.body.innerHTML += '<br>'
,您所做的就是从 <body>
中删除 每个 元素,并用 全新的 恰好共享相同结构的元素。
value
属性 是在原来的 <textarea>
上设置的,但全新的 value
属性 没有设置。
如果您只想追加一个 <br>
元素,请创建一个并通过 DOM api:
追加它
var br = document.createElement('br');
document.body.appendChild(br);
当您像这样使用 +=
运算符时,您在做什么:
document.body.innerHTML += "<br>";
等同于:
document.body.innerHTML = document.body.innerHTML + "<br>";
因此,您正在获取正文中的所有元素并转换为 HTML 代码,附加更多 HTML 代码,然后再次将其转换为元素。
当您获得元素的 HTML 代码时,您只会获得创建它的原始 HTML 代码,而不是当前值。文本区域内的文本被重置为创建时的状态,即在您设置 value
属性.
之前
要添加一个元素,您应该创建它并附加它。这不会破坏已经存在的元素:
var br = document.createElement("br");
document.body.appendChild(br);
那你为什么不这样做呢
document.body.appendChild(document.createElement("br"));
so there is still a security risk whenever you use innerHTML to set strings over which you have no control. For example:
var name = "<img src=x onerror=alert(1)>";
el.innerHTML = name; // shows the alert
For that reason, it is recommended you not use innerHTML when inserting plain text; instead, use node.textContent. This doesn't interpret the passed content as HTML, but instead inserts it as raw text.
改变这个:
document.body.innerHTML += "<br>";
对此:
document.body.appendChild(document.createElement("br"));
这会将单个新元素附加到 DOM,而不是用所有新元素替换 DOM 的全部内容。
当你这样做时:
document.body.innerHTML += "<br>";
相当于:
var str = document.body.innerHTML;
str += "<br>";
document.body.innerHTML = str;
因此,您正在将整个主体 DOM 变成一个 HTML 字符串,在字符串末尾添加一个东西,然后用一个新的替换整个主体 DOM HTML 的一部分将创建所有新元素。
除了这样做效率低下之外,它还会用不同的 DOM 元素替换所有 DOM 元素,因此任何 DOM 引用或事件处理程序现在都已损坏,任何动态您对 DOM 元素所做的未反映在 HTML 中的更改将会丢失。
当此脚本插入 HTML 文档时,会导致奇怪的行为。显示的 textarea 元素在 <br>
标签插入后丢失了它的值(我在 Chrome 42 中测试过):
var text = document.createElement("textarea");
document.body.appendChild(text);
text.value = "text";
alert("value presents");
document.body.innerHTML += "<br>"; //(*)
alert("value absents");
这是什么原因?
innerHTML
属性 是一把大锤。
通过调用 document.body.innerHTML += '<br>'
,您所做的就是从 <body>
中删除 每个 元素,并用 全新的 恰好共享相同结构的元素。
value
属性 是在原来的 <textarea>
上设置的,但全新的 value
属性 没有设置。
如果您只想追加一个 <br>
元素,请创建一个并通过 DOM api:
var br = document.createElement('br');
document.body.appendChild(br);
当您像这样使用 +=
运算符时,您在做什么:
document.body.innerHTML += "<br>";
等同于:
document.body.innerHTML = document.body.innerHTML + "<br>";
因此,您正在获取正文中的所有元素并转换为 HTML 代码,附加更多 HTML 代码,然后再次将其转换为元素。
当您获得元素的 HTML 代码时,您只会获得创建它的原始 HTML 代码,而不是当前值。文本区域内的文本被重置为创建时的状态,即在您设置 value
属性.
要添加一个元素,您应该创建它并附加它。这不会破坏已经存在的元素:
var br = document.createElement("br");
document.body.appendChild(br);
那你为什么不这样做呢
document.body.appendChild(document.createElement("br"));
so there is still a security risk whenever you use innerHTML to set strings over which you have no control. For example:
var name = "<img src=x onerror=alert(1)>"; el.innerHTML = name; // shows the alert
For that reason, it is recommended you not use innerHTML when inserting plain text; instead, use node.textContent. This doesn't interpret the passed content as HTML, but instead inserts it as raw text.
改变这个:
document.body.innerHTML += "<br>";
对此:
document.body.appendChild(document.createElement("br"));
这会将单个新元素附加到 DOM,而不是用所有新元素替换 DOM 的全部内容。
当你这样做时:
document.body.innerHTML += "<br>";
相当于:
var str = document.body.innerHTML;
str += "<br>";
document.body.innerHTML = str;
因此,您正在将整个主体 DOM 变成一个 HTML 字符串,在字符串末尾添加一个东西,然后用一个新的替换整个主体 DOM HTML 的一部分将创建所有新元素。
除了这样做效率低下之外,它还会用不同的 DOM 元素替换所有 DOM 元素,因此任何 DOM 引用或事件处理程序现在都已损坏,任何动态您对 DOM 元素所做的未反映在 HTML 中的更改将会丢失。