2

想象一下页面上的这个 html

<div id="hpl_content_wrap">
<p class="foobar">this is one word and then another word comes in foobar and then more words and then foobar again.</p>
<p>this is a <a href="http://foobar.com" data-bitly-type="bitly_hover_card">link with foobar in an attribute</a> but only the foobar inside of the link should be replaced.</p>
</div>

使用 javascript,如何在不更改任何内部 html 标签的情况下将所有 'foobar' 单词更改为 'herpderp'?

IE。只应更改纯文本。

所以成功的html改变将是

<div id="hpl_content_wrap">
<p class="foobar">this is one word and then another word comes in herpderp and then more words and then herpderp again.</p>
<p>this is a <a href="http://foobar.com" data-bitly-type="bitly_hover_card">link with herpderp in an attribute</a> but only the herpderp inside of the link should be replaced.    </p>
</div>
4

2 回答 2

1

这是您需要做的...

  1. 获取对一堆元素的引用。
  2. 递归遍历子节点,仅替换文本节点中的文本。

抱歉耽搁了,我还没来得及添加代码就跑题了。

var replaceText = function me(parentNode, find, replace) {
    var children = parentNode.childNodes;

    for (var i = 0, length = children.length; i < length; i++) {
        if (children[i].nodeType == 1) {
            me(children[i], find, replace);            
        } else if (children[i].nodeType == 3) {
            children[i].data = children[i].data.replace(find, replace);
        }

    }

    return parentNode;

}

replaceText(document.body, /foobar/g, "herpderp");​​​

js小提琴

于 2012-06-08T04:46:32.910 回答
0

这是一个简单的问题:

  • 识别 DOM 树中的所有文本节点,
  • 然后替换其中的所有 foobar 字符串。

这是完整的代码:

// from: https://stackoverflow.com/questions/298750/how-do-i-select-text-nodes-with-jquery
var getTextNodesIn = function (el) {
    return $(el).find(":not(iframe)").andSelf().contents().filter(function() {
        return this.nodeType == 3;
    });
};

var replaceAllText = function (pattern, replacement, root) {
    var nodes = getTextNodesIn(root || $('body'))
    var re    = new RegExp(pattern, 'g')

    nodes.each(function (i, e) {
        if (e.textContent && e.textContent.indexOf(pattern) != -1) {
           e.textContent = e.textContent.replace(re, replacement);
        }
    });
};


// replace all text nodes in document's body
replaceAllText('foobar', 'herpderp');

// replace all text nodes under element with ID 'someRootElement'
replaceAllText('foobar', 'herpderp', $('#someRootElement'));

请注意,我对 foobar 进行了预检查,以避免使用正则表达式处理疯狂的长字符串。可能是也可能不是一个好主意。

如果您不想使用 jQuery,而只想使用纯 JavaScript,请点击代码片段中的链接(如何使用 jQuery 选择文本节点?),您还可以在其中找到仅 JS 的版本来获取节点。然后,您只需以类似的方式迭代返回的元素。

于 2012-06-08T04:47:57.357 回答