最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Select2 Custom Matcher for Non-Adjacent Keywords - Stack Overflow

programmeradmin4浏览0评论

I use Select2 in my app to allow for searching a dropdown with about 1200 options.

I am currently making use of the default implementation of Select2's matcher, which works well as long as keywords are adjacent in the search results:

function(term, text) { return text.toUpperCase().indexOf(term.toUpperCase())>=0; }

For example, a search for 'stackoverflow question' returns option 'Stackoverflow question about Select2'

I would however else like the matcher to return results based on non-adjacent keywords. For instance, I would also like it to return the above option when searching for 'stackoverflow select2'.

Would anyone have an idea how to create a custom matcher to allow for this behavior?

I use Select2 in my app to allow for searching a dropdown with about 1200 options.

I am currently making use of the default implementation of Select2's matcher, which works well as long as keywords are adjacent in the search results:

function(term, text) { return text.toUpperCase().indexOf(term.toUpperCase())>=0; }

For example, a search for 'stackoverflow question' returns option 'Stackoverflow question about Select2'

I would however else like the matcher to return results based on non-adjacent keywords. For instance, I would also like it to return the above option when searching for 'stackoverflow select2'.

Would anyone have an idea how to create a custom matcher to allow for this behavior?

Share Improve this question edited Jul 28, 2014 at 15:42 Charles 51.4k13 gold badges106 silver badges144 bronze badges asked Jul 27, 2014 at 11:21 ACDSLACDSL 872 silver badges7 bronze badges 2
  • Please note that tags are not keywords. Stuffing the tag list full of the same words that are in your question (search, keyword, mapper) will not help categorize it. Always be sure to read the descriptions that appear when selecting tags! – Charles Commented Jul 28, 2014 at 15:56
  • Thanks for the notice Charles, will do so in future posts! – ACDSL Commented Jul 28, 2014 at 16:11
Add a ment  | 

4 Answers 4

Reset to default 11

this is what i did in Select2 4. i wanted matcher to return only options that contains all of keywords entered (assuming keywords are search term splitted by " "). Matching is case insesitive.

        matcher: function (params, data) {
                // If there are no search terms, return all of the data
                if ($.trim(params.term) === '') {
                    return data;
                }
                // `params.term` should be the term that is used for searching
                // split by " " to get keywords
                keywords=(params.term).split(" ");
                // `data.text` is the text that is displayed for the data object
                // check if data.text contains all of keywords, if some is missing, return null
                for (var i = 0; i < keywords.length; i++) {

                    if (((data.text).toUpperCase()).indexOf((keywords[i]).toUpperCase()) == -1) 
                      // Return `null` if the term should not be displayed
                      return null;

                }
                // If here, data.text contains all keywords, so return it.
                return data;
            }

i know this is old topic, but maybe someone find this usefull.

If you have large amount of data or nested data then the permutation will take lot of time.

Try instead this for searching using Non-Adjacent Keywords.

Just put this function in your document.ready before initializing select2.

$(function () { 

    var keywords;

    $.fn.select2.defaults = $.extend($.fn.select2.defaults, {            
        placeholder: 'Select...',            
        matcher: function(term, text, option) {

            if ($.trim(term) === '') {
                return true;
            }             
            keywords = (term).split(" ");

            for (var i = 0; i < keywords.length; i++) {

                if ((text.toUpperCase()).indexOf((keywords[i]).toUpperCase()) == -1 )                        
                {                        
                    return false;
                }                                         
            }                
            return true;  
        }
    });

  $("#DropdownID").select2();

});

The Working example is here : http://makmilan.blogspot.in/2015/11/select2-custom-matcher-for-non-adjacent.html

Try this:

search Stackoverflow question, stackoverflow select2, select2 stackoverflow, about stackoverflow select2 question, question select2 about

<select id="e17_2" style="width:300px">
   <option alt="Stackoverflow question about Select2">Stackoverflow question about Select2</option>
   <option alt="Stackoverflow Other line ...">Stackoverflow Other line ...</option>
</select>

Copied from: https://stackoverflow./a/21745151/3710490

function permute(input, permArr, usedChars) {
    var i, ch;
    for (i = 0; i < input.length; i++) {
        ch = input.splice(i, 1)[0];
        usedChars.push(ch);
        if (input.length == 0) {
            permArr.push(usedChars.slice());
        }
        permute(input, permArr, usedChars);
        input.splice(i, 0, ch);
        usedChars.pop();
    }
    return permArr
};


$("#e17_2").select2({
    matcher: function(term, text) { 

                if (term.length == 0) return true;
                texts = text.split(" ");

                allCombinations = permute(texts, [], []);

                for(i in allCombinations){
                    if( allCombinations[i].join(" ").toUpperCase().indexOf(term.toUpperCase())==0 ){
                        return true;
                    }
                }

                return false;

    }
});

Look for all or part of imperativements words :

element.select2({
    matcher: function(term, text){
        if (term.length < 3) { return true }
        var terms = term.split(" ");
        var count = 0;
        var nbterm = terms.length;

        for(i in terms) {
            if (text.toUpperCase().match(new RegExp(terms[i], "i"))) { count++ }
                if(nbterm == count){
                    return true;
                }
             }
             return false;
         }
});
发布评论

评论列表(0)

  1. 暂无评论