Difference between textContent vs innerText

What is the difference between textContent and innerText in JavaScript?

Can I use textContent as follows:

var logo$ = document.getElementsByClassName('logo')[0];
logo$.textContent = "Example";

Answers:

Answer

Both innerText & textContent are standardized as of 2016. All Node objects (including pure text nodes) have textContent, but only HTMLElement objects have innerText.

While textContent works with most browsers, it does not work on IE8 or earlier. Use this polyfill for it to work on IE8 only. This polyfill will not work with IE7 or earlier.

if (Object.defineProperty 
  && Object.getOwnPropertyDescriptor 
  && Object.getOwnPropertyDescriptor(Element.prototype, "textContent") 
  && !Object.getOwnPropertyDescriptor(Element.prototype, "textContent").get) {
  (function() {
    var innerText = Object.getOwnPropertyDescriptor(Element.prototype, "innerText");
    Object.defineProperty(Element.prototype, "textContent",
     {
       get: function() {
         return innerText.get.call(this);
       },
       set: function(s) {
         return innerText.set.call(this, s);
       }
     }
   );
  })();
}

The Object.defineProperty method is availabe in IE9 or up, however it is available in IE8 for DOM objects only.

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/defineProperty

https://developer.mozilla.org/en-US/docs/Web/API/Node/textContent

Answer

textContent is the only one available for text nodes:

var text = document.createTextNode('text');

console.log(text.innerText);    //  undefined
console.log(text.textContent);  //  text

In element nodes, innerText evaluates <br> elements, while textContent evaluates control characters:

var span = document.querySelector('span');
span.innerHTML = "1<br>2<br>3<br>4\n5\n6\n7\n8";
console.log(span.innerText); // breaks in first half
console.log(span.textContent); // breaks in second half
<span></span>

span.innerText gives:

1
2
3
4 5 6 7 8

span.textContent gives:

1234
5
6
7
8

Strings with control characters (e. g. line feeds) are not available with textContent, if the content was set with innerText. The other way (set control characters with textContent), all characters are returned both with innerText and textContent:

var div = document.createElement('div');
div.innerText = "x\ny";
console.log(div.textContent);  //  xy

Answer

For those who googled this question and arrived here. I feel the most clear answer to this question is in MDN document: https://developer.mozilla.org/en-US/docs/Web/API/Node/textContent.

You can forgot all the points that may confuse you but remember 2 things:

  1. When you are trying to alter the text, textContent is usually the property you are looking for.
  2. When you are trying to grab text from some element, innerText approximates the text the user would get if they highlighted the contents of the element with the cursor and then copied to the clipboard. And textContent gives you everything, visible or hidden, including <script> and <style> elements.
Answer

textContent is supported by most browsers. It is not supported by ie8 or earlier, but a polyfill can be used for this

The textContent property sets or returns the textual content of the specified node, and all its descendants.

See http://www.w3schools.com/jsref/prop_node_textcontent.asp

Answer

textContent returns full text and does not care about visibility, while innerText does.

<p id="source">
    <style>#source { color: red; }</style>
    Text with breaking<br>point.
    <span style="display:none">HIDDEN TEXT</span>
</p>

Output of textContent:

#source { color: red; } Text with breakingpoint. HIDDEN TEXT

Output of innerText ( note how innerText is aware of tags like <br>, and ignores hidden element ):

Text with breaking point.
Answer

innerHTML will execute even the HTML tags which might be dangerous causing any kind of client-side injection attack like DOM based XSS. Here is the code snippet:

<!DOCTYPE html>
<html>
    <body>
        <script>
            var source = "Hello " + decodeURIComponent("<h1>Text inside gets executed as h1 tag HTML is evaluated</h1>");  //Source
            var divElement = document.createElement("div");
            divElement.innerHTML = source;  //Sink
            document.body.appendChild(divElement);
        </script>
    </body>
</html>

If you use .textContent, it will not evaluate the HTML tags and print it as String.

<!DOCTYPE html>
<html>
    <body>
        <script>
            var source = "Hello " + decodeURIComponent("<h1>Text inside will not get executed as HTML</h1>");  //Source
            var divElement = document.createElement("div");
            divElement.textContent = source;  //Sink
            document.body.appendChild(divElement);
        </script>
    </body>
</html>

Reference: https://www.scip.ch/en/?labs.20171214

Answer

Aside from all the differences that were named in the other answers, here is another one which I discovered only recently:

Even though the innerText property is said to've been standardised since 2016, it exhibits differences between browsers: Mozilla ignores U+200E and U+200F characters ("lrm" and "rlm") in innerText, while Chrome does not.

console.log(document.getElementById('test').textContent.length);
console.log(document.getElementById('test').innerText.length);
<div id="test">[&#x200E;]</div>

Firefox reports 3 and 2, Chrome reports 3 and 3.

Not sure yet if this is a bug (and if so, in which browser) or just one of those quirky incompatibilities which we have to live with.

Answer

None of the other answers succeeds in providing the full explanation, hence this one. The key differences between innerText and textContent are outlined very well in Kelly Norton's blogpost: innerText vs. textContent. Below you can find a summary:

  1. innerText was non-standard, while textContent was standardized earlier.
  2. innerText returns the visible text contained in a node, while textContent returns the full text. For example, on the following HTML <span>Hello <span style="display: none;">World</span></span>, innerText will return 'Hello', while textContent will return 'Hello World'. For a more complete list of differences, see the table at http://perfectionkills.com/the-poor-misunderstood-innerText/ (further reading at 'innerText' works in IE, but not in Firefox).
  3. As a result, innerText is much more performance-heavy: it requires layout information to return the result.
  4. innerText is defined only for HTMLElement objects, while textContent is defined for all Node objects.

A workaround for textContent in IE8- would involve a recursive function using nodeValue on all childNodes of the specified node, here's a try at a polyfill:

function textContent(rootNode) {
  if ('textContent' in document.createTextNode(''))
    return rootNode.textContent;

  var childNodes = rootNode.childNodes,
      len = childNodes.length,
      result = '';

  for (var i = 0; i < len; i++) {
    if (childNodes[i].nodeType === 3)
      result += childNodes[i].nodeValue;
    else if (childNodes[i].nodeType === 1) 
      result += textContent(childNodes[i]);
  }

  return result;
}

Tags

Recent Questions

Top Questions

Home Tags Terms of Service Privacy Policy DMCA Contact Us Javascript

©2020 All rights reserved.