如何从一个数组中的所有标签获取所有文本?

时间:2013-07-18 15:38:22

标签: javascript getelementsbytagname

我需要创建一个包含页面中没有jQuery的所有文本的数组。这是我的HTML:

<html>
<head>
    <title>Hello world!</title>
</head>
<body>
    <h1>Hello!</h1>
    <p>
        <div>What are you doing?</div>
        <div>Fine, and you?</div>
    </p>
    <a href="http://google.com">Thank you!</a>
</body>
</html>

这是我想要的

text[1] = "Hello world!";
text[2] = "Hello!";
text[3] = "What are you doing?";
text[4] = "Fine, and you?";
text[5] = "Thank you!";

以下是我尝试但似乎无法在浏览器中正常运行的内容:

var elements = document.getElementsByTagName('*');
console.log(elements);

PS。我需要使用document.getElementsByTagName('*');并排除“脚本”和“风格”。

5 个答案:

答案 0 :(得分:3)

  var array = [];

    var elements = document.body.getElementsByTagName("*");

    for(var i = 0; i < elements.length; i++) {
       var current = elements[i];
        if(current.children.length === 0 && current.textContent.replace(/ |\n/g,'') !== '') {
           // Check the element has no children && that it is not empty
           array.push(current.textContent);
        }
    } 

你可以做这样的事情

Demo

result = ["What are you doing?", "Fine, and you?"]

或者您可以使用document.documentElement.getElementsByTagName('*');

还要确保您的代码在此

document.addEventListener('DOMContentLoaded', function(){

   /// Code...
});

如果它只是你需要的标题,你也可以这样做

array.push(document.title);

通过脚本保存循环&amp;风格

答案 1 :(得分:2)

如果您想要整个页面的内容,您应该可以使用

var allText = document.body.textContent;

在IE9之前的Internet Explorer中,存在类似但不相同的属性innerTextMDN page about textContent有更详细的内容。

现在一个问题是,textContent会为您提供任何<style><script>标记的内容,这些标记可能是您想要的,也可能不是。如果你不想那样,你可以使用这样的东西:

function getText(startingPoint) {
  var text = "";
  function gt(start) {
    if (start.nodeType === 3)
      text += start.nodeValue;
    else if (start.nodeType === 1)
      if (start.tagName != "SCRIPT" && start.tagName != "STYLE")
        for (var i = 0; i < start.childNodes.length; ++i)
          gt(start.childNodes[i]);
  }
  gt(startingPoint);
  return text;
}

然后:

var allText = getText(document.body);

注意:这个(或document.body.innerText)会为您提供所有文字,但按深度优先顺序排列。在页面呈现后,按照人类实际看到的顺序从页面获取所有文本是一个很多更难的问题,因为它需要代码来理解视觉效果(和视觉效果)语义!)由CSS(等)指示的布局。

编辑 - 如果您希望文本“存储到数组中”,我想在逐个节点的基础上(?),您只需要将数组追加替换为字符串连接以上:

function getTextArray(startingPoint) {
  var text = [];
  function gt(start) {
    if (start.nodeType === 3)
      text.push(start.nodeValue);
    else if (start.nodeType === 1)
      if (start.tagName != "SCRIPT" && start.tagName != "STYLE")
        for (var i = 0; i < start.childNodes.length; ++i)
          gt(start.childNodes[i]);
  }
  gt(startingPoint);
  return text;
}

答案 2 :(得分:0)

    <html>
    <head>
            <title>Hello world!</title>
    </head>
    <body>
            <h1>Hello!</h1>
            <p>
                    <div>What are you doing?</div>
                    <div>Fine, 
                        <span> and you? </span>
                    </div>
            </p>
            <a href="http://google.com">Thank you!</a>
            <script type="text/javascript">
                function getLeafNodesOfHTMLTree(root) {
                    if (root.nodeType == 3) {
                        return [root];
                    } else {
                        var all = [];
                        for (var i = 0; i < root.childNodes.length; i++) {
                            var ret2 = getLeafNodesOfHTMLTree(root.childNodes[i]);
                            all = all.concat(ret2);
                        }
                        return all;
                    }
                }
                var allnodes = getLeafNodesOfHTMLTree(document.getElementsByTagName("html")[0]);
                console.log(allnodes);
                 //in modern browsers that surport array filter and map
                allnodes = allnodes.filter(function (node) {
                    return node && node.nodeValue && node.nodeValue.replace(/\s/g, '').length;
                });
                allnodes = allnodes.map(function (node) {
                    return node.nodeValue
                })
                 console.log(allnodes);
            </script>
    </body>
    </html>

答案 3 :(得分:0)

遍历DOM树,获取所有文本节点,获取文本节点的nodeValue。

var result = [];
var itr = document.createTreeWalker(
    document.getElementsByTagName("html")[0],
    NodeFilter.SHOW_TEXT,
    null, // no filter
    false);
while(itr.nextNode()) {
    if(itr.currentNode.nodeValue != "")
        result.push(itr.currentNode.nodeValue);
}
alert(result);

替代方法:拆分HTML标记的textContent。

var result = document.getElementsByTagName("html")[0].textContent.split("\n");
for(var i=0; i<result.length; i++)
    if(result[i] == "")
        result.splice(i, 1);
alert(result);

答案 4 :(得分:0)

似乎是单行解决方案(fiddle):

document.body.innerHTML.replace(/^\s*<[^>]*>\s*|\s*<[^>]*>\s*$|>\s*</g,'').split(/<[^>]*>/g)

如果body中有复杂的脚本,这可能会失败,我知道用正则表达式is not a very clever idea解析HTML,但是对于简单的情况或者为了演示目的,它仍然适用,不是吗? :)