J'ai jQuery mais je ne suis pas sûr s'il a des aides de tri intégrés. Je pourrais faire un tableau 2d des propriétés text
, value
, et selected
de chaque élément, mais je ne pense pas que javascript construit en Array.sort()
fonctionnerait correctement.Quel est le moyen le plus efficace pour trier les options d'un Html Select par valeur, tout en préservant l'élément actuellement sélectionné?
Répondre
options d'extraction dans un tableau temporaire, trier, puis reconstruisent la liste:
var my_options = $("#my_select option");
var selected = $("#my_select").val();
my_options.sort(function(a,b) {
if (a.text > b.text) return 1;
if (a.text < b.text) return -1;
return 0
})
$("#my_select").empty().append(my_options);
$("#my_select").val(selected);
Mozilla's sort documentation (en particulier le compareFunction) et Wikipedia's Sorting Algorithm page sont pertinents.
Si vous voulez faire le cas de tri insensible, remplacez text
avec text.toLowerCase()
La fonction de tri ci-dessus illustre comment trier. Le tri précis des langues autres que l'anglais peut être complexe (voir le unicode collation algorithm). En utilisant localeCompare dans la fonction de tri est une bonne solution, par exemple:
my_options.sort(function(a,b) {
return a.text.localeCompare(b.text);
});
revenir sur cette question 3 ans plus tard, et cette route semble être la bonne voie à suivre – travis
Notez que cela est sensible à la casse - c'est-à-dire, il va trier toutes les choses qui commencent par des majuscules avant les choses qui commencent par des lettres minuscules. Si cela n'est pas souhaitable, ajoutez juste un '.toUpperCase()' après chaque '.text' –
Aussi, il ne conservera pas l'option actuellement sélectionnée dans tous les navigateurs en l'état (Chrome se souvient de ce qui a été sélectionné, mais firefox et ie didn ' t, et sélectionné le dernier élément après la lecture des options). Pour résoudre ce problème, sauvegardez la valeur sélectionnée avant de trier, puis resélectionnez-la. -à-dire, avant tout faire 'var selected = $ ("# my_select") val().' puis après les options triées ont été jointes, restaurez la val, par exemple '$ ("# my_select") .val (sélectionné); ' –
Eh bien, dans IE6, il semble trier sur le point de tableau imbriqué [0]:
function sortSelect(selectToSort) {
var arrOptions = [];
for (var i = 0; i < selectToSort.options.length; i++) {
arrOptions[i] = [];
arrOptions[i][0] = selectToSort.options[i].value;
arrOptions[i][1] = selectToSort.options[i].text;
arrOptions[i][2] = selectToSort.options[i].selected;
}
arrOptions.sort();
for (var i = 0; i < selectToSort.options.length; i++) {
selectToSort.options[i].value = arrOptions[i][0];
selectToSort.options[i].text = arrOptions[i][1];
selectToSort.options[i].selected = arrOptions[i][2];
}
}
Je vais voir si cela fonctionne dans d'autres navigateurs ...
Edit: il fonctionne en Firefox aussi, woo hoo!
Y a-t-il un moyen plus simple que celui-ci? Y at-il une méthode intégrée dans javascript ou jQuery qui trie les sélections qui me manquent, ou est-ce la meilleure façon?
Notez que cette fonction ne triera pas les éléments ** option **; il change le * [valeur, texte, sélectionné] * sur les éléments existants de sorte qu'ils sont triés (par valeur dans ce cas). C'est suffisant pour la plupart des applications, mais si vous avez d'autres attributs (CSS, info-bulles, etc.), cette approche ne suffira pas. – NVRAM
Array.sort()
par défaut de convertir chaque élément en chaîne, et en comparant ces valeurs. Donc ["value", "text", "selected"]
est trié comme "value, text, selected"
. Ce qui fonctionnera probablement bien, la plupart du temps.
Si vous voulez trier la valeur seule, ou d'interpréter la valeur comme un nombre, alors vous pouvez passer une fonction de comparaison en sort():
arrOptions.sort(function(a,b) { return new Number(a[0]) - new Number(b[0]); });
Il y a a closed jQuery ticket pour une sorte qui devrait fonctionner, mais juste n'était pas inclus dans le noyau.
jQuery.fn.sort = function() {
return this.pushStack([].sort.apply(this, arguments), []);
};
de a Google Groups thread Referenced, je pense que vous venez de passer dans une fonction qui est utilisée pour trier, comme si
function sortSelect(selectToSort) {
jQuery(selectToSort.options).sort(function(a,b){
return a.value > b.value ? 1 : -1;
});
}
it helps!
Problèmes liés à la fonction sortSelect: les options d'égalité ne sont pas prises en compte. Trie en fonction de la valeur et non du texte. Les objets jQuery n'ont pas de propriété nommée "options". Cela n'a aucun effet, car vous devez ajouter les options à un nouvel élément select. – simon
Je viens enveloppai l'idée de Mark dans une fonction jquery
$('#your_select_box').sort_select_box();
fonction JQuery:
$.fn.sort_select_box = function(){
var my_options = $("#" + this.attr('id') + ' option');
my_options.sort(function(a,b) {
if (a.text > b.text) return 1;
else if (a.text < b.text) return -1;
else return 0
})
return my_options;
}
comment pourrais-je l'ajouter à mon événement click actuel? \t $ ('# addwire'). Click (function() { \t return! $ ('# Wireselection option: sélectionnée'). Remove(). AppendTo ('# wires'). Sort_select_box(); \t}) ; ne semble pas fonctionner – mcgrailm
Je ne peux pas sembler obtenir ce à travailler à atll – mcgrailm
modifié Tom répondez légèrement ci-dessus afin qu'il modifie réellement le contenu de la boîte de sélection à trier, plutôt que de simplement renvoyer les éléments triés.
$('#your_select_box').sort_select_box();
fonction jQuery:
$.fn.sort_select_box = function(){
// Get options from select box
var my_options = $("#" + this.attr('id') + ' option');
// sort alphabetically
my_options.sort(function(a,b) {
if (a.text > b.text) return 1;
else if (a.text < b.text) return -1;
else return 0
})
//replace with sorted my_options;
$(this).empty().append(my_options);
// clearing any selections
$("#"+this.attr('id')+" option").attr('selected', false);
}
Cette réponse est près du sommet, mais ne sélectionne pas correctement – thouliha
Rappelez-vous: si vous souhaitez utiliser le sélecteur de contexte, juste concaténer l'ID ne fonctionnera pas
$.fn.sort_select_box = function(){
var my_options = $("option", $(this));
my_options.sort(function(a,b) {
if (a.text > b.text) return 1;
else if (a.text < b.text) return -1;
else return 0
});
$(this).empty().append(my_options);
}
// Usando:
$("select#ProdutoFornecedorId", $($context)).sort_select_box();
Ceci est une meilleure solution. Déclarer une fonction globale à JQuery
$.fn.sortSelect = function() {
var op = this.children("option");
op.sort(function(a, b) {
return a.text > b.text ? 1 : -1;
})
return this.empty().append(op);
}
Et appeler la fonction à partir du code.
$("#my_select").sortSelect();
J'ai utilisé une variation sur ce, en enveloppant la partie intérieure en $ (ce) .each() afin que je puisse passer un sélecteur pour gérer plus d'un à la fois. –
Aussi, vous devez utiliser '$ (this)' au lieu de simplement 'this' –
La solution je l'ai mentionné dans mon commentaire à @Juan Perez
$.fn.sortOptions = function(){
$(this).each(function(){
var op = $(this).children("option");
op.sort(function(a, b) {
return a.text > b.text ? 1 : -1;
})
return $(this).empty().append(op);
});
}
Utilisation:
$("select").sortOptions();
Cela peut encore être améliorée, mais je ne l'ai pas besoin d'ajouter une plus de cloches ou de sifflets :)
Note à moi-même (puisque je suis revenu à cette question plusieurs fois via google): voici une bonne solution que vous écrivez e: https://gist.github.com/1072537 – travis