views:

3409

answers:

3

Hi,

I'm trying to build a web page with a number of drop-down select boxes that load their options asynchronously when the box is first opened. This works very well under Firefox, but not under Internet Explorer.

Below is a small example of what I'm trying to achieve. Basically, there is a select box (with the id "selectBox"), which contains just one option ("Any"). Then there is an onmousedown handler that loads the other options when the box is clicked.

<html>
 <head>
  <script type="text/javascript">
    function appendOption(select,option) {
      try {
        selectBox.add(option,null); // Standards compliant.
      } catch (e) {
        selectBox.add(option);      // IE only version.
      }
    }

    function loadOptions() {
      // Simulate an AJAX request that will call the
      // loadOptionsCallback function after 500ms.
      setTimeout(loadOptionsCallback,500);
    }

    function loadOptionsCallback() {
      var selectBox = document.getElementById('selectBox');
      var option = document.createElement('option');
      option.text = 'new option';
      appendOption(selectBox,option);
    }
  </script>
 </head>
 <body>
  <select id="selectBox" onmousedown="loadOptions();">
   <option>Any</option>
  </select>
 </body>
</html>

The desired behavior (which Firefox does) is:

  1. the user see's a closed select box containing "Any".
  2. the user clicks on the select box.
  3. the select box opens to reveal the one and only option ("Any").
  4. 500ms later (or when the AJAX call has returned) the dropped-down list expands to include the new options (hard coded to 'new option' in this example).

So that's exactly what Firefox does, which is great. However, in Internet Explorer, as soon as the new option is added in "4" the browser closes the select box. The select box does contain the correct options, but the box is closed, requiring the user to click to re-open it.

So, does anyone have any suggestions for how I can load the select control's options asynchronously without IE closing the drop-down box?

I know that I can load the list before the box is even clicked, but the real form I'm developing contains many such select boxes, which are all interrelated, so it will be much better for both the client and server if I can load each set of options only when needed.

Also, if the results are loaded synchronously, before the select box's onmousedown handler completes, then IE will show the full list as expected - however, synchronous loading is a bad idea here, since it will completely "lock" the browser while the network requests are taking place.

Finally, I've also tried using IE's click() method to open the select box once the new options have been added, but that does not re-open the select box.

Any ideas or suggestions would be really appreciated!! :)

Thanks!

Paul.

+1  A: 

Have you considered calling the loadOptions method in the onblur event of one of the other interrelated fields on the form? This would load the list into the drop down box before it is clicked, but the behavior should still be similar.

I think you are going to have explore slightly different options to obtain what you want as you are probably stuck with Internet Explorer closing that drop down list if you use the onmousedown or onclick events. Another downside to using those events is if the user uses the keyboard to select the fields, your method may never get called.

Bryan Friedman
+1  A: 

I would suggest to load the contents of the selects that don't depend on any other select boxes on page load. Then in the onchange event of those selects load the contents of the rest of the selects that depend on them.

Your idea is sound from a programming point of view, but you will get that lag between clicking on the select and it being populated with all the options which from the user's point of view looks kind of sloppy.

Svet
+1  A: 

I found a solution to this, the problem seems to lie in IE's implementation of onclick, hover, mouseover etc. After the items are added to the dropdown, the dropdown closes. If you instead of providing the method in the select attribute, let jquery add the function at runtime it works.

$(function() {
    jQuery(".selectBox").live("focus", function() {
       loadOptions();
     });
});

The whole page:

<html>
<head>
    <script src="jquery-latest.js" type="text/javascript"/>
</head>
<body>
    <select id="selectBox" onmousedown="loadOptions();">
        <option>Any</option>
    </select>
    <script type="text/javascript">
        $(function() {
            jQuery(".selectBox").live("focus", function() {
                loadOptions();
            });
        });
        function appendOption(select, option) {
            try {
                selectBox.add(option, null); // Standards compliant.
            } catch (e) {
                selectBox.add(option);      // IE only version.
            }
        }

        function loadOptions() {
            // Simulate an AJAX request that will call the
            // loadOptionsCallback function after 500ms.
            setTimeout(loadOptionsCallback, 500);
        }

        function loadOptionsCallback() {
            var selectBox = document.getElementById('selectBox');
            var option = document.createElement('option');
            option.text = 'new option';
            appendOption(selectBox, option);
        }
    </script>
</body>

Hugo Forte