使用jQuery获取元素的类列表


657

jQuery中是否有一种方法可以循环或将分配给元素的所有类分配给数组?

例如

<div class="Lorem ipsum dolor_spec sit amet">Hello World!</div>

我将在上面的“ dolor_spec”中寻找“特殊”类。我知道我可以使用hasClass(),但当时不一定知道实际的类名。


如果您当时不知道类名,从而无法使用hasClass(),那么您打算如何知道它是数组中的哪一个呢?
doomspork

我正在设计一种使用jQuery进行初步验证的表单。如果生成一个,我会将输入元素的ID附加到错误div的类列表中。然后,我可以单击error div以聚焦错误的输入元素。该脚本将用于多种形式。因此,我不想在脚本中对ID进行硬编码。
2009年

1
是的,我知道您为什么不想硬编码。但是,如果花一点时间查看redsquare的示例,您会发现必须将'someClass'硬编码到if块中。无论哪种方式,您都可以使用变量来实现。
doomspork

与其使用class属性,不如在您的命名空间中包含一个错误列表变量,其中包含对有错误元素的DOM引用。因此,无需每次都拉出属性列表,对其进行迭代,找到DOM元素并对其进行聚焦。
doomspork

Answers:


731

您可以document.getElementById('divId').className.split(/\s+/);用来获取一组类名。

然后,您可以迭代并找到所需的那个。

var classList = document.getElementById('divId').className.split(/\s+/);
for (var i = 0; i < classList.length; i++) {
    if (classList[i] === 'someClass') {
        //do something
    }
}

jQuery并没有真正帮助您...

var classList = $('#divId').attr('class').split(/\s+/);
$.each(classList, function(index, item) {
    if (item === 'someClass') {
        //do something
    }
});

4
这正是我要做的事情,但是我不确定jQuery函数中是否有内置功能可以为您提供这些类的集合。
桑德

36
仅供参考:jQuery使用className.split(/ \ s + /)
kͩeͩmͣpͥ2010年

70
自己添加一个jQuery插件:$.fn.classList = function() {return this[0].className.split(/\s+/);};
ripper234 2012年

1
否则您可以: if ($.inArray("someclass",classList)>=0) { /* hasClass someclass*/ }
sambomartin 2012年

不是这里的JavaScript专家。您能告诉我split(/ \ s + /)是否比仅仅进行split(“”)好?在FF23 / Chrome28 / IE8中,它对我的​​工作原理相同。
罗伯托·利纳雷斯

288

为什么没有人简单列出。

$(element).attr("class").split(/\s+/);

编辑:正如@MarkAmery指出的那样,您不能仅仅.split(' ')因为类名可以用任何一种空格分隔。


6
这是公认的答案的一部分...我需要应用于元素的所有类。
Buggabill

54
因为错了!类可以用任何类型的空格分隔(例如,您可以将HTML中的long类属性包装到多行中),但是此答案不能解决这个问题。尝试粘贴$('<div class="foo bar baz">').attr("class").split(' ')到浏览器控制台中(那里有一个制表符);您会得到["foo", "bar baz"]而不是正确的类列表["foo", "bar", "baz"]
Mark Amery 2014年

2
@MarkAmery是正确的。如果您有一个class="foo <lots of spaces here> bar",最终将得到一个包含空字符串元素的数组。
Jacob van Lingen 2015年

4
我认为在99%的情况下,该解决方案是有效的,即只要您控制HTML。我想不出任何理由,即使HTML标准允许,我们也需要支持制表符或类名之间多个空格的可能性。
Gordon Rouse

5
@GordonRouse爬到类列表中的额外空间是很常见的,尤其是当某种逻辑写出类列表时。
埃里克(Eric)

142

在支持的浏览器上,您可以使用DOM元素的classList属性。

$(element)[0].classList

它是一个类似数组的对象,列出了元素具有的所有类。

如果您需要支持不支持该classList属性的旧浏览器版本,则链接的MDN页面还包含一个填充程序-尽管即使该填充程序也无法在IE 8以下的Internet Explorer版本上运行。


干净的答案,不会重新发明轮子。
Marco Sulla

@Marco Sulla:除了支持过时的软件之外,这确实还有一个缺点。 .classList不是真正的数组,因此无法使用此类方法.indexOf(⋯)。它只是一个“类似数组的对象”,而.className.split(/\s+/).indexOf(⋯)(根据公认的答案)是有效的。
Incnis Mrsi

您可以轻松地将任何可迭代形式转换为Array使用[...iterable]Array.from(iterable)
Marco Sulla

142

这是一个jQuery插件,它将返回匹配元素具有的所有类的数组

;!(function ($) {
    $.fn.classes = function (callback) {
        var classes = [];
        $.each(this, function (i, v) {
            var splitClassName = v.className.split(/\s+/);
            for (var j = 0; j < splitClassName.length; j++) {
                var className = splitClassName[j];
                if (-1 === classes.indexOf(className)) {
                    classes.push(className);
                }
            }
        });
        if ('function' === typeof callback) {
            for (var i in classes) {
                callback(classes[i]);
            }
        }
        return classes;
    };
})(jQuery);

像这样使用

$('div').classes();

就您而言

["Lorem", "ipsum", "dolor_spec", "sit", "amet"]

您还可以将函数传递给要在每个类上调用的方法

$('div').classes(
    function(c) {
        // do something with each class
    }
);

这是我设置用来演示和测试的jsFiddle http://jsfiddle.net/GD8Qn/8/

精简Javascript

;!function(e){e.fn.classes=function(t){var n=[];e.each(this,function(e,t){var r=t.className.split(/\s+/);for(var i in r){var s=r[i];if(-1===n.indexOf(s)){n.push(s)}}});if("function"===typeof t){for(var r in n){t(n[r])}}return n}}(jQuery);

将类复制到Event 的className属性中时,它非常适合FullCalendar
Dan Power

78

您应该尝试以下一种方法:

$("selector").prop("classList")

它返回该元素的所有当前类的数组。


这比公认的答案更整洁,是否有任何理由不使用此方法?
RozzA

5
好吧,我不知道。但这是从DOM元素获取属性的正确方法。而“ classList”是这样的属性,它为您提供了应用于该元素的一组css类。
P.Petkov '16

@RozzA也许那时还不可用?不过,我会说这是最合适的方法现在,除非你不使用jQuery,其中一个简单.classList的解决方案-你只需要注意的不一致和/或丢失的浏览器支持..
Dennis98

@ Dennis98是个好电话,我忘记了有时候新功能有多快出现。我也做了普通的js .classList,在现代浏览器中效果很好
RozzA'9

1
请注意,该classList属性不适用于SVG元素的IE 10/11(尽管它适用于HTML元素)。见developer.mozilla.org/en-US/docs/Web/API/Element/classList
Métoule

17
var classList = $(element).attr('class').split(/\s+/);
$(classList).each(function(index){

     //do something

});

7

更新:

正如@Ryan Leonard正确指出的那样,我的答案并不能真正解决我自己提出的问题...您需要同时修剪和删除双精度空格(例如,使用string.replace(/ + / g,“”) ..或者您可以拆分el.className,然后使用(例如)arr.filter(Boolean)删除空值。

const classes = element.className.split(' ').filter(Boolean);

或更现代

const classes = element.classList;

旧:

有了所有给定的答案,您永远都不要忘记使用.trim()(或$ .trim())用户。

因为添加和删除了类,所以类字符串之间可能存在多个空格。例如,“ class1 class2 class3”。

这将变成['class1','class2','','','','class3']。

使用修剪时,所有多个空格都将被删除。


2
这是不正确的(不是答案)。String.trim()和$ .trim()都删除所有前导和尾随空格,并将其余的字符串保留下来。 jsconsole.com /%22%20%20A%20%20B%20%20%22.trim()?
瑞恩伦纳德

你甚至看过答案吗?所有原生JS的解决方案没有检查开头和结尾的空格,从而使故障类列表,将有数组中的空类.. jQuery不会与内部装饰同样的,当它读取类
DutchKevv

2
我确实看到了其他答案,并同意应该在类名之间删除空格。我指出一个),这应该是对其他解决方案的评论,因为它不是一个完整的答案B).trim()并没有删除多个空格来实现你所需要的。
瑞安·伦纳德

1
您确实完全正确...很抱歉,我的快速评论..它不会删除它们之间的空格... s.trim()。replace(/ + / g,“”)否则将需要某些内容删除类之间的所有多个空格。.紧接着,el.classList得到广泛支持,修复了所有我想的问题
。– DutchKevv

1
没问题。令人高兴的是,这.classList是一种更清洁的方法!
瑞安·伦纳德

7
$('div').attr('class').split(' ').each(function(cls){ console.log(cls);})

2
这是可怕的虐待.map; 使用.each如果你不需要.map的返回值。在空格而不是任何空格上的拆分也被破坏了-请参阅我对stackoverflow.com/a/10159062/1709587的评论。即使这些观点都不成立,这也没有为页面增加任何新内容。-1!
Mark Amery 2014年

3

可能对您有帮助。我已经使用此函数来获取子元素的类。

function getClickClicked(){
    var clickedElement=null;
    var classes = null;<--- this is array
    ELEMENT.on("click",function(e){//<-- where element can div,p span, or any id also a class
        clickedElement = $(e.target);
        classes = clickedElement.attr("class").split(" ");
        for(var i = 0; i<classes.length;i++){
            console.log(classes[i]);
        }
        e.preventDefault();
    });
}

在您的情况下,您希望doler_ipsum类现在可以这样做calsses[2];


2

谢谢您-我遇到了类似的问题,因为我试图以编程方式将对象与分层的类名相关联,即使这些名称不一定是我的脚本知道的。

在我的脚本中,我希望<a>标签通过给<a>标签[some_class]加上的类toggle,然后为其提供帮助文本,作为类来打开/关闭帮助文本[some_class]_toggle。这段代码使用jQuery成功找到了相关元素:

$("a.toggle").toggle(function(){toggleHelp($(this), false);}, function(){toggleHelp($(this), true);});

function toggleHelp(obj, mode){
    var classList = obj.attr('class').split(/\s+/);
    $.each( classList, function(index, item){
    if (item.indexOf("_toggle") > 0) {
       var targetClass = "." + item.replace("_toggle", "");
       if(mode===false){$(targetClass).removeClass("off");}
       else{$(targetClass).addClass("off");}
    }
    });
} 

谢谢Alan,我正在做类似的事情,我很惊讶没有一个更简单的方法可以做到这一点。
埃里克·基加西

-1-tl; dr,在与该问题不直接相关的切线处开始。
Mark Amery 2014年

2

尝试这个。这将从文档的所有元素中获取所有类的名称。

$(document).ready(function() {
var currentHtml="";
$('*').each(function() {
    if ($(this).hasClass('') === false) {
        var class_name = $(this).attr('class');
        if (class_name.match(/\s/g)){
            var newClasses= class_name.split(' ');
            for (var i = 0; i <= newClasses.length - 1; i++) {
                if (currentHtml.indexOf(newClasses[i]) <0) {
                    currentHtml += "."+newClasses[i]+"<br>{<br><br>}<br>"
                }
            }
        }
        else
        {
            if (currentHtml.indexOf(class_name) <0) {
                currentHtml += "."+class_name+"<br>{<br><br>}<br>"
            }
        }
    }
    else
    {
        console.log("none");
    }
});
$("#Test").html(currentHtml);

});

这是工作示例:https : //jsfiddle.net/raju_sumit/2xu1ujoy/3/


1

对于image类型的元素,我也遇到了类似的问题。我需要检查元素是否属于某个类。首先,我尝试了:

$('<img>').hasClass("nameOfMyClass"); 

但是我得到了一个很好的“此元素不可用此功能”。

然后,我在DOM资源管理器上检查了我的元素,然后看到了可以使用的非常不错的属性:className。它包含我的元素的所有类的名称,用空格分隔。

$('img').className // it contains "class1 class2 class3"

一旦获得此权限,只需照常拆分字符串即可。

就我而言,这可行:

var listOfClassesOfMyElement= $('img').className.split(" ");

我假设这将与其他类型的元素一起工作(除了img)。

希望能帮助到你。


0

javascript为dom中的节点元素提供了classList属性。只需使用

  element.classList

将返回一个形式的对象

  DOMTokenList {0: "class1", 1: "class2", 2: "class3", length: 3, item: function, contains: function, add: function, remove: function…}

该对象具有包含,添加,删除之类的功能,可以使用


在您之前3年发布的stackoverflow.com/a/5457148/1709587的劣等副本;-1。
Mark Amery 2014年

-3

有点晚了,但是使用extend()函数可以在任何元素上调用“ hasClass()”,例如:
var hasClass = $('#divId').hasClass('someClass');

(function($) {
$.extend({
    hasClass: new function(className) {
        var classAttr = $J(this).attr('class');
        if (classAttr != null && classAttr != undefined) {
            var classList = classAttr.split(/\s+/);
            for(var ix = 0, len = classList.length;ix < len;ix++) {
                if (className === classList[ix]) {
                    return true;
                }
            }
        }
        return false;
    }
}); })(jQuery);

10
那不是问题。
托马斯

5
此外,jQuery自1.2版以来就内置了此功能。
Andrew

-3

问题是Jquery打算做什么。

$('.dolor_spec').each(function(){ //do stuff

为什么没有人给出.find()作为答案?

$('div').find('.dolor_spec').each(function(){
  ..
});

对于非IE浏览器,还有classList:

if element.classList.contains("dolor_spec") {  //do stuff

3
-1; 除其他问题外,您的前两个代码段与所询问的问题无关,而最后一个代码段是语法错误。
Mark Amery 2014年

-4

在这里,只需调整readsquare的答案即可返回所有类的数组:

function classList(elem){
   var classList = elem.attr('class').split(/\s+/);
    var classes = new Array(classList.length);
    $.each( classList, function(index, item){
        classes[index] = item;
    });

    return classes;
}

将jQuery元素传递给函数,这样一个示例调用将是:

var myClasses = classList($('#myElement'));

3
为什么要遍历classList数组,将所有元素添加到classes数组并返回classes数组?只是返回classList应该做同样的事情,对不对?
Martijn 2012年

不。因为我们指的是同一元素有很多类的情况。如果是如此简单,那么我们不在此线程上:)
Gregra

8
这个线程是关于返回一个类列表的,只需返回$(elem).attr('class').split(/\s+/)就可以了。也许是我误会了,但是我看不出有任何理由可以遍历一个集合,将内容复制到一个新集合中并返回该新集合。
马丁,2012年

-4

我知道这是一个古老的问题,但仍然存在。

<div id="specId" class="Lorem ipsum dolor_spec sit amet">Hello World!</div>

var className=".dolor_spec" //dynamic

如果要操纵元素

$("#specId"+className).addClass('whatever');

如果要检查元素是否具有类

 $("#specId"+className).length>0

如果有多个班级

//if you want to select ONE of the classes
var classNames = ['.dolor_spec','.test','.test2']
$("#specId"+classNames).addClass('whatever');
$("#specId"+classNames).length>0
//if you want to select all of the classes
var result = {className: ""};
classNames.forEach(function(el){this.className+=el;},result);
var searchedElement= $("#specId"+result.className);
searchedElement.addClass('whatever');
searchedElement.length>0

1
这些片段都没有解决所提出的问题。-1。
Mark Amery
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.