Multiselectable jQuery plugin

A Progressive Enhancement to <select multiple>

Selecting multiple values on a standard <select multiple> HTML control is an overwhelming task for a normal person. For a skilled computer user it is an exercise in frustration at best.

Multiselectable removes the issue of using keyboard modifiers to make a selection. It also makes it easier to see what elements are actually selected.

Multiselectable is certainly not a new idea. However, I could not find a proper implementation in jQuery. There have been other, not so traditional solutions to this problem as well.

Download Multiselectable

Multiselectable will turn this…

…into this:

How to Use

You must include the jQuery library, multiselectable.js and a one line of JavaScript to activate Multiselectable on the select element you choose. Here is an example how this page uses the plugin:

<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"
	type="text/javascript"></script>
<script src="multiselectable.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
	$('.multi').multiselectable();
});
</script>

Here is some useful CSS you should also include to your page if you want it to resemble usable:

.multiselectable { width:500px; display:block; overflow: hidden; width: 100%; }
.multiselectable select, .multiselectable div { width: 200px; float:left; }
.multiselectable div * { display: block; margin: 0 auto; }
.multiselectable div { display: inline; }
.multiselectable .m-selectable-controls { margin-top: 3em; width: 50px; }
.multiselectable .m-selectable-controls button { margin-top: 1em; }

You can customize the default markup to suit your needs, just keep the class names and id:s intact. However, if you just need to change the labels or the button text, you can set them easily. Here is an example:

<script type="text/javascript">
$(document).ready(function() {
	$('.multi').multiselectable({
		selectableLabel: 'All countries',
		selectedLabel: 'Countries I\'ve visited',
		moveRightText: '+',
		moveLeftText: '-'
	});
});
</script>

Some Additional Niceties

  1. If you include the SortOptions plugin from the Select box manipulation plugin collection, then by default the options will be sorted automatically. Options will remain in their order even if they are transferred back and forth.
  2. Double-clicking an option will move it to the other side.
  3. Hitting the enter key will move selected options.

Technical Details for Server-side Developers

Multiselectable hides the original select element but does not remove it from the page. Multiselectable updates the original options to match those that are transferred right. This means that it should not interfere with any kind of sane server-side technology.

Accessibility

Multiselectable is fully functional using only a keyboard. Labels correctly point to the right elements, even when there are multiple Multiselectable controls within the page.

License and Copyright

Multiselectable copyright © Aki Björklund, 2009. Licensed under MIT.

Download Multiselectable

23 Replies to “Multiselectable jQuery plugin”

  1. Do you know how to add a “search” box to multiselectable element?

  2. Hello,
    Any chance you could provide a version compatible with jQuery 1.4.2? It would be greatly appreciated.

  3. This page is actually running 1.4.2 (even thou the example states otherwise) and it looks like it’s working ok to me. What seems to be the problem?

  4. I have the problem in IE (7 and 8). When I select one of the options and press the button to move it to the selected options, it disappears from the not-selected options but it does not appear on the selected ones.

    I was suspecting some strange behavior of the clone() function, but it is really difficult to pinpoint the issue in IE…

  5. By the way, on the page it seems to be working for me as well in IE, so the problem lies somewhere in my code…
    Thank you anyway for your quick answer!

  6. Hi Aki,

    Looks like it is not working in IE 7, but it is in IE 8. So it is probably not jQuery related.

    It looks like the option is moved between the from and to select controls, but the behaviour of the control breaks after doing this. We use your control on a form page, where the value gets posted correctly to the server, which means that the value is correctly added to the other selector.

    If you could look into this (with IE 7) and possibly fix this, that would be great!

    Regards, Hendrik

  7. The example on this page doesn’t work right for me in IE 9 Beta 9.0.7930.

    The first items I add to Selected only show the first letter. However after adding some more they will be suddenly expanded to the correct length. Weird!

    PS: Thank you for this great plugin!

  8. First of all, thanks for an awesome plug-in.
    I was planning to write something like this for my needs, but after a quick google-ing I found your plug-in. So, again, huge thank you for saving me some time!

    I just have one suggestion. To make this plug-in compatible with other JS frameworks (e.g. prototype), I recommend using jQuery instead of $ as per http://docs.jquery.com/Using_jQuery_with_Other_Libraries


    var matchedElem = master.find('option[value="' + $(this).val() + '"]');

    is better if replaced with:

    var matchedElem = master.find('option[value="' + jQuery(this).val() + '"]');

    I had to make this change to make it work for a project I took over (uses Prototype), which I’m slowing migrating to jQuery. In the mean time, making this change (along with jQuery.noConflict();) allowed me to continue using Prototype and JQuery (1.4.4) along with your plug-in without any further issues.

  9. The new changes result in JS error:

    $(this).val is not a function in
    var matchedElem = master.find('option[value="' + $(this).val() + '"]');

    I’m using this to resolve any conflict with prototype.js

    var $jq = jQuery.noConflict();

    $jq(document).ready(function() {
    $jq('.multi').multiselectable({
    selectableLabel: 'Available',
    selectedLabel: 'Selected',
    moveRightText: '>>',
    moveLeftText: '<<'
    });
    });

  10. I still think the original v1.0 of you script where you use jQuery instead $ would cause the least amount of problems when including multiple JS frameworks.

  11. I tried adding Prototype temporarily to this page, and the plugin worked fine in its current form (after tweaking some other JS-code on the page). Are you sure you are using the plugin as is?

  12. I do have older prototype 1.6.1, that’s what the existing app uses. Along with some other stuff like lowpro, datepicker, etc.
    Then I have jQuery min v1.4.4 (latest).
    And then your plug-in as is.
    Then a custom.js, which includes that little bit I copy/pasted earlier with the noConflict() call.

    As I said, just replacing one instance of $ with jQuery in version 1.0 of your plug-in makes it all work just fine. So I’m just going to keep it that way.

    Hmmm…

  13. Arghhhh… submitted prematurely.
    Is there any way to add support for optgroup?

Comments are closed.