jQuery bagaimana menemukan elemen berdasarkan nilai atribut data?

994

Saya punya skenario berikut:

var el = 'li';

dan ada 5 <li>'s pada halaman masing-masing dengan data-slide=numberatribut (nomor masing-masing 1,2,3,4,5) .

Saya sekarang perlu menemukan nomor slide yang sedang aktif yang dipetakan ke var current = $('ul').data(current);dan diperbarui pada setiap perubahan slide.

Sejauh ini percobaan saya tidak berhasil, mencoba membuat pemilih yang cocok dengan slide saat ini:

$('ul').find(el+[data-slide=+current+]);

tidak cocok / mengembalikan apa pun ...

Alasan saya tidak bisa meng-hardcode libagian tersebut adalah karena ini adalah variabel yang dapat diakses pengguna yang dapat diubah ke elemen lain jika diperlukan, jadi itu mungkin tidak selalu menjadi li.

Ada ide tentang apa yang saya lewatkan?

Jannis
sumber
6
Anda yakin di dalam diri Anda .find(el+[data-slide=+current+]);adalah kode yang Anda tulis? sepertinya Anda melewatkan beberapa kutipan untuk"[data-slide]"
xandy
Itulah yang membantu saya memilih semua atribut data (berapapun nilainya): $('*[data-slide]')Anda dapat menggunakannya dengan misalnya$('*[data-slide]').each( function() { ... });
Kai Noack

Jawaban:

1481

Anda harus menyuntikkan nilai currentke dalam pemilih Atribut Setara :

$("ul").find(`[data-slide='${current}']`)

Untuk lingkungan JavaScript yang lebih lama ( ES5 dan sebelumnya):

$("ul").find("[data-slide='" + current + "']"); 
Frédéric Hamidi
sumber
8
@ Jannis, Anda bisa melakukannya $("ul").find(el + "[data-slide='" + current +"']");.
Frédéric Hamidi
7
@ c00lryguy, jQuery UI mendefinisikan satu, dan ada implementasi mandiri di sekitar. Tampaknya upaya untuk menambahkannya ke jQuery Core ditolak . Dua kali .
Frédéric Hamidi
6
jawaban ini pada pos serupa memiliki contoh fungsi filter
drzaus
77
Saya khawatir ini tidak akan berfungsi jika data ditambahkan melalui fungsi jQuery. Data (...), karena ini tidak selalu membuat atribut dan waktu penggunaan menggunakan mekanisme penyimpanan khusus browser. Alasan lain saya berharap jQuery core memiliki pemilih data khusus.
AaronLS
77
Perhatikan bahwa itu tidak berfungsi untuk elemen tempat Anda menyetel data dengan $ ('# element'). Data ('some-att-name', value); tetapi hanya untuk mereka yang memiliki atribut hardcoded. Saya punya masalah ini dan membuatnya berfungsi mengatur data dengan menulis atribut langsung $ ('# element'). Attr ('data-some-att-name', value);
Pawel
463

jika Anda tidak ingin mengetik semua itu, inilah cara yang lebih pendek untuk melakukan kueri berdasarkan atribut data:

$("ul[data-slide='" + current +"']");

FYI: http://james.padolsey.com/javascript/a-better-data-selector-for-jquery/

KevinDeus
sumber
31
Bagi Anda yang peduli, mengingat struktur <ul><li data-slide="item"></li></ul>pemilih jawaban ini akan kembali tidak terdefinisi sehingga tidak berfungsi mengingat skenario pengguna. Jawaban ini AKAN bekerja untuk struktur. <ul data-slide="item"><li></li></ul> Sementara saya mengerti mengapa popularitasnya karena singkatnya, secara teknis jawaban itu salah. jsfiddle.net/py5p2abL/1
akousmata
4
Jangan lupa untuk memperlakukannya sebagai sebuah array. Gunakan [0]untuk mengakses elemen pertama yang ditemukan.
Aminah Nuraini
Efek samping yang aneh ... metode ini bekerja mencocokkan elemen dengan atribut data ketika .find("[data-attrib='value']")tidak berfungsi. Saya tidak tahu apakah nilai atribut data ditambahkan oleh jQuery atau tidak ...
error
1
Itu tidak aneh karena kedua jawaban itu melakukan 2 hal yang berbeda. $.findsecara khusus menemukan keturunan elemen itu, tetapi menggunakan sintaksis filter dalam string pemilih hanya akan menyaring hasilnya.
Phil
227

Saat mencari dengan [data-x = ...], hati-hati, itu tidak berfungsi dengan setter jQuery.data (..) :

$('<b data-x="1">'  ).is('[data-x=1]') // this works
> true

$('<b>').data('x', 1).is('[data-x=1]') // this doesn't
> false

$('<b>').attr('data-x', 1).is('[data-x=1]') // this is the workaround
> true

Anda bisa menggunakan ini sebagai gantinya:

$.fn.filterByData = function(prop, val) {
    return this.filter(
        function() { return $(this).data(prop)==val; }
    );
}

$('<b>').data('x', 1).filterByData('x', 1).length
> 1
psiko brm
sumber
1
yang $.fn.filterByDatabrilian; Namun, ini adalah peringatan untuk copy-pasters di luar sana ... Anda hanya perlu $('<b>').filterByData('x', 1)menemukan <b>tag data-x="1". jika Anda menyalin-menempelkan .data(x, 1)bagian ... Anda akan mengatur data-xke "1" sebelum memfilter.
WEBjuju
39

Saya meningkatkan ekstensi filterByData psiko brm ke jQuery.

Di mana mantan ekstensi mencari pasangan nilai kunci, dengan ekstensi ini Anda juga dapat mencari keberadaan atribut data, terlepas dari nilainya.

(function ($) {

    $.fn.filterByData = function (prop, val) {
        var $self = this;
        if (typeof val === 'undefined') {
            return $self.filter(
                function () { return typeof $(this).data(prop) !== 'undefined'; }
            );
        }
        return $self.filter(
            function () { return $(this).data(prop) == val; }
        );
    };

})(window.jQuery);

Pemakaian:

$('<b>').data('x', 1).filterByData('x', 1).length    // output: 1
$('<b>').data('x', 1).filterByData('x').length       // output: 1

Atau biola: http://jsfiddle.net/PTqmE/46/

bPratik
sumber
34

Tanpa JQuery, ES6

document.querySelectorAll(`[data-slide='${current}']`);

Saya tahu pertanyaannya adalah tentang JQuery, tetapi pembaca mungkin menginginkan metode JS murni.

rap-2-h
sumber
33

Saya telah menghadapi masalah yang sama saat mengambil elemen menggunakan atribut jQuery dan data- *.

jadi untuk referensi Anda, kode terpendek ada di sini:

Ini adalah Kode HTML saya:

<section data-js="carousel"></section>
<section></section>
<section></section>
<section data-js="carousel"></section>

Ini adalah pemilih jQuery saya:

$('section[data-js="carousel"]');
// this will return array of the section elements which has data-js="carousel" attribute.
pengguna1378423
sumber
19
$("ul").find("li[data-slide='" + current + "']");

Saya harap ini bisa bekerja lebih baik

Terima kasih

Jomin George Paul
sumber
15

Pemilih ini $("ul [data-slide='" + current +"']");akan bekerja untuk struktur berikut:

<ul><li data-slide="item"></li></ul>  

Sementara ini $("ul[data-slide='" + current +"']");akan bekerja untuk:

<ul data-slide="item"><li></li></ul>

Matas Vaitkevicius
sumber
12

Kembali ke pertanyaan aslinya, tentang cara membuat ini bekerja tanpa mengetahui jenis elemen di muka, berikut hal ini:

$(ContainerNode).find(el.nodeName + "[data-slide='" + current + "']");
Bryan Garaventa
sumber