Menerapkan gaya CSS ke elemen tergantung pada elemen anaknya


203

Apakah mungkin untuk mendefinisikan gaya CSS untuk suatu elemen, yang hanya diterapkan jika elemen yang cocok mengandung elemen tertentu (sebagai item turunan langsung)?

Saya pikir ini paling baik dijelaskan menggunakan contoh.

Catatan : Saya mencoba gaya elemen induk , tergantung pada elemen anak apa yang dikandungnya.

<style>
  /* note this is invalid syntax. I'm using the non-existing
   ":containing" pseudo-class to show what I want to achieve. */
  div:containing div.a { border: solid 3px red; }
  div:containing div.b { border: solid 3px blue; }
</style>

<!-- the following div should have a red border because
     if contains a div with class="a" -->
<div>
  <div class="a"></div>
</div>

<!-- the following div should have a blue border -->
<div>
  <div class="b"></div>
</div>

Catatan 2 : Saya tahu saya bisa mencapai ini menggunakan javascript, tapi saya hanya bertanya-tanya apakah ini mungkin menggunakan beberapa fitur CSS yang tidak diketahui (untuk saya).


1
Anda mungkin ingin memperbarui pertanyaan untuk menyatakan, mungkin dengan teks tebal yang berkedip, bahwa Anda mencoba mendesain PARENT div, bukan anak-anaknya. Saya tahu bahwa info ada dalam pertanyaan itu sendiri, tetapi kecuali jika Anda ingin mendapatkan satu ton jawaban yang salah, itu mungkin layak dilakukan.
Seth Petry-Johnson

Terima kasih @Seth. Saya mencoba memperbaiki judul dan teks pertanyaan. Harap edit pertanyaan jika menurut Anda masih belum jelas.
M4N


Ini adalah contoh sempurna mengapa jenis dukungan dalam CSS ini ideal: ol < li:nth-child(n+10) { margin-left: 2rem; } ol < li:nth-child(n+100) { margin-left: 3rem; } ol < li:nth-child(n+1000) { margin-left: 4rem; }Dalam dunia ideal ini akan meningkatkan margin olketergantungan pada jumlah lianak yang terkandung sehingga margin di sebelah kiri hanya akan selebar itu dibutuhkan.
Jonmark Weber

Jawaban:


124

Sejauh yang saya ketahui, menata elemen induk berdasarkan elemen anak bukanlah fitur CSS yang tersedia. Anda mungkin perlu membuat skrip untuk ini.

Akan luar biasa jika Anda bisa melakukan sesuatu seperti div[div.a]atau div:containing[div.a]seperti yang Anda katakan, tetapi ini tidak mungkin.

Anda mungkin ingin mempertimbangkan untuk melihat jQuery . Selektornya bekerja sangat baik dengan tipe 'mengandung'. Anda dapat memilih div, berdasarkan konten turunannya dan kemudian menerapkan kelas CSS ke induk semua dalam satu baris.

Jika Anda menggunakan jQuery, sesuatu di sepanjang baris ini akan berfungsi (tidak teruji tetapi teorinya ada di sana):

$('div:has(div.a)').css('border', '1px solid red');

atau

$('div:has(div.a)').addClass('redBorder');

dikombinasikan dengan kelas CSS:

.redBorder
{
    border: 1px solid red;
}

Berikut dokumentasi untuk pemilih "memiliki" jQuery .


15
Catatan tambahan: untuk kinerja yang lebih baik, halaman dokumen jQuery untuk :haspemilih menyarankan untuk menggunakan .has()metode ( api.jquery.com/has ) => diterapkan pada pertanyaan saat ini yang akan diberikan misalnya$('div').has('div.a').css('border', '1px solid red');
Frosty Z

Agar ini bekerja, seseorang harus menggunakan pengamat mutasi, untuk memeriksa apakah anak itu berubah keadaan ...
Legends

Ini tidak benar-benar menjawab pertanyaan yang "Apakah ada cara untuk melakukan ini dengan CSS". Ini dengan jelas menyatakan: "Saya tahu saya bisa mencapai ini menggunakan javascript, tapi saya hanya bertanya-tanya apakah ini mungkin menggunakan beberapa fitur CSS yang tidak diketahui (untuk saya)."
SunshinyDoyle

developer.mozilla.org/en-US/docs/Web/CSS/:has , saya pikir :haspemilih ini dapat bekerja tetapi dalam versi konsep dan tidak ada browser yang mendukungnya.
AliF50

62

Pada dasarnya tidak. Berikut ini yang akan Anda kejar dalam teori:

div.a < div { border: solid 3px red; }

Sayangnya itu tidak ada.

Ada beberapa tulisan di sepanjang baris "kenapa tidak". Yang sangat bagus dari Shaun Inman cukup bagus:

http://www.shauninman.com/archive/2008/05/05/css_qualified_selectors


34
hanya pembaruan 8 tahun kemudian: masih belum ada dukungan untuk metode pemilih ini.
Kraang Prime

1
Ada konsep kerja untuk fitur ini dalam bentuk :has()pseudo-class, tetapi kita hanya bisa menggunakannya di CSS4. Sampai sekarang (akhir 2019), JS masih merupakan satu-satunya cara untuk mencapai fungsi ini.
zepp.lee

Saya percaya ini tidak akan mengaktifkan gaya css, masih perlu javascript untuk menggunakan pemilih. Kecuali ini telah berubah?
Justin Wignall

3
9 tahun dan apakah menurut mereka fitur ini tidak perlu?
Loi Nguyen Huynh

1

Di atas jawaban @ kp:

Saya berurusan dengan ini dan dalam kasus saya, saya harus menunjukkan elemen turunan dan mengoreksi ketinggian objek induk sesuai (ukuran otomatis tidak bekerja di header bootstrap karena beberapa alasan saya tidak punya waktu untuk debug) .

Tetapi alih-alih menggunakan javascript untuk memodifikasi induk, saya pikir saya akan secara dinamis menambahkan kelas CSS ke induk dan CSS secara selektif menunjukkan kepada anak-anak sesuai. Ini akan mempertahankan keputusan dalam logika dan tidak didasarkan pada keadaan CSS.

tl; dr; terapkan adan bgaya ke orang tua <div>, bukan anak (tentu saja, tidak semua orang akan dapat melakukan ini. yaitu komponen sudut membuat keputusan mereka sendiri).

<style>
  .parent            { height: 50px; }
  .parent div        { display: none; }
  .with-children     { height: 100px; }
  .with-children div { display: block; }
</style>

<div class="parent">
  <div>child</div>
</div>

<script>
  // to show the children
  $('.parent').addClass('with-children');
</script>

0

Dalam kasus saya, saya harus mengubah sel sel elemen yang berisi kotak centang input untuk tabel yang secara dinamis dirender dengan DataTables:

<td class="dt-center">
    <input class="a" name="constCheck" type="checkbox" checked="">
</td>

Setelah menerapkan kode baris berikut dalam fungsi initComplete, saya dapat menghasilkan padding yang benar, yang menjaga baris agar tidak ditampilkan dengan tinggi yang tidak normal.

 $('tbody td:has(input.a)').css('padding', '0px');

Sekarang, Anda dapat melihat bahwa gaya yang benar sedang diterapkan ke elemen induk:

<td class=" dt-center" style="padding: 0px;">
    <input class="a" name="constCheck" type="checkbox" checked="">
</td>

Pada dasarnya, jawaban ini adalah perpanjangan dari jawaban @ KP, tetapi semakin banyak kolaborasi penerapan ini semakin baik. Singkatnya, saya harap ini membantu orang lain karena berhasil! Terakhir, terima kasih banyak @KP karena telah membimbing saya ke arah yang benar!

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.