Search code examples
jqueryajaxjquery-select2dropdownjquery-select2-4

Select2 dependent dropdown with templating and search


I have 2 lists. When I select a value in the first one, it updates the options in the second list. Only the second list is a Select2.

enter image description here

I made it work but the search functionality of Select2 doesn't work.

enter image description here enter image description here

If I check the DOM, I notice that the options generated by Select2 don't have a text. Is it because of it that the search doesn't work ?

enter image description here

Here is my JS code :

$('.category').change(function(event) {
    var measure = $(this).parents('.row').find('.measure');

    // Modify placeholder when searching
    measure.prop('disabled', true).select2({placeholder: "Searching..."});

    // Remove existing options of the list (of a previous usage)
    measure.children('option').each(function(index, el) {
        if ($(el).val().length > 0)
            $(el).remove();
    });

    var DATA = 'tagcat=' + $(this).val();

    $.ajax({
        type    : "GET",
        url     : $('.custom-table-container').data('search-js'),
        data    : DATA,
        cache   : false,
        success : function(response) {
            var data = JSON.parse(response);

            // Update the measures list    
            measure.select2({
                allowClear       : true,
                data             : data.items,
                escapeMarkup     : function (markup) { return markup; },
                templateResult   : formatTag,
                templateSelection: formatTagSelect
            }).prop('disabled', false);
        }
    });
});

I was able to make the search work in adding manually the HTML options in the list but I loose the result template...

enter image description here enter image description here

Code :

$.ajax({
    // ...
    success : function(response) {
        var data = JSON.parse(response);

        data.items.forEach(function(tag) {
            // create the option and append to Select2
            var option = new Option(tag.name, tag.id, false, false);
            measure.append(option);
        });

        measure.select2({
            allowClear          : true,
            data                : data.items,
            escapeMarkup        : function (markup) { return markup; },
           templateResult       : formatTag,
           templateSelection    : formatTagSelect
        }).prop('disabled', false);
    }
});

How am I suppose to code this to have both templating and search ?


Solution

  • Sorry, I just found where I was wrong : I didn’t show the right data inside my template result function.

    So, in a case it worked because a specific data didn’t exist and, in the other case, that data existed and it replaced a specific template I did… It’s not very effective to work on it a friday afternoon. :D

    So the right way to do this is to add manually the options of the select in the DOM and init the Select2 after.

    $.ajax({
        // ...
        success : function(response) {
            var data = JSON.parse(response);
    
            // create options in the DOM
            data.items.forEach(function(tag) {
                // create the option and append to Select2
                var option = new Option(tag.name, tag.id, false, false);
                measure.append(option);
            });
    
            // init Select2 with data
            measure.select2({
                theme               : "bootstrap4",
                placeholder         : "- Select a measure -",
                allowClear          : true,
                data                : data.items,
                escapeMarkup        : function (markup) { return markup; },
               templateResult       : formatTag,
               templateSelection    : formatTagSelect
            });
        }
    });