Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/436.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 用元素替换文本节点中间的文本_Javascript_Html_Dom_Textnode - Fatal编程技术网

Javascript 用元素替换文本节点中间的文本

Javascript 用元素替换文本节点中间的文本,javascript,html,dom,textnode,Javascript,Html,Dom,Textnode,我想用TreeWalker在文本节点中插入html标记,但TreeWalker强制将html括号插入<;&燃气轮机;不管我怎么努力。代码如下: var text; var tree = document.createTreeWalker(document.body,NodeFilter.SHOW_TEXT); while (tree.nextNode()) { text = tree.currentNode.nodeValue; text = text.replace(/(\

我想用TreeWalker在文本节点中插入html标记,但TreeWalker强制将html括号插入<;&燃气轮机;不管我怎么努力。代码如下:

var text;
var tree = document.createTreeWalker(document.body,NodeFilter.SHOW_TEXT);
while (tree.nextNode()) {
    text = tree.currentNode.nodeValue;
    text = text.replace(/(\W)(\w+)/g, '$1<element onmouseover="sendWord(\'$2\')">$2</element>');
    text = text.replace(/^(\w+)/, '<element onmouseover="sendWord(\'$1\')">$1</element>');
    tree.currentNode.nodeValue = text;
}
var文本;
var tree=document.createTreeWalker(document.body,NodeFilter.SHOW_TEXT);
while(tree.nextNode()){
text=tree.currentNode.nodeValue;
text=text.replace(/(\W)(\W+)/g,$1$2');
text=text.replace(/^(\w+/,“$1”);
tree.currentNode.nodeValue=文本;
}
使用\<或“而不是‘没用’。我的解决方法是将所有DOM树复制到一个字符串中,并用该字符串替换html正文。它可以在非常简单的网页上工作,解决了我的第一个问题,但是它是一个很糟糕的黑客,除了一个普通的页面之外,它什么都不能用。我想知道我是否可以直接使用文本节点,而不是使用变通方法。以下是(当前存在错误)解决方案的代码:

var text;
var newHTML = "";
var tree = document.createTreeWalker(document.body);
while (tree.nextNode()) {
    text = tree.currentNode.nodeValue;
    if (tree.currentNode.nodeType == 3){
        text = text.replace(/(\W)(\w+)/g, '$1<element onmouseover="sendWord(\'$2\')">$2</element>');
        text = text.replace(/^(\w+)/, '<element onmouseover="sendWord(\'$1\')">$1</element>');
        }
    newHTML += text
}
document.body.innerHTML = newHTML;
var文本;
var newHTML=“”;
var tree=document.createTreeWalker(document.body);
while(tree.nextNode()){
text=tree.currentNode.nodeValue;
if(tree.currentNode.nodeType==3){
text=text.replace(/(\W)(\W+)/g,$1$2');
text=text.replace(/^(\w+/,“$1”);
}
newHTML+=文本
}
document.body.innerHTML=newHTML;

编辑:我意识到一个更好的解决方法是自定义标记文本节点((这里是Customtag_Start_)等等),将整个DOM复制到一个字符串中,然后使用我的自定义标记来标识文本节点并以这种方式修改它们。但是,如果不必这样做,我宁愿不这样做。

要将文本节点“更改”为元素,您必须。例如:

var text = tree.currentNode;
var el = document.createElement('foo');
el.setAttribute('bar','yes');
text.parentNode.replaceChild( el, text );
如果要保留部分文本节点,并在“中间”插入元素,则需要在树中的适当位置将和和元素插入到树中


编辑:这里有一个可能对您非常有用的函数:

给定一个文本节点,它对文本值运行正则表达式。对于找到的每个命中,它都会调用您提供的自定义函数。如果该函数返回字符串,则替换匹配项。但是,如果该函数返回如下对象:

{ name:"element", attrs{onmouseover:"sendWord('foo')"}, content:"foo" }
然后,它将围绕匹配项拆分文本节点,并在该位置注入元素。您还可以返回字符串数组或那些对象(并且可以递归地使用数组、字符串或对象作为
内容
属性)

演示: 它不是完全通用的,因为它不支持属性上的名称空间。但希望这足以让你继续前进。:)


您可以这样使用它:

findAllTextNodes(document.body).forEach(function(textNode){
  replaceTextNode( textNode, /\b\w+/g, function(match){
    return {
      name:'element',
      attrs:{onmouseover:"sendWord('"+match[0]+"')"},
      content:match[0]
    };
  });
});

function findAllTextNodes(node){
  var walker = node.ownerDocument.createTreeWalker(node,NodeFilter.SHOW_TEXT);
  var textNodes = [];
  while (walker.nextNode())
    if (walker.currentNode.parentNode.tagName!='SCRIPT')
      textNodes.push(walker.currentNode);
  return textNodes;
}
或者,如果您想要更接近原始正则表达式:

  replaceTextNode( textNode, /(^|\W)(\w+)/g, function(match){
    return [
      match[1], // might be an empty string
      {
        name:'element',
        attrs:{onmouseover:"sendWord('"+match[2]+"')"},
        content:match[2]
      }
    ];
  });

您无法在文本节点中插入HTML…我是否可以告诉文本节点它不想再成为文本节点(即,告诉它有很多文本节点子节点)?@e2r2i2k2否。您可以替换它,可以拆分它,但不能更改它。请注意,如果您在漫游期间创建新的文本节点,那么您也将漫游并访问它们。根据我的回答,最简单的方法是收集所有文本节点,然后遍历它们。我现在知道该怎么做了,但是上面的代码抛出了一个很长的
DomException….消息:未找到节点
错误。我将继续玩弄它以使其正常工作。@e2r2i2k2请参阅我的编辑,了解如何用元素“替换”文本节点中的文本,并让它们自动拆分。一定要看到它的应用程序的演示URL。哇,谢谢!这个功能对我来说很有用。对于您的原始代码,我发现了问题。最后一行应为
text.parentNode.replaceChild(el,text)
两个节点变量被反转。如果textnode的父节点为空会怎样?如何用html元素替换该textnode?
  replaceTextNode( textNode, /(^|\W)(\w+)/g, function(match){
    return [
      match[1], // might be an empty string
      {
        name:'element',
        attrs:{onmouseover:"sendWord('"+match[2]+"')"},
        content:match[2]
      }
    ];
  });