【问题标题】:Using jquery or JS how do you turn a string into a link?使用 jquery 或 JS 如何将字符串转换为链接?
【发布时间】:2012-10-01 00:52:32
【问题描述】:

所以我有一段看起来像这样的 HTML...

<p>This is some copy. In this copy is the word hello</p>

我想使用 jquery 将单词 hello 转换为链接。

<p>This is some copy. In this copy is the word <a href="">hello</a></p>

这本身并不太难。我的问题是,如果这个词已经是一个链接的一部分,比如下面的例子......

<p>In this copy is the <a href="">word hello</a></p>

我不希望它以链接中的链接结束...

<p>In this copy is the <a href="">word <a href="">hello</a></a></p>

任何帮助将不胜感激。

【问题讨论】:

  • 你能不能只在文本元素上调用 parent("a") 看看是否不返回 null?
  • 你能发布你已经在使用的代码吗?

标签: jquery dynamic-links


【解决方案1】:

一点正则表达式就可以解决问题(更新,见下文):

$(document).ready(function(){
    var needle = 'hello';
    $('p').each(function(){
        var me = $(this),
            txt = me.html(),
            found = me.find(needle).length;
        if (found != -1) {
            txt = txt.replace(/(hello)(?!.*?<\/a>)/gi, '<a href="">$1</a>');
            me.html(txt);
        }
    });
});

小提琴:http://jsfiddle.net/G8rKw/

编辑:这个版本效果更好:

$(document).ready(function() {
    var needle = 'hello';
    $('p').each(function() {
        var me = $(this),
            txt = me.html(),
            found = me.find(needle).length;
        if (found != -1) {
            txt = txt.replace(/(hello)(?![^(<a.*?>).]*?<\/a>)/gi, '<a href="">$1</a>');
            me.html(txt);
        }
    });
});

小提琴:http://jsfiddle.net/G8rKw/3/

再次编辑:这次,“hello”作为变量传递给正则表达式

$(document).ready(function() {
    var needle = 'hello';
    $('p').each(function() {
        var me = $(this),
        txt = me.html(),
        found = me.find(needle).length,
        regex = new RegExp('(' + needle + ')(?![^(<a.*?>).]*?<\/a>)','gi');
        if (found != -1) {
            txt = txt.replace(regex, '<a href="">$1</a>');
            me.html(txt);
        }
    });
});

小提琴:http://jsfiddle.net/webrocker/MtM3s/

【讨论】:

  • hm,正则表达式需要更多细化;如果'word hello'前面有'hello',则不会被替换,因为/(hello)(?!.*? ) 将寻找 "hello" 后面没有结束 标记——不知何故,这个表达式中还必须包含一个开始 标记以停止匹配......
  • 添加了第 2 个版本,该版本可在一个段落中使用原始排行和无链接搜索词的组合。
  • 添加了第三版,其中“hello”作为正则表达式中的变量传递。
【解决方案2】:

此 jQuery 解决方案搜索特定术语,如果发现它后面跟着一个结束链接标记,则不会创建链接。

var searchTerm = "hello";

$('p:contains("' + searchTerm + '")').each(function(){
    var searchString = $(this).html();
    var searchIndex = searchString.indexOf(searchTerm);
    var startString = searchString.substr(0 , searchIndex);
    var endString = searchString.substr(searchIndex + searchTerm.length);
    if(endString.match(/<\/a>/g)) return;
    $(this).html(startString + "<a href=''>" + searchTerm + "</a>" + endString);
});​

这是 a link 给它的 jsfiddle。

【讨论】:

  • 关闭,但当你用另一个词括起来时失败,比如&lt;p&gt;This is some copy. In this copy the word &lt;a href=""&gt;is hello&lt;/a&gt;&lt;/p&gt;
  • @Vega 更改为您的示例,它成功了 - 因为 hello 后面跟着一个结束标记,它会返回 - 正如 Paul 所希望的那样。但是,如果它是&lt;p&gt;This is some copy. In this copy the word &lt;a href=""&gt;hello is&lt;/a&gt;&lt;/p&gt;,它将失败。我已经更新了我的解决方案,以便它能够处理这个问题。
【解决方案3】:

编写了一个简单的函数来检查替换文本是否包含在链接标记中。见下文,

演示: http://jsfiddle.net/wyUYb/4/

function changeToLink (sel, txt) {
   var regEx = new RegExp(txt, 'g');
   $.each($(sel), function (i, el) {
       var linkHTML = $(el).html();
       var idx = linkHTML.indexOf(txt);

       if (idx >= 0) {
           var t = linkHTML.substring(idx);
           //Fix for IE returning tag names in upper case http://stackoverflow.com/questions/2873326/convert-html-tag-to-lowercase
           t = t.replace(/<\/?[A-Z]+.*?>/g, function (m) { return m.toLowerCase(); })
           var closingA = t.indexOf('</a>');

           t = t.substring(0, closingA);
           if (closingA != -1) {
               t = t.substring(0, closingA); 
               if (t.indexOf('<a') < txt.length) {
                   return;
               }
           }               

           linkHTML = linkHTML.replace(regEx, '<a href="">' + txt + '</a>');
           $(el).html(linkHTML);
       }           
   });
}

此外,即使您添加了一个嵌套链接,您的浏览器也会简单地将其更改为两个链接。可能是因为使用嵌套链接是不合法的。见下文,

在 W3C 中也记录了Nested Links

12.2.2 嵌套链接是非法的

A 元素定义的链接和锚点不能嵌套;一个A 元素不得包含任何其他 A 元素。

由于 DTD 将 LINK 元素定义为空,因此 LINK 元素可以 也不能嵌套。

这就是浏览器将嵌套链接作为单独链接处理的原因。

http://jsfiddle.net/H44jE/

查看图片右下角的萤火虫检查。

【讨论】:

    【解决方案4】:

    你可以这样做,

    Live Demo

    $('p').each(function(){    
        if($(this).find('a').length > 0) return;  
        lastSpaceIndex = $(this).text().lastIndexOf(' ');
        if(lastSpaceIndex  == -1)
            lastSpaceIndex = 0;    
        WordToReplace = $(this).text().substring(lastSpaceIndex);
        idx = $(this).text().lastIndexOf(WordToReplace);
        resultstring = $(this).text().substring(0, idx); 
        $(this).html(resultstring);
        $(this).append($( "<a href='#'>" + WordToReplace  + "</a>"));
    });​
    

    【讨论】:

      【解决方案5】:

      尝试用户 .replace jquery 函数是这样的:

      var str = $('p').html().replace('(some)','(to some)');
      

      【讨论】:

        【解决方案6】:

        您需要 jquery :not 选择器或 .not()。

        API 文档很好地涵盖了这一点,您应该能够选择您的内容,然后取消选择其中的链接。

        http://api.jquery.com/not-selector/

        【讨论】:

          【解决方案7】:

          不要搜索单词并尝试查找其父项,而是搜索链接并检查其中包含的单词:

          if($('a').text() === "hello"){
            //already linked
          }else{
            //not linked
          }
          

          【讨论】:

            【解决方案8】:

            先保留单词,同时去掉当前的锚标签,如果有的话:

            $('a').each(function() {
                $(this).replaceWith(this.childNodes);
             });
            

            然后对需要使用的字符串进行替换

            $('p').html($('p').text().replace('hello', '<a href="">hello</a>'));
            

            【讨论】:

              【解决方案9】:

              在把它变成链接之前,你能不测试它的父元素吗?

              if (parent != 'a') {
                 // do your thing
              }
              

              (我不知道实际的 jQuery 会测试这个)

              编辑

              以下内容将替换所有不包含链接的 &lt;p&gt; 元素中的单词。

              可能无法完全按照要求工作,但希望为您指明方向

              // get all p elements that contain the word hello but DO NOT have link in them
              var elems = $('p:contains("hello")').not(':has(a)');
              
              
              // replace instances of hello in the selected p elements
              $(elems).html($(elems).html().replace(/(hello)/g,'<a href="new">$1</a>'));
              

              Live Demo on JSBin

              【讨论】:

              • 这是我的问题,我也不知道实际的 jquery。因为您选择的是字符串(单词 Hello)而不是 dom 元素,所以我不知道您如何检查它的直接父元素。
              猜你喜欢
              • 2015-12-03
              • 1970-01-01
              • 2023-03-03
              • 2014-04-08
              • 2013-04-14
              • 2020-12-27
              • 2012-02-28
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多