javascriptajaxhighlightdom7

Highlight Ajax Response with Javascript


I'm trying to highlight a query inside a text coming from an ajax response, before constructing HTML with it and pasting that into the DOM. Right now I'm using this code snippet:

function highlightWords(line, word, htmltag) {
    var tag = htmltag || ["<b>", "</b>"];
    var regex = new RegExp('(' + preg_quote(word) + ')', 'gi');
    return line.replace(regex, tag[0] + "$1" + tag[1]);
}

function preg_quote(str) {
    return (str + '').replace(/([\\\.\+\*\?\[\^\]\$\(\)\{\}\=\!\<\>\|\:])/g, "\\$1");
}

However, this is not capeable of highlighting different words if the query is something like sit behind. It will only highlight the complete phrase and not the single words. It also doesn't care about HTML tags and that produces unpretty results if the query is span for example...

I've found various libraries which handle highlighting way better, like https://markjs.io/ or https://www.the-art-of-web.com/javascript/search-highlight/

Those libraries though always want to highlight content which is already present in the DOM.

My search gets an ajax response, which I then turn into HTML with JS and paste the complete HTMLString into a parent container using DOM7 (which is similar to jQuery). Therfor I would prefer to highlight the text before creating the HTMLString and pasting it in the DOM.

Any ideas?


Solution

  • Snippet style: Warning: this uses DOM7 as per Question

    Overview: Instead of appending the whole text as HTML string to your #container, Append the portions of normal text, as text, and the highlighted elements as elements, so you can style them at will.

    var text // your ajax text response
    var strQuery = 'sit behind' // your query string 
    
    var queryWords = strQuery.split(' ')
    var textWords = text.split(' ')
    var bufferNormalWords  = []
    
    textWords.forEach(function (word) {
        if (queryWords.indexOf(word) != -1) { // found
          var normalWords = bufferNormalWords.splice(0, buffer.length) // empty buffer
          // Your DOM7 commands
          $$('#container').add('span').text(normalWords.join(' ')) // normal text
          $$('#container').add('span').css('color', 'red').text(word + ' ') // why not red          
        }
        else bufferNormalWords.push(word)
    })
    

    Do not mess up with text becoming HTMLStrings, just set text, and create the necesary elements to style them as you want with your DOM7.