Selectize dropdown selection outside of bootstrap modal window causes the modal to close
Asked Answered
I

4

6

This is the very simple modal window that I am using to select a task.

<div id="add_task_modal" class="modal fade" tabindex="-1" role="dialog">
    <div class="modal-dialog" role="document">
        <div class="modal-content">
            <div class="modal-header">
                <h5 class="modal-title">Lookup Task</h5>
            </div>
            <div class="modal-body">
                <select id="select_customer_name" placeholder="Select a customer..."></select>
                <select id="select_project_name" placeholder="Select a project..."></select>
                <select id="select_task_name" placeholder="Select a task..."></select>
            </div>
            <div class="modal-footer">
                <button id="submit_add_task" class="btn btn-primary">Add</button>
                <button class="btn btn-primary" data-dismiss="modal">Cancel</button>
            </div>
        </div>
    </div>
</div>

There are three <select>s inside that are selectized. I can post this code if requested but I do not think it is relevant.

Basically the problem is that the dropdowns extend beyond the bottom of the modal window in some cases (this is what I want), and if you click on an option that is below the bottom it will close the modal. Obviously I can make the modal static but that is not the functionality I want.

Is there any way to prevent the click event from closing the modal in this circumstance?

EDIT: These are the two click events I get when clicking on one such <option>:

click { target: div#add_task_modal.modal.fade.show , buttons: 0, clientX: 1251, clientY: 370, layerX: 1251, layerY: 370 }

click { target: div#add_task_modal.modal.fade, buttons: 0, clientX: 1251, clientY: 370, layerX: 1251, layerY: 370 }

Illfavored answered 18/8, 2020 at 14:48 Comment(7)
Add a click handler to the dropdown that calls stopPropagation() so the click event doesn't bubble up to the rest of the DOM?Faludi
$(".selectize-dropdown").click(function(evt) { evt.stopPropagation(); evt.preventDefault(); }); This is what I have tried, but no use.Illfavored
I created a vanilla Bootstrap modal with <select> options that extend below the modal. When I click any option that extends below the modal, it does not close the modal. I'm guessing you either have a JS error, or it's a symptom of selectize.js. Can you post a minimal, reproducible example?Faludi
This is the best I could do: jsfiddle.net/ysjp74wkIllfavored
I added click handlers on both the modal and the Selectize object to call stopPropagation() and preventDefault() but unfortunately it had no effect. At this point I'm out of ideas, sorry! You may want to look into how Selectize handles events and keep investigating.Faludi
Can you please a minimal working example of this ? Like js fiddleYbarra
I did, see my comment above.Illfavored
R
2

This may not be a clean solutuion. But you can set the modal to static when your "select" is opened, and change it back when select is clicked or lost focus.

$("#select_customer_name").on("focus", function(e) {
    modal.data('bs.modal')._config.backdrop = 'static';
});

$("#select_customer_name").on("blur", function(e) {
    modal.data('bs.modal')._config.backdrop = true;
});

Note: This works on Chrome, not on Firefox.

Revetment answered 24/8, 2020 at 2:29 Comment(4)
I would be fine using a solution like this, but this particular approach doesn't work. The backdrop is set back to non-static before the event which closes it fires so it closes anyway. This does prevent it from closing if you click outside of the options menu while it is open, but that is not what I care about.Illfavored
@AlexCoats How about use the 'focusout' event to set the 'backdrop' back to true.Revetment
There is no focusout event on the select, but I tried with blur and it also did not work. Here is an updated jsfiddle. jsfiddle.net/28mrne0kIllfavored
I am accepting this as the answer because, as you said, this solution does work on Chrome. Unfortunately for me, I am using Firefox, but it seems that nobody has a better option than this.Illfavored
E
1

I like to suggest using attribute data-backdrop with value "static" and data-keyboard with value "false".

Here's a link!

  [1]: https://jsfiddle.net/owmfj98s/
Endanger answered 29/8, 2020 at 18:19 Comment(1)
I stated above that although this is an option, it is not the functionality I want.Illfavored
R
1

What you should do is place the select inside a div, in that div you apply class="d-flex bg-transparent", in addition you must use a high z-index in the div so that it overlaps the modal and must manipulate the height and width of the div so that it fills the entire space where there will be a click.

Something like:

<div class="row d-flex  bd-highlight">
    <div class="flex-fill bg-transparent justify-content-around" style="z-index:9999; width:auto; height:auto;">
    <select class="form-control bg-white">
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    </select></div>

 <div class="flex-fill bg-transparent justify-content-around" style="z-index:9999; width:auto; height:auto;">
    <select class="form-control bg-white">
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    </select></div>
 <div class="flex-fill bg-transparent justify-content-around" style="z-index:9999; widht:auto; height:auto;">
    <select class="form-control bg-white">
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    <option>test--test<option>
    </select></div>
</div>

You need a parent element, it doesn't have to be a div, but the select must be in the middle of it. You must define Width and Height on your own.

Regnant answered 30/8, 2020 at 20:21 Comment(0)
B
1

Is there any way to prevent the click event from closing the modal in this circumstance?

I checked your code and found that, the modal is only closed when select the same option each time. Example:

  1. Select "Thing 7", then "Thing 7" --> Modal is closed (problem happend)
  2. Select "Thing 7", then select "Thing 8" --> Modal is not closed

I found reason is that:

  • When select the same "thing": Selectize just close the list (hide the DOM elements). The sequence of action as bellow:
    1. mousedown: the event is fired on the element in the list
    2. Selectize close hide list
    3. mouseup: the event is fired on the ".modal.face" element (the element located under the mouse) Refer to click event doc, the click event is fired on ".modal.face" element and cause close the modal
  • When select the different "thing": in the mousedown event, Selectize re-create the list (destroy and create DOM object again). So that, the target of mousedown event is destroyed, and the click event not fired.

"Click outside of modal will cause modal to close" is the default behavior of "Modal". So, fix it may need some trick which I not recommend. But, if you still want to fix it, you can do as bellow:

$(document).ready(function() {
    $("#select").selectize({
        valueField: 'id',
        labelField: 'val',
        searchField: 'val',
        create: false,
        maxItems: 1,
        onDropdownClose: function(dd) {  // <-- Add this
            this.refreshOptions(false);
        }
    });
    
    ...
  • Adding refreshOptions inside onDropdownClose will re-create the DOM elements and click event is cancelled.
Beiderbecke answered 31/8, 2020 at 9:25 Comment(1)
That's not correct. The modal closes because the click event is on an item outside of the modal window. It is easily reproducible.Illfavored

© 2022 - 2024 — McMap. All rights reserved.