细述textContent 与 innerText、innerHTML 的区别

Node.textContent 属性表示一个节点及其后代的文本内容。

1. 语法

let text = element.textContent;
element.textContent = "some text";

2. 描述

  • 如果 element 是 Document,DocumentType 或者 Notation 类型节点,则 textContent 返回 null。如果你要获取整个文档的文本以及CDATA数据,可以使用 document.documentElement.textContent。
  • 如果节点是个CDATA片段,注释,ProcessingInstruction节点或一个文本节点,textContent 返回节点内部的文本内容(即 nodeValue)。
  • 对于其他节点类型,textContent 将所有子节点的 textContent 合并后返回,除了注释、ProcessingInstruction节点。如果该节点没有子节点的话,返回一个空字符串。
  • 在节点上设置 textContent 属性的话,会删除它的所有子节点,并替换为一个具有给定值的文本节点。

3. 与innerText的区别

Internet Explorer 引入了 node.innerText。innerText不是HTML的一个属性,而是浏览器自己实现的,所以不同的浏览器之间是有区别的,所以说如果想使用这个属性,最好先进行一下判断,

typeof textContent === 'string'

若结果等于string,则说明浏览器支持textContent;
若不等于string,说明浏览器不支持textContent,只需要使用innerText即可。

但就此引出一个问题,为何我们先判断textContent,而不是先按断innerText呢,也就是说,若浏览器同时支持textContent和innerText,我们会优先使用textContent。

为何要这样呢?

innerText与textContent意图类似,但有以下区别:

  1. textContent 会获取所有元素的内容,包括 <script><style> 元素,然而 innerText 不会包含。
  2. innerText的返回值依赖于页面的显示(你在页面中看到的),而textContent依赖于代码的内容
    比如有以下内容
<div>
  outer
  <span style="display: none"></span>		// visibility: hidden
</div>

这个span标签不会在页面中显示,那么innerText不会返回隐藏元素(span)的文本,而textContent会。

此时就可以解释第一点的区别了, <script><style> 元素的内容再页面中是不会被显示的,所以用 innerText 获取不会返回,但是textContent会返回。

  1. 由于 innerText 受 CSS 样式的影响,依赖于页面的显示,它会触发回流(backflow),但textContent 可能不会触发回流。

回流:当render tree中的一部分或全部因为元素的规模尺寸、布局、隐藏等改变时,浏览器重新渲染部分DOM或全部DOM的过程。回流也被称为重排,其实从字面上来看,重排更容易让人形象易懂(即重新排版整个页面)。

重绘:当页面元素样式改变不影响元素在文档流中的位置时(如background-color,border-color,visibility),浏览器只会将新样式赋予元素并进行重新绘制操作。

什么时候会触发回流或重绘?
有大量的用户行为以及潜在的DHTML改变会触发回流。例如,改变浏览器窗口的大小,使用一些JavaScript方法,包括计算样式,对DOM进行元素的添加或删除,或是改变元素的class等。

添加或者删除可见的DOM元素;
元素位置改变;
元素尺寸改变——边距、填充、边框、宽度和高度;
内容变化,比如用户在input框中输入文字,文本或者图片大小改变而引起的计算值宽度和高度改变;
页面渲染初始化;
浏览器窗口尺寸改变,resize事件发生时;
计算offsetWidth和offsetHeight属性;
设置style属性的值;

回流必将引起重绘,而重绘不一定会引起回流。

浏览器认为你重新设置了innerText,会对你整个页面的渲染造成影响,所以这时候它会从当前的这个节点一直往回追溯,比如说从一个子节点找到它的父节点,从父节点再找到上一层父节点。一层一层往上找,一直找到根节点,执行这样一个逆向的,一步一步查找的这个过程,查找到了根节点,把整个树重新渲染一遍。这种情况称之为回流。

大家可以想象一下,浏览器执行这样操作的时候,对整个浏览器的性能影响是非常大的,所以如果用innerText设置一个值的时候,浏览器会触发回流操作,把整个页面重新渲染一遍。

相应的,textContent可能会触发重绘,比如你设置的textContent值由张三改为李四,这个div占据的面积未变,整个页面也没有排版,这时候既不会重绘也不会回流;若文本的长度,设置不一样的长度,那么只对小区域有影响,那么此时只会触发重绘,不会触发回流;若你设置的值再配上整个的显示的样式,对整个页面有影响了,那么这个时候就会触发回流。

<div>张三</div>
el.textContent = '李四'

相对来讲,textContent对浏览器性能的影响要比innerText小;

所以在对浏览器进行兼容性判断的时候,要先判断textContent,再去判断innerText

  1. innerText的返回值会被格式化,而textContent不会;

造成此区别的主因还是由于第一点,innerText依赖于页面的显示

比如现在为dom节点 div1设置值为’a\na’,本意是在页面中显示成a、换行、a,innerText依赖于页面的显示,这时候就会按照你写的方式把它展示出来,反映在页面中就是<div>a<br>a</div>

为另一个dom节点div2设置textContent为’a\na’,那么它会把这个值直接写在源码中,反映在页面中就是<div>a a</div>

<html lang="en">
  <head>
    <style>
      div {
        width: 300px;
        margin-top: 10px;
        border: 1px solid #eee;
        padding: 5px;
      }
      
    </style>
  </head>
  <body>
    <div id="div1"></div>
    <div id="div2"></div>
  </body>
  <script>
    const el = document.getElementById('div1')
    el.innerText = 'a\n\na'
    const el2 = document.getElementById('div2')
    el2.textContent = `a\n\n\na`
  </script>
</html>

效果:
请添加图片描述
5. 与 textContent 不同的是, 在 Internet Explorer (对于小于等于 IE11 的版本) 中对 innerText 进行修改, 不仅会移除当前元素的子节点,而且还会永久性地破坏所有后代文本节点(所以不可能再次将节点再次插入到任何其他元素或同一元素中)。

4. 与innerHTML的区别

正如其名称,innerHTML 返回 HTML 文本。通常,为了在元素中检索或写入文本,人们使用innerHTML。但是,textContent通常具有更好的性能,因为文本不会被解析为HTML。此外,使用textContent可以防止 XSS 攻击。

5. 归属区别

  • textContent 是 Node 对象的属性;
  • innerHTML 是 Element 对象的属性;
  • innerText 是 HTMLElement 对象的属性;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值