Highlight a word with jQuery

2018-12-31 04:39发布

I basically need to highlight a particular word in a block of text. For example, pretend I wanted to highlight the word "dolor" in this text:

<p>
    Lorem ipsum dolor sit amet, consectetuer adipiscing elit.
</p>
<p>
    Quisque bibendum sem ut lacus. Integer dolor ullamcorper libero.
    Aliquam rhoncus eros at augue. Suspendisse vitae mauris.
</p>

How do I convert the above to something like this:

<p>
    Lorem ipsum <span class="myClass">dolor</span> sit amet, consectetuer adipiscing elit.
</p>
<p>
    Quisque bibendum sem ut lacus. Integer <span class="myClass">dolor</span> ullamcorper
    libero. Aliquam rhoncus eros at augue. Suspendisse vitae mauris.
</p>

Is this possible with jQuery?

Edit: As Sebastian pointed out, this is quite possible without jQuery - but I was hoping there might be a special method of jQuery which would let you do selectors on the text itself. I'm already using jQuery heavily on this site, so keeping everything wrapped up in jQuery would make things perhaps a bit more tidy.

13条回答
骚的不知所云
2楼-- · 2018-12-31 05:02

I wrote a very simple function that uses jQuery to iterate the elements wrapping each keyword with a .highlight class.

function highlight_words(word, element) {
    if(word) {
        var textNodes;
        word = word.replace(/\W/g, '');
        var str = word.split(" ");
        $(str).each(function() {
            var term = this;
            var textNodes = $(element).contents().filter(function() { return this.nodeType === 3 });
            textNodes.each(function() {
              var content = $(this).text();
              var regex = new RegExp(term, "gi");
              content = content.replace(regex, '<span class="highlight">' + term + '</span>');
              $(this).replaceWith(content);
            });
        });
    }
}

More info:

http://www.hawkee.com/snippet/9854/

查看更多
低头抚发
3楼-- · 2018-12-31 05:02

If you're really game you could look through the source of StackOverflow for how it does syntax highlighting on the code blocks ;)

Essentially you'll have to just dynamically insert HTML (spans would be best) where you need them.

查看更多
后来的你喜欢了谁
4楼-- · 2018-12-31 05:04
function hiliter(word, element) {
    var rgxp = new RegExp(word, 'g');
    var repl = '<span class="myClass">' + word + '</span>';
    element.innerHTML = element.innerHTML.replace(rgxp, repl);
}
hiliter('dolor');
查看更多
步步皆殇っ
5楼-- · 2018-12-31 05:05

Why using a selfmade highlighting function is a bad idea

The reason why it's probably a bad idea to start building your own highlighting function from scratch is because you will certainly run into issues that others have already solved. Challenges:

  • You would need to remove text nodes with HTML elements to highlight your matches without destroying DOM events and triggering DOM regeneration over and over again (which would be the case with e.g. innerHTML)
  • If you want to remove highlighted elements you would have to remove HTML elements with their content and also have to combine the splitted text-nodes for further searches. This is necessary because every highlighter plugin searches inside text nodes for matches and if your keywords will be splitted into several text nodes they will not being found.
  • You would also need to build tests to make sure your plugin works in situations which you have not thought about. And I'm talking about cross-browser tests!

Sounds complicated? If you want some features like ignoring some elements from highlighting, diacritics mapping, synonyms mapping, search inside iframes, separated word search, etc. this becomes more and more complicated.

Use an existing plugin

When using an existing, well implemented plugin, you don't have to worry about above named things. The article 10 jQuery text highlighter plugins on Sitepoint compares popular highlighter plugins. This includes plugins of answers from this question.

Have a look at mark.js

mark.js is such a plugin that is written in pure JavaScript, but is also available as jQuery plugin. It was developed to offer more opportunities than the other plugins with options to:

  • search for keywords separately instead of the complete term
  • map diacritics (For example if "justo" should also match "justò")
  • ignore matches inside custom elements
  • use custom highlighting element
  • use custom highlighting class
  • map custom synonyms
  • search also inside iframes
  • receive not found terms

DEMO

Alternatively you can see this fiddle.

Usage example:

// Highlight "keyword" in the specified context
$(".context").mark("keyword");

// Highlight the custom regular expression in the specified context
$(".context").markRegExp(/Lorem/gmi);

It's free and developed open-source on GitHub (project reference).

查看更多
弹指情弦暗扣
6楼-- · 2018-12-31 05:05

I have created a repository on similar concept that changes the colors of the texts whose colors are recognised by html5 (we don't have to use actual #rrggbb values and could just use the names as html5 standardised about 140 of them)

colors.js colors.js

$( document ).ready(function() {
	
	function hiliter(word, element) {
		var rgxp = new RegExp("\\b" + word + "\\b" , 'gi'); // g modifier for global and i for case insensitive 
		var repl = '<span class="myClass">' + word + '</span>';
		element.innerHTML = element.innerHTML.replace(rgxp, repl);
			
			};

	hiliter('dolor', document.getElementById('dolor'));
});
.myClass{

background-color:red;
}
<!DOCTYPE html>
<html>
	<head>
		<title>highlight</title>
		
		<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.0/jquery.min.js"></script>
	
		 <link href="main.css" type="text/css"  rel="stylesheet"/>
		 
	</head>
	<body id='dolor'>
<p >
    Lorem ipsum dolor sit amet, consectetuer adipiscing elit.
</p>
<p>
    Quisque bibendum sem ut lacus. Integer dolor ullamcorper libero.
    Aliquam rhoncus eros at augue. Suspendisse vitae mauris.
</p>
 <script type="text/javascript" src="main.js" charset="utf-8"></script>
	</body>
</html>

查看更多
大哥的爱人
7楼-- · 2018-12-31 05:08
$(function () {
    $("#txtSearch").keyup(function (event) {
        var txt = $("#txtSearch").val()
        if (txt.length > 3) {
            $("span.hilightable").each(function (i, v) {
                v.innerHTML = v.innerText.replace(txt, "<hilight>" + txt + "</hilight>");
            });

        }
    });
});

Jfiddle here

查看更多
登录 后发表回答