Select2 open dropdown on focus

前端 未结 16 2199
陌清茗
陌清茗 2020-12-05 00:21

I have a form with multiple text inputs and some select2 elements. Using the keyboard to tab between fields works fine - the Select2 element behaves like a form element and

相关标签:
16条回答
  • 2020-12-05 00:44

    For me using Select2.full.js Version 4.0.3 none of the above solutions was working the way it should be. So I wrote a combination of the solutions above. First of all I modified Select2.full.js to transfer the internal focus and blur events to jquery events as "Thomas Molnar" did in his answer.

    EventRelay.prototype.bind = function (decorated, container, $container) {
        var self = this;
        var relayEvents = [
          'open', 'opening',
          'close', 'closing',
          'select', 'selecting',
          'unselect', 'unselecting',
          'focus', 'blur'
        ];
    

    And then I added the following code to handle focus and blur and focussing the next element

    $("#myId").select2(   ...   ).one("select2:focus", select2Focus).on("select2:blur", function ()
    {
        var select2 = $(this).data('select2');
        if (select2.isOpen() == false)
        {
            $(this).one("select2:focus", select2Focus);
        }
    }).on("select2:close", function ()
    {
        setTimeout(function ()
        {
            // Find the next element and set focus on it.
            $(":focus").closest("tr").next("tr").find("select:visible,input:visible").focus();            
        }, 0);
    });
    function select2Focus()
    {
        var select2 = $(this).data('select2');
        setTimeout(function() {
            if (!select2.isOpen()) {
                select2.open();
            }
        }, 0);  
    }
    
    0 讨论(0)
  • 2020-12-05 00:46

    I've tried a pretty ugly solution but it fixed my problem.

        var tabPressed = false;
    
        $(document).keydown(function (e) {
            // Listening tab button.
            if (e.which == 9) {
                tabPressed = true;
            }
        });
    
        $(document).on('focus', '.select2', function() {
            if (tabPressed) {
                tabPressed = false;
                $(this).siblings('select').select2('open');
            }
        });
    
    0 讨论(0)
  • 2020-12-05 00:47

    I tried a number of these and finally came up with the following that works for me with Select2 4.0.1. element is the <select> element.

    $.data(element).select2.on("focus", function (e) {
        $(element).select2("open");
    });
    
    0 讨论(0)
  • 2020-12-05 00:48

    Probably after the selection is made a select2-focus event is triggered.

    The only way I found is a combination of select2-focus and select2-blur event and the jQuery one event handler.

    So the first time the element get the focus, the select2 is opened for one time (because of one), when the element is blurred the one event handler is attached again and so on.

    Code:

    $('#test').select2({
        data: [{
            id: 0,
            text: "enhancement"
        }, {
            id: 1,
            text: "bug"
        }, {
            id: 2,
            text: "duplicate"
        }, {
            id: 3,
            text: "invalid"
        }, {
            id: 4,
            text: "wontfix"
        }],
        width: "300px"
    }).one('select2-focus', select2Focus).on("select2-blur", function () {
        $(this).one('select2-focus', select2Focus)
    })
    
    function select2Focus() {
        $(this).select2('open');
    }
    

    Demo: http://jsfiddle.net/IrvinDominin/fnjNb/

    UPDATE

    To let the mouse click work you must check the event that fires the handler, it must fire the open method only if the event is focus

    Code:

    function select2Focus() {
        if (/^focus/.test(event.type)) {
            $(this).select2('open');
        }
    }
    

    Demo: http://jsfiddle.net/IrvinDominin/fnjNb/4/

    UPDATE FOR SELECT2 V 4.0

    select2 v 4.0 has changed its API's and dropped the custom events (see https://github.com/select2/select2/issues/1908). So it's necessary change the way to detect the focus on it.

    Code:

    $('.js-select').select2({
        placeholder: "Select",
        width: "100%"
    })
    
    $('.js-select').next('.select2').find('.select2-selection').one('focus', select2Focus).on('blur', function () {
        $(this).one('focus', select2Focus)
    })
    
    function select2Focus() {
        $(this).closest('.select2').prev('select').select2('open');
    }
    

    Demo: http://jsfiddle.net/IrvinDominin/xfmgte70/

    0 讨论(0)
  • 2020-12-05 00:50

    I've had the problem which was two pronged:
    1. In a form with multiple select2 elements, the dropdown won't open on tab, and you need to press space key to open it
    2. Once you have made a selection, the tabindex won't be honored and you have to manually click on the next input field

    While the usual suggestions worked, I came up with my own version, since a library script was doing the conversion of normal select to select2, and hence I had no control over this initialization.

    Here is the code that worked for me.

    Tab to open

    $(document).on("focus", ".select2", function() {
        $(this).siblings("select").select2("open");
    });
    

    Move to next on selection

    var inputs = $("input,select"); // You can use other elements such as textarea, button etc. 
                                    //depending on input field types you have used
    $("select").on("select2:close",function(){
        var pos = $(inputs).index(this) + 1;
        var next = $(inputs).eq(pos);
        setTimeout( function() {
            next.focus();
            if (next.siblings(".select2").length) { //If it's a select
                next.select2("open");
            }
        }, 500); //The delay is required to allow default events to occur
    });
    

    Hope this helps.

    0 讨论(0)
  • 2020-12-05 00:53

    The problem is, that the internal focus event is not transformed to jQuery event, so I've modified the plugin and added the focus event to the EventRelay on line 2063 of Select2 4.0.3:

    EventRelay.prototype.bind = function (decorated, container, $container) {
        var self = this;
        var relayEvents = [
          'open', 'opening',
          'close', 'closing',
          'select', 'selecting',
          'unselect', 'unselecting',
          'focus'
        ];
    

    Then it is enough to open the select2 when the focus occurs:

    $('#select2').on('select2:focus', function(evt){
        $(this).select2('open');
    });
    

    Works well on Chrome 54, IE 11, FF 49, Opera 40

    0 讨论(0)
提交回复
热议问题