вторник, 20 апреля 2010 г.

вторник, 6 апреля 2010 г.

html select box выделить все опции

Допустим у нас есть multiple select box с большим количеством options, ну скажем 450. Надо выделить все.
Рассмотрим 2 способа.
Решение 1. В лоб
selectAll_method1 = function(selectBoxId, selected) {
    var selectBox = document.getElementById(selectBoxId);
    for (var i=0; i < selectBox.options.length; i++) {
         selectBox.options[i].selected = selected;
    }
}



В IE 8 это происходит очень долго. Мы визуально видим как браузер пробегается по опциям при этом проматывая скролл. Решение 2. Пересоздание опций.
selectAll_method2 = function(selectBoxId, selected) {
    var selectBox = document.getElementById(selectBoxId);
    var optionsCopy = new Array();
    for (var i=0; i < selectBox.options.length; i++) {
        var option = selectBox.options[i];
        optionsCopy[i] = new Option(option.text,option.value,selected,selected);
    }
    selectBox.options.length = 0;
    for (var i=0; i < optionsCopy.length; i++) {
        selectBox.options[i] = optionsCopy[i];
    }
}



Странно, но пересоздание опций работает значительно быстрее. Сравним?
IE 7IE 8FF 3.6Chrome 4.1
Метод 1900160011707
Метод 2270300460450

Очевидно что в IE8 есть досадный баг связаный с выделением. Хром приятно порадовал.
Плюсы метода 2.
1. Почти везде быстрее, кроме хрома
2. Визуально приятнее так как селект бокс не прокручивается вниз.
Минусы метода 2.
1. Пересоздание не копируют свойства опций, например, class. При необходимости метод можна расширить, правда не известно как это отобразится на скорости его выполнения.
2. Пересоздание будет происходить всегда. В случае первого метода, если все опции уже выбраны метод исполняется быстро, так как менять состояние опций не приходится.
3. Снятие выделения методом 1 везде быстрее
4. Это хак.

Итого: для выделения юзаем метод 2, для снятия выделения - метод 1.