jQuery hasClass () - проверить наличие нескольких классов

162

С участием:

if(element.hasClass("class"))

Я могу проверить один класс, но есть ли простой способ проверить, имеет ли «элемент» какой-либо из многих классов?

Я использую:

if(element.hasClass("class") || element.hasClass("class") ... )

Что не так уж плохо, но я думаю о чем-то вроде:

if(element.hasClass("class", "class2")

К сожалению, это не работает.

Есть ли что-то подобное?

Hans
источник

Ответы:

228

Как насчет:

element.is('.class1, .class2')
Matchu
источник
9
Нет, потому что это будет искать элементы, которые имеют оба класса. Я думаю, что Марсель ищет элементы с одним или несколькими классами.
Джайлз Ван Груизен
Только сейчас заметил, что у меня там 4 элемента id = "hello". Исправлена ​​версия для того, чтобы осчастливить валидаторов: jsbin.com/uqoku/2/edit
Matchu
1
@Matchu У меня была та же проблема, .hasClass()но ваше решение, похоже, сработало , спасибо
Насир
11
Это не работает для меня, но $('element').is('.class1.class2')сделал
iamchriswick
6
@iamchriswick: Это немного отличается от того, о чем просил OP. .class1.class2будет соответствовать элементам, которые имеют оба класса, но они искали элементы, которые соответствуют любому классу.
Матчу
291
element.is('.class1, .class2')

работает, но это на 35% медленнее, чем

element.hasClass('class1') || element.hasClass('class2')

введите описание изображения здесь

Если вы сомневаетесь в том, что я говорю, вы можете проверить на jsperf.com .

Надеюсь, это поможет кому-то.

Саймон Арнольд
источник
16
19% медленнее, большое дело. Программисты дороже.
Новакер
21
@DamianNowak, если эти программисты не хотят писать то, что составляет тривиальное количество кода, они, вероятно, не очень дорогие.
Аккума
2
... но я только что запустил это в jsperf для Chrome 21.0.1180 и метод is () теперь работает примерно на 20% быстрее. Но hasClass () кажется более читабельным.
Данял Айтекин
3
@psychobrm: Если вам нужно проверить 10 классов одновременно, то вам действительно нужно упростить имена ваших классов. Там нет причин для такой ерунды. :)
cHao
5
Лично не вижу необходимости оптимизации производительности. 12000 операций в секунду мне кажется достаточно быстрым. Я бы сказал, что пользуйтесь тем, что выглядит лучше для вас. Оптимизируйте производительность, когда возникнет такая необходимость.
3Dom
38
$.fn.extend({
    hasClasses: function (selectors) {
        var self = this;
        for (var i in selectors) {
            if ($(self).hasClass(selectors[i])) 
                return true;
        }
        return false;
    }
});

$('#element').hasClasses(['class1', 'class2', 'class3']);

Это должно сделать это, просто и легко.

Калель Уэйд
источник
2
Вам не хватает переменной в for (я в селекторах), таким образом, создается глобальный.
Грэмвелл
4
Немного второстепенный вопрос, но селекторы параметров должны действительно называться классами или classNames , поскольку именно это вы и передаете, а не селекторы. Селекторы будут иметь точку перед ними, как в $ ('# element'). HasClasses (['. Class1', '.class2', '.class3']);
Jbyrd
10

filter () - это еще один вариант

Сократите набор соответствующих элементов до тех, которые соответствуют селектору или проходят тест функции.

$(selector).filter('.class1, .class2'); //Filter elements: class1 OR class2

$(selector).filter('.class1.class2'); // Filter elements: class1 AND class2
Джон Магнолия
источник
6

Как насчет этого?

if (element.hasClass("class1 class2")
Роберт Лозиньски
источник
3
Это не работает, если вы смотрите на условие ИЛИ.
Джейсон Конвилл
4

вот ответ, который следует синтаксису

$(element).hasAnyOfClasses("class1","class2","class3")
(function($){
    $.fn.hasAnyOfClasses = function(){
        for(var i= 0, il=arguments.length; i<il; i++){
            if($self.hasClass(arguments[i])) return true;
        }
        return false;
    }
})(jQuery);

это не самый быстрый, но однозначный и решение, которое я предпочитаю. скамейка: http://jsperf.com/hasclasstest/10

Хенрик Мынтти
источник
Error: $self is not defined
bagofmilk
1
@bagofmilk Мой ответ был отредактирован другими, так как я написал это 6 лет назад. Так как я годами не использовал jQuery, я не знаю точно, что было задумано с правкой, но изначально у меня было это var $self = $(this);незадолго до цикла for
Henrik Myntti
1

Как насчет этого,

$.fn.extend({
     hasClasses: function( selector ) {
        var classNamesRegex = new RegExp("( " + selector.replace(/ +/g,"").replace(/,/g, " | ") + " )"),
            rclass = /[\n\t\r]/g,
            i = 0,
            l = this.length;
        for ( ; i < l; i++ ) {
            if ( this[i].nodeType === 1 && classNamesRegex.test((" " + this[i].className + " ").replace(rclass, " "))) {
                return true;
            }
        }
        return false;
    }
});

Легко использовать,

if ( $("selector").hasClasses("class1, class2, class3") ) {
  //Yes It does
}

И, кажется, быстрее, http://jsperf.com/hasclasstest/7

Окан Коцигит
источник
1

Что о:

if($('.class.class2.class3').length > 0){
    //...
}
u01jmg3
источник
3
Вам не нужно > 0. Если длина не равна нулю, он вернет истину.
Исаак Любов
1

JQuery

if( ['class', 'class2'].some(c => [...element[0].classList].includes(c)) )

Ваниль JS

if( ['class', 'class2'].some(c => [...element.classList].includes(c)) )
Саймон Арнольд
источник
0

использовать функцию js match () по умолчанию:

if( element.attr('class') !== undefined && element.attr('class').match(/class1|class2|class3|class4|class5/) ) {
  console.log("match");
}

чтобы использовать переменные в регулярном выражении, используйте это:

var reg = new RegExp(variable, 'g');
$(this).match(reg);

Кстати, это самый быстрый способ: http://jsperf.com/hasclass-vs-is-stackoverflow/22

Ромуальдс Кирсис
источник
Как этот ответ лучше всего, хотя я подозреваю, что цикл через классы и использование строкового теста indexOf может быть еще быстрее ...
terraling
0

Работает для меня:

 if ( $("element").hasClass( "class1") || $("element").hasClass("class2") ) {

 //do something here

 }
Рангель Р. Морайс
источник
0

Вы можете сделать это так:

if($(selector).filter('.class1, .class2').length){
    // Or logic
}

if($(selector).filter('.class1, .class2').length){
    // And logic
}
Hamidreza
источник
-1

Это сработало для меня:

$('.class1[class~="class2"]').append('something');
Тина
источник
3
Этот ответ не имеет ничего общего с заданным вопросом.
Джезен Томас
Это на самом деле отличный ответ. Приведенный выше синтаксис селектора захватывает все элементы как с class1, так и с class2. Тогда вы можете делать то, что вам нравится, в этом случае добавить. Не проверял производительность по сравнению с другими методами, но синтаксис хорош и лаконичен.
Тим Райт
2
@TimWright Это ужасный ответ. Обычный способ выбрать элемент с 2 классами - $('.class1.class2')нет необходимости использовать селектор атрибута для второго класса. Кроме того, вопрос состоит в том, как выбрать элемент одним из любых, а не всеми классами.
Все работники необходимы