Memilih elemen berdasarkan atribut data

1020

Apakah ada metode yang mudah dan langsung untuk memilih elemen berdasarkan dataatributnya? Misalnya, pilih semua jangkar yang memiliki atribut data bernama customerIDyang memiliki nilai 22.

Saya agak ragu untuk menggunakan relatau atribut lain untuk menyimpan informasi tersebut, tetapi saya merasa lebih sulit untuk memilih elemen berdasarkan data apa yang disimpan di dalamnya.

Hazem Salama
sumber
2
Lihat juga stackoverflow.com/q/4191386/292060
selamat tinggal
Itulah yang membantu saya memilih semua atribut data (berapapun nilainya): $('*[data-customerID]')Anda dapat menggunakannya dengan misalnya$('*[data-customerID]').each( function() { ... });
Kai Noack

Jawaban:

1469
$('*[data-customerID="22"]');

Anda seharusnya dapat menghilangkan *, tetapi jika saya mengingatnya dengan benar, tergantung pada versi jQuery yang Anda gunakan, ini mungkin memberikan hasil yang salah.

Perhatikan bahwa untuk kompatibilitas dengan Selectors API ( document.querySelector{,all}), tanda kutip di sekitar nilai atribut ( 22) mungkin tidak dihilangkan dalam kasus ini .

Juga, jika Anda sering bekerja dengan atribut data dalam skrip jQuery, Anda mungkin ingin mempertimbangkan untuk menggunakan plugin atribut data kustom HTML5 . Ini memungkinkan Anda untuk menulis kode yang lebih mudah dibaca dengan menggunakan .dataAttr('foo'), dan menghasilkan ukuran file yang lebih kecil setelah minifikasi (dibandingkan dengan menggunakan .attr('data-foo')).

Mathias Bynens
sumber
69
Perhatikan bahwa .data ('foo') berfungsi untuk mendapatkan nilai atribut 'data-foo' sejak jQuery 1.4.3. Juga, sejak jQuery 1.6: .data ('fooBar') mendapat atribut 'data-foo-bar'.
James McCormack
4
@ Zootius: Ya, readme plugin memiliki catatan tentang hal itu: “Pada jQuery 1.4.3, .data()memetakan ke data-*atribut kustom secara default, menjadikan plugin ini berlebihan. Itu masih bisa digunakan untuk versi jQuery yang lebih lama. ”
Mathias Bynens
Jadi bagaimana caranya memposting jQuery 1.4.3, memilih objek berdasarkan nilai objek datanya? Mari kita ingin memilih dalam contoh ini, benda dengan data untuk customerID sama dengan 22?
Perjalanan
54
Juga jika Anda hanya tertarik pada kehadiran atribut data tertentu, Anda dapat melakukan ini:$('[data-customerID]')
Darkside
7
Ini tidak berfungsi, jika bidang data diatur oleh jquery (menggunakan .data()), kan?
Martin R.
329

Untuk orang yang mencari Google dan ingin aturan umum tentang memilih dengan atribut data:

$("[data-test]")akan memilih elemen apa saja yang hanya memiliki atribut data (tidak peduli nilai atributnya). Termasuk:

<div data-test=value>attributes with values</div>
<div data-test>attributes without values</div>

$('[data-test~="foo"]')akan memilih elemen mana pun yang berisi atribut data footetapi tidak harus tepat, seperti:

<div data-test="foo">Exact Matches</div>
<div data-test="this has the word foo">Where the Attribute merely contains "foo"</div>

$('[data-test="the_exact_value"]')akan memilih elemen apa pun di mana nilai tepat atribut data the_exact_value, misalnya:

<div data-test="the_exact_value">Exact Matches</div>

tapi tidak

<div data-test="the_exact_value foo">This won't match</div>
JTG
sumber
21
Baik. Perhatikan bahwa ~=cocok dengan kata-kata yang dipisahkan dengan spasi putih sedangkan *=cocok dengan substring apa pun.
sam
Bagaimana dengan ^karakter?
kuba44
1
@ kuba44 memang Anda juga dapat menggunakan ^, karena itu $('[data-test^=foo]')dalam hal ini Anda memilih apa pun yang dimulai dengan foo, seperti <div data-test="foo_exact_value">atau <div data-test="food">tetapi tidak<div data-test="seafoo">
JDuarteDJ
Daftar pemilih atribut yang komprehensif: drafts.csswg.org/selectors-3/#attribute-selectors
user1460043
142

Menggunakan $('[data-whatever="myvalue"]')akan memilih apa saja dengan atribut html, tetapi di jQueries yang lebih baru tampaknya jika Anda menggunakan $(...).data(...)untuk melampirkan data, ia menggunakan beberapa peramban ajaib dan tidak memengaruhi html, karena itu tidak ditemukan .findseperti yang ditunjukkan dalam jawaban sebelumnya .

Verifikasi (diuji dengan 1.7.2+) (lihat juga biola ): (diperbarui agar lebih lengkap)

var $container = $('<div><div id="item1"/><div id="item2"/></div>');

// add html attribute
var $item1 = $('#item1').attr('data-generated', true);

// add as data
var $item2 = $('#item2').data('generated', true);

// create item, add data attribute via jquery
var $item3 = $('<div />', {id: 'item3', data: { generated: 'true' }, text: 'Item 3' });
$container.append($item3);

// create item, "manually" add data attribute
var $item4 = $('<div id="item4" data-generated="true">Item 4</div>');
$container.append($item4);

// only returns $item1 and $item4
var $result = $container.find('[data-generated="true"]');
drzaus
sumber
1
aha - ternyata orang lain menunjukkan hal ini di stackoverflow.com/questions/4191386/...
drzaus
4
dan menawarkan solusi dengan di .filter sini
drzaus
22
ia menggunakan beberapa peramban ajaib dan tidak memengaruhi html : tidak ada yang namanya ajaib;) learningjquery.com/2011/09/using-jquerys-data-apis
Tom Sarduy
1
Jika Anda menambahkan atribut data yang perlu Anda temukan nanti, gunakan$item.attr('data-id', 10);
Pedro Moreira
77

Saya belum melihat jawaban JavaScript tanpa jQuery. Semoga ini membantu seseorang.

var elements = document.querySelectorAll('[data-customerID="22"]');

elements[0].innerHTML = 'it worked!';
<a data-customerID='22'>test</a>

Info:

Sjoerd Pottuit
sumber
1
Terima kasih untuk ini. Bagus untuk melihat solusi non-jquery.
Chuck
68

Untuk memilih semua jangkar dengan atribut data data-customerID==22, Anda harus menyertakan auntuk membatasi ruang lingkup pencarian hanya untuk tipe elemen itu. Melakukan pencarian atribut data dalam satu lingkaran besar atau pada frekuensi tinggi ketika ada banyak elemen pada halaman dapat menyebabkan masalah kinerja.

$('a[data-customerID="22"]');
Travis J
sumber
27

Contoh JS Asli

Dapatkan NodeList elemen

var elem = document.querySelectorAll('[data-id="container"]')

html: <div data-id="container"></div>

Dapatkan elemen pertama

var firstElem = document.querySelector('[id="container"]')

html: <div id="container"></div>

Targetkan kumpulan node yang mengembalikan nodelist

document.getElementById('footer').querySelectorAll('[data-id]')

html:

<div class="footer">
    <div data-id="12"></div>
    <div data-id="22"></div>
</div>

Dapatkan elemen berdasarkan pada beberapa nilai data (OR)

document.querySelectorAll('[data-section="12"],[data-selection="20"]')

html:

<div data-selection="20"></div>
<div data-section="12"></div>

Dapatkan elemen berdasarkan nilai data gabungan (DAN)

document.querySelectorAll('[data-prop1="12"][data-prop2="20"]')

html:

<div data-prop1="12" data-prop2="20"></div>

Dapatkan item dari mana nilai dimulai

document.querySelectorAll('[href^="https://"]')
etoksin
sumber
Selektor untuk "dapatkan elemen pertama" benar tetapi tidak konsisten dengan contoh lain - saya yakin itu tidak ada "data-".
GuyPaddock
15

melalui metode filter Jquery ():

http://jsfiddle.net/9n4e1agn/1/

HTML:

<button   data-id='1'>One</button>
<button   data-id='2'>Two</button>

JavaScript:

$(function() {    
    $('button').filter(function(){
        return $(this).data("id")   == 2}).css({background:'red'});  
     });
Razan Paul
sumber
Apakah Anda mencoba biola? Metode FIlter hanyalah pendekatan lain untuk mencapai hal yang sama. Ini bisa berguna ketika Anda sudah memiliki satu set objek Jquery dan Anda perlu memfilter berdasarkan atribut data atau apa pun.
Razan Paul
Saya minta maaf, @Blizzard. Saya sudah mengomentari jawaban yang salah. Rekatkan ke kanan sekarang. #AlwaysALongDayAtWork
Peter Bishop
15

Konstruksi seperti ini: $('[data-XXX=111]')tidak berfungsi di Safari 8.0 .

Jika Anda kumpulan data atribut dengan cara ini: $('div').data('XXX', 111), hanya bekerja jika Anda menetapkan atribut data secara langsung dalam DOM seperti ini: $('div').attr('data-XXX', 111).

Saya pikir itu karena tim jQuery mengoptimalkan pengumpul sampah untuk mencegah kebocoran memori dan operasi berat pada pembangunan kembali DOM pada setiap atribut perubahan data.

Anton Danilchenko
sumber
Ini banyak membantu saya - jika saya menggunakan data atau metode penyangga, maka pemilihan dengan $ ('... [data-x = "y"]') tidak berfungsi - Saya menggunakan attr sebagai gantinya (itu mendorong perubahan atribut menjadi DOM). Thx
Jarda
13

Agar ini berfungsi di Chrome, nilainya tidak boleh memiliki pasangan tanda kutip lainnya.

Ini hanya berfungsi, misalnya, seperti ini:

$('a[data-customerID=22]');
pengguna55318
sumber
4
Tampaknya ini salah. Setidaknya itu tidak benar sekarang. Saya baru saja menggunakan $ ('[data-action = "setStatus"]'). RemoveClass ('dinonaktifkan'); di Chrome dan berfungsi dengan baik.
Peter Bishop
Saya kira tidak ada penggunaan "" di dalam pemilih, itu dapat digunakan sebagai$('[data-action=setStatus]').removeClass('disabled')
Animesh Singh
6

Terkadang diinginkan untuk memfilter elemen berdasarkan apakah mereka memiliki data-item yang melekat padanya secara terprogram (alias tidak melalui atribut dom):

$el.filter(function(i, x) { return $(x).data('foo-bar'); }).doSomething();

Di atas berfungsi tetapi tidak terlalu mudah dibaca. Pendekatan yang lebih baik adalah dengan menggunakan pemilih-semu untuk menguji hal semacam ini:

$.expr[":"].hasData = $.expr.createPseudo(function (arg) {
    return function (domEl) {
        var $el = $(domEl);
        return $el.is("[" + ((arg.startsWith("data-") ? "" : "data-") + arg) + "]") || typeof ($el.data(arg)) !== "undefined";
    };
});

Sekarang kita dapat memperbaiki pernyataan asli menjadi sesuatu yang lebih lancar dan mudah dibaca:

$el.filter(":hasData('foo-bar')").doSomething();
XDS
sumber
1
Solusi pertama melewatkan pernyataan pengembalian, itu harus: $ el.filter (function (i, x) {return $ (x) .data ('foo-bar');}). DoSomething ();
Salma Gomaa
3

Hanya untuk melengkapi semua jawaban dengan beberapa fitur 'standar hidup' - Sekarang (di era HTML5) dimungkinkan untuk melakukannya tanpa lib pihak ke-3:

  • JS murni / polos dengan querySelector (menggunakan pemilih CSS):
    • pilih yang pertama di DOM: document.querySelector('[data-answer="42"],[type="submit"]')
    • pilih semua di DOM: document.querySelectorAll('[data-answer="42"],[type="submit"]')
  • CSS murni / polos
    • beberapa tag spesifik: [data-answer="42"],[type="submit"]
    • semua tag dengan atribut spesifik: [data-answer]atauinput[type]
Sven
sumber