jjzjj

javascript - jQuery/JavaScript插件,用于突出显示文本

coder 2024-05-18 原文

我正在寻找一个jquery插件,用于在一个元素中显示多个突出显示的文本。我发现了一个非常受欢迎的插件,它就是http://bartaz.github.com/sandbox.js/jquery.highlight.html以及许多其他插件。

它们工作正常,但是如果我要突出显示与早期突出显示的文本重叠的文本,则不起作用。

有谁知道一个jQuery或JavaScript插件,它支持多个突出显示的文本并且正确突出显示重叠的文本?

最佳答案

如果添加一些小调整,就可以使用找到的highlighter plugin进行所有操作。
作为说明,我张贴了一个 fiddle ,以提速一个今天下午我迅速整理的工作示例:http://jsfiddle.net/4bwgA/

在这里,我将逐步介绍插件(OP所指)已经完成的所有工作,最后给出重叠的突出显示区域的解决方案。

荧光笔的作用是在您要应用的单词周围放置一个标签。所以如果你有

   <p>Who is the quick brown fox?</p>

然后您用
   $("p").highlight("brown");

你得到
   <p>Who is the quick <span class="highlight">brown</span> fox?</p>

和一个附加的命令
   $("p").highlight("brown fox");

不会找到任何东西,
导致该字符串不再具有该子字符串,因为它现在具有棕色标签。

因此,如果只是重叠...解决方案就很容易。该软件包提供了取消突出显示的功能,您可以在新的突出显示之前应用该功能
   $("p").unhighlight().highlight("brown fox");

并得到
   <p>Who is the quick <span class="highlight">brown fox</span>?</p>

到目前为止,这并不令人兴奋。但是,如果我们先突出显示“棕色”,然后再突出显示“狐狸”,该怎么办。我们得到这个
   <p>Who is the quick <span class="highlight">brown</span> <span class="highlight">fox</span>?</p>

然后,我们想加入相邻的突出显示区域。可以使用其他功能完成此操作,例如:
    function mergenode(node) {
        var parent1 = node.contents();
        parent1.each(function (i) {
            if (i > 0 && this.nodeType !== 1 && //if text node
                this.data.search(/^\s*$/g) === 0 && //consisting only of hyphens or blanks
                parent1[i - 1].nodeName === "SPAN" && //bordering to SPAN elements
                parent1[i + 1].nodeName === "SPAN" && 
                parent1[i - 1].className === "highlight" && //of class highlight
                parent1[i + 1].className === "highlight") {
                    selected1.push(parent1[i - 1]
                        .textContent.concat(this.data, parent1[i + 1].textContent));
            }
            else if (this.nodeType === 1 && 
                this.nodeName === "SPAN" && 
                parent1[i + 1].nodeName === "SPAN" && 
                this.className === "highlight" && 
                parent1[i + 1].className === "highlight") {
                    selected1.push(this.textContent.concat(parent1[i + 1].textContent));
            }
        });
        $(node).unhighlight().highlight(selected1);
    }

这会将所有相邻范围与类高亮合并(这是为通用荧光笔标记编写的,但是可以为nodeName和className加上两个额外的参数(对于自定义标记很容易地扩展))。结果将如下所示
    <p>Who is the quick <span class="highlight">brown fox</span>?</p>

到目前为止一切都很好。但是,如果我们的搜索字符串重叠怎么办?
首先...与重叠最好的做法是取消选中旧选项,然后再检查已清除的文本上是否有重叠的字符串。为此,我们需要记住先前的选择,例如可以将其保存在一个数组(我称为selected1)中,该数组在每个附加选择处都会添加一个值。

每次运行时,最终选择(全部合并)都保存到selected1数组中,以便将来用于合并和重叠。

现在,荧光笔如何处理字符串数组?它将高亮功能按它们传递给函数的顺序应用到它们中的每一个。因此,如果两个字符串完全重叠,我们可以通过对选择字符串的数组进行排序并首先突出显示较长的字符串来解决该问题。例如
    $("p").highlight(["brown fox","brown"]);

只会突出显示
    <p>Who is the quick <span class="highlight">brown fox</span>?</p>

数组可以按如下所示按长度排序
    words = words.sort(function (str1, str2) {
        return (str1.length < str2.length) ? 1 : 0;
    });

现在处理完全重叠和相邻的亮点。现在我们必须确保得到部分重叠的字符串。在这里,我写了一个比较两个字符串是否重叠的函数...还有其他方法可以做到这一点,但是我想在这个答案中显示的只是您需要突出显示自己的方式而需要执行的步骤顺序想要=)

此函数接收两个字符串,检查它们是否重叠,如果重叠,则将它们合并,并将新的合并字符串保存到数组toselect中,最后将其附加到原始words数组中。可能会有一些无用的组合,但不会造成伤害-它们不会在最后显示。
    function overlap(a, b) {
        var l = b.length,
            m = a.length;
        for (var j = 1; j < l; j++) {
            if (a.indexOf(b.substr(l - j)) === 0) {
                toselect.push(b.concat(a.substr(j)));
            } else if (a.substr(m - j).indexOf(b.substr(0, j)) === 0) {
                toselect.push(a.concat(b.substr(j)));
            }
        }
    }

现在,我们想将此功能应用于words数组中所有可能的元素对。我们可以循环循环进行此操作,但我对此有些兴奋,并做到了
    $.each(arr, function (i) {
        $.each(arr.slice(i + 1), function (i, v) {
            overlap(arr[i], v);
        });
    });

现在,我们只需要将新的toselect数组(其中所有可能的重叠字符串都已串联在一起)附加到原始words数组中。

因此,现在我们有了所需的所有部件,可以将它们放在一起。每次我们要突出显示一个新的字符串或字符串数​​组时,我们都会执行以下步骤:
  • 取消突出显示当前突出显示的所有内容(突出显示的所有内容将在selected1数组中)。
  • 我们新的字符串或字符串数​​组进入words数组
  • selected1附加到words
  • words中组合所有部分重叠的字符串对,然后将新的组合字符串添加到words中(使用overlap函数及其遍历整个数组的包装器-在 fiddle 示例中为overdiag)
  • 按字符串长度对words进行排序,因此最长的字符串将排在首位
  • 突出显示words的所有字符串
  • 合并所有相邻的突出显示的字符串(使用mergenode函数)
  • 突出显示的字符串的最后一组保存到selected1


  • 我今天下午很快将它们放在一起,所以它不是一个理想的实现,但是它可以工作=)我将代码添加到了荧光笔脚本中,并将它们添加到jsfiddle上的一个简单示例中,以便您与http://jsfiddle.net/4bwgA/一起玩。有按钮,因此您可以按所有不同的步骤,并查看它们的作用。

    关于javascript - jQuery/JavaScript插件,用于突出显示文本,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12018174/

    有关javascript - jQuery/JavaScript插件,用于突出显示文本的更多相关文章

    1. ruby - 使用 ruby​​ 将 HTML 转换为纯文本并维护结构/格式 - 2

      我想将html转换为纯文本。不过,我不想只删除标签,我想智能地保留尽可能多的格式。为插入换行符标签,检测段落并格式化它们等。输入非常简单,通常是格式良好的html(不是整个文档,只是一堆内容,通常没有anchor或图像)。我可以将几个正则表达式放在一起,让我达到80%,但我认为可能有一些现有的解决方案更智能。 最佳答案 首先,不要尝试为此使用正则表达式。很有可能你会想出一个脆弱/脆弱的解决方案,它会随着HTML的变化而崩溃,或者很难管理和维护。您可以使用Nokogiri快速解析HTML并提取文本:require'nokogiri'h

    2. ruby-on-rails - Rails 编辑表单不显示嵌套项 - 2

      我得到了一个包含嵌套链接的表单。编辑时链接字段为空的问题。这是我的表格:Editingkategori{:action=>'update',:id=>@konkurrancer.id})do|f|%>'Trackingurl',:style=>'width:500;'%>'Editkonkurrence'%>|我的konkurrencer模型:has_one:link我的链接模型:classLink我的konkurrancer编辑操作:defedit@konkurrancer=Konkurrancer.find(params[:id])@konkurrancer.link_attrib

    3. ruby-on-rails - Rails 常用字符串(用于通知和错误信息等) - 2

      大约一年前,我决定确保每个包含非唯一文本的Flash通知都将从模块中的方法中获取文本。我这样做的最初原因是为了避免一遍又一遍地输入相同的字符串。如果我想更改措辞,我可以在一个地方轻松完成,而且一遍又一遍地重复同一件事而出现拼写错误的可能性也会降低。我最终得到的是这样的:moduleMessagesdefformat_error_messages(errors)errors.map{|attribute,message|"Error:#{attribute.to_s.titleize}#{message}."}enddeferror_message_could_not_find(obje

    4. ruby - 解析 RDFa、微数据等的最佳方式是什么,使用统一的模式/词汇(例如 schema.org)存储和显示信息 - 2

      我主要使用Ruby来执行此操作,但到目前为止我的攻击计划如下:使用gemsrdf、rdf-rdfa和rdf-microdata或mida来解析给定任何URI的数据。我认为最好映射到像schema.org这样的统一模式,例如使用这个yaml文件,它试图描述数据词汇表和opengraph到schema.org之间的转换:#SchemaXtoschema.orgconversion#data-vocabularyDV:name:namestreet-address:streetAddressregion:addressRegionlocality:addressLocalityphoto:i

    5. ruby - 如何每月在 Heroku 运行一次 Scheduler 插件? - 2

      在选择我想要运行操作的频率时,唯一的选项是“每天”、“每小时”和“每10分钟”。谢谢!我想为我的Rails3.1应用程序运行调度程序。 最佳答案 这不是一个优雅的解决方案,但您可以安排它每天运行,并在实际开始工作之前检查日期是否为当月的第一天。 关于ruby-如何每月在Heroku运行一次Scheduler插件?,我们在StackOverflow上找到一个类似的问题: https://stackoverflow.com/questions/8692687/

    6. ruby-on-rails - 无法使用 Rails 3.2 创建插件? - 2

      我对最新版本的Rails有疑问。我创建了一个新应用程序(railsnewMyProject),但我没有脚本/生成,只有脚本/rails,当我输入ruby./script/railsgeneratepluginmy_plugin"Couldnotfindgeneratorplugin.".你知道如何生成插件模板吗?没有这个命令可以创建插件吗?PS:我正在使用Rails3.2.1和ruby​​1.8.7[universal-darwin11.0] 最佳答案 随着Rails3.2.0的发布,插件生成器已经被移除。查看变更日志here.现在

    7. ruby-on-rails - 使用 Sublime Text 3 突出显示 HTML 背景语法中的 ERB? - 2

      所以我在关注Railscast,我注意到在html.erb文件中,ruby代码有一个微弱的背景高亮效果,以区别于其他代码HTML文档。我知道Ryan使用TextMate。我正在使用SublimeText3。我怎样才能达到同样的效果?谢谢! 最佳答案 为SublimeText安装ERB包。假设您安装了SublimeText包管理器*,只需点击cmd+shift+P即可获得命令菜单,然后键入installpackage并选择PackageControl:InstallPackage获取包管理器菜单。在该菜单中,键入ERB并在看到包时选择

    8. ruby-on-rails - link_to 不显示任何 rails - 2

      我试图在索引页中创建一个超链接,但它没有显示,也没有给出任何错误。这是我的index.html.erb代码。ListingarticlesTitleTextssss我检查了我的路线,我认为它们也没有问题。PrefixVerbURIPatternController#Actionwelcome_indexGET/welcome/index(.:format)welcome#indexarticlesGET/articles(.:format)articles#indexPOST/articles(.:format)articles#createnew_articleGET/article

    9. Ruby Sinatra 配置用于生产和开发 - 2

      我已经在Sinatra上创建了应用程序,它代表了一个简单的API。我想在生产和开发上进行部署。我想在部署时选择,是开发还是生产,一些方法的逻辑应该改变,这取决于部署类型。是否有任何想法,如何完成以及解决此问题的一些示例。例子:我有代码get'/api/test'doreturn"Itisdev"end但是在部署到生产环境之后我想在运行/api/test之后看到ItisPROD如何实现? 最佳答案 根据SinatraDocumentation:EnvironmentscanbesetthroughtheRACK_ENVenvironm

    10. ruby-on-rails - 如何在 Rails View 上显示错误消息? - 2

      我是rails的新手,想在form字段上应用验证。myviewsnew.html.erb.....模拟.rbclassSimulation{:in=>1..25,:message=>'Therowmustbebetween1and25'}end模拟Controller.rbclassSimulationsController我想检查模型类中row字段的整数范围,如果不在范围内则返回错误信息。我可以检查上面代码的范围,但无法返回错误消息提前致谢 最佳答案 关键是您使用的是模型表单,一种显示ActiveRecord模型实例属性的表单。c

    随机推荐