Bagaimana cara mencegah pewarisan CSS?

94

Saya memiliki menu navigasi hierarki di sidebar saya yang menggunakan daftar bersarang (tag <ul> dan <li>). Saya menggunakan tema yang sudah dibuat sebelumnya yang sudah memiliki gaya untuk item daftar, tetapi saya ingin mengubah gaya untuk item tingkat atas tetapi TIDAK menerapkannya ke sub-item. Adakah cara mudah untuk menerapkan gaya ke tag item daftar tingkat atas TANPA membuat gaya tersebut menurun ke item daftar turunannya? Saya memahami bahwa saya dapat secara eksplisit menambahkan gaya pengganti ke sub-item tetapi saya sangat ingin menghindari keharusan menduplikasi semua kode gaya tersebut jika ada cara mudah untuk hanya mengatakan "terapkan gaya ini ke kelas ini dan JANGAN bertingkat mereka ke semua elemen anak ". Ini html yang saya gunakan:

<ul id="sidebar">
  <li class="top-level-nav">
    <span>HEADING 1</span>
    <ul>
      <li>sub-heading A</li>
      <li>sub-heading B</li>
    </ul>
  </li>
  <li class="top-level-nav">
    <span>HEADING 2</span>
    <ul>
      <li>sub-heading A</li>
      <li>sub-heading B</li>
    </ul>
  </li>
</ul>

Jadi CSS memiliki gaya untuk #sidebar uldan #sidebar ul lisudah, tapi saya ingin menambahkan gaya tambahan #sidebar .top-level-navyang TIDAK menurun ke sub-anaknya. Apakah ada cara untuk melakukan ini secara sederhana atau apakah saya perlu mengatur ulang semua gaya sehingga gaya yang dulu #sidebar ulsekarang khusus untuk kelas tertentu?

Saeed Hassanvand
sumber
2
Saya memang mencari di situs untuk pertanyaan serupa dan tidak menemukan apa pun (tidak mengatakan tidak ada, tetapi saya memang melihat). Jika Anda tahu apa itu, bisakah Anda mengarahkan saya ke sana? Terima kasih!
1
stackoverflow.com/questions/747308/breaking-css-inheritance | cukup banyak yang mengatakan apa yang dijawab Matius.
JasonV
1
Jadi saya anggap jawabannya adalah "tidak, tidak ada cara untuk melakukannya secara sederhana - Anda harus mengganti setiap pengaturan gaya secara manual pada sub-item" - apakah saya menafsirkannya dengan benar? Terima kasih lagi.

Jawaban:

38

Sampai saat ini belum ada pemilih induk (atau seperti Shaun Inman memanggil mereka, penyeleksi yang memenuhi syarat ), jadi Anda harus menerapkan gaya ke item daftar anak untuk menimpa gaya pada item daftar induk.

Cascading adalah semacam inti dari Cascading Style Sheets, maka namanya.

Scott
sumber
13
Informasi ini sudah usang sejak IE8. Lihat jawabannya oleh Silviu Postavaru. Harap pertimbangkan untuk mengubah cek ke jawaban yang lebih sesuai.
tmuecksch
lol, saya setuju cascading adalah intinya. Tetapi harus ada cara untuk menghentikan perbanyakan dari induk tertentu yang dimaksudkan untuk menjadi berbeda.
Obay Abd-Algader
72

Anda juga menggunakan pemilih anak

Jadi menggunakan

#parent > child

Akan membuat hanya anak-anak tingkat pertama yang menerapkan gaya. Sayangnya IE6 tidak mendukung pemilih anak.

Jika tidak, Anda bisa menggunakan

#parent child child

Untuk menyetel gaya khusus lain untuk anak-anak yang lebih dari satu tingkat di bawah.

Silviu Postavaru
sumber
1
Bisakah Anda menunjukkan kepada saya tindakan ini di JSFiddle? Saya mencoba untuk memusatkan div yang ditampilkan blok-inline, tetapi masih memusatkan teks di dalam div.
Calmarius
41

Ada properti yang disebut alldalam modul pewarisan CSS3 . Ini bekerja seperti ini:

#sidebar ul li {
  all: initial;
}

Mulai 2016-12, semua browser kecuali IE / Edge dan Opera Mini mendukung properti ini.

Boldewyn
sumber
4
@AndriusDobrotinas menjadi didukung pada akhirnya? Saya tampaknya tidak sepenuhnya memahami komentar Anda. Ada plugin PostCSS yang menyediakan fitur ini, jika Anda menggunakan PostCSS: github.com/maximkoretskiy/postcss-initial
Boldewyn
1
@AndriusDobrotinas, Komentar Anda sangat tidak membangun. Jawabannya diposting demi komunitas; berusaha sekuat tenaga untuk melihat manfaatnya.
Cody
2
Saat ini, hanya IE dan Opera Mini yang tidak mendukungnya, semua browser utama lainnya mendukungnya
Legends
@Boldewyn tidak ada nilai 'default', sejauh yang bisa diketahui dari dokumen w3 tertaut ...
benomatis
@webeno dulu, ketika saya menulis jawabannya: w3.org/TR/2013/WD-css3-cascade-20130103/#all-shorthand Tampaknya ada beberapa perbedaan halus antara yang lama defaultdan yang baru unset, tetapi saat ini saya ' tidak punya waktu untuk menyelidiki lebih lanjut. Jangan ragu untuk mengedit jawaban untuk memperbaruinya.
Boldewyn
26

Anda dapat menggunakan * selektor untuk mengubah gaya anak kembali ke default

contoh

#parent {
    white-space: pre-wrap;
}

#parent * {
    white-space: initial;
}
terimakasih
sumber
1
Itu solusi yang sangat bagus - terutama jika Anda tidak tahu kelas orang tua.
BurninLeo
Saya rasa saya tahu jawabannya tetapi apakah ada cara untuk mengatur ini sebaris? <div id="parent" style="white-space:pre-wrap;*white-space:initial;"/>
1,21 gigawatt
11

Membungkus dengan iframe membuat css induk menjadi usang.

Tuğrul
sumber
2
Lucu bahwa ini adalah jawaban yang dibuat paling buruk karena secara teknis ini adalah satu - satunya cara fisik untuk menghentikan warisan CSS. Bukannya saya berpendapat bahwa Anda harus menggunakannya dengan cara ini.
davidelrizzo
2
Saya sarankan untuk tidak menggunakan CSS secara fisik, biarkan di dunia virtual tempatnya!
michaelward82
Sebenarnya menambahkan iframemembuat komponen anak saya tidak terlihat. Pikiran?
Kevin Ghaboosi
5

Jawaban singkatnya adalah: Tidak, pewarisan CSS tidak mungkin dilakukan. Anda hanya dapat mengganti gaya yang disetel pada orang tua. Lihat spesifikasinya:

Setiap elemen dalam dokumen HTML akan mewarisi semua properti yang diwariskan dari induknya kecuali elemen root ( html), yang tidak memiliki induk. - W3C

Selain menimpa setiap properti yang diwariskan. Anda juga dapat menggunakan initialkata kunci, mis color: initial;. Ini juga dapat digunakan bersama dengan all, misalnya all: initial;, yang akan mengatur ulang semua properti sekaligus. Contoh:

.container {
  color: blue;
  font-style: italic;
}
.initial {
  all: initial;
}
<div class="container">
  The quick brown <span class="initial">fox</span> jumps over the lazy dog
</div>

Tabel dukungan browser menurut Can I use ...

  • all (Saat ini tidak ada dukungan di IE dan Edge, yang lainnya bagus)
  • initial (Saat ini tidak ada dukungan di IE, yang lainnya bagus)

Anda mungkin merasa berguna dengan menggunakan pemilih turunan langsung> dalam beberapa kasus. Contoh:

.list > li {
  border: 1px solid red;
  color: blue;
}
<ul class="list">
  <li>
    <span>HEADING 1</span>
    <ul>
      <li>sub-heading A</li>
      <li>sub-heading B</li>
    </ul>
  </li>
  <li>
    <span>HEADING 2</span>
    <ul>
      <li>sub-heading A</li>
      <li>sub-heading B</li>
    </ul>
  </li>
</ul>

Gaya batas telah diterapkan hanya untuk turunan langsung <li>, seperti borderproperti yang tidak diwariskan. Tapi warna teks telah diterapkan ke semua anak, seperti colorproperti yang diwariskan.

Oleh karena itu, >pemilih hanya akan berguna dengan properti yang tidak diwariskan, dalam hal mencegah pewarisan.

Stiker
sumber
2

Anda dapat menggunakan sesuatu seperti jQuery untuk "menonaktifkan" perilaku ini, meskipun menurut saya ini bukan solusi yang baik karena Anda mendapatkan logika tampilan di css & javascript. Namun, tergantung pada kebutuhan Anda, Anda mungkin menemukan utilitas css jQuery membuat hidup Anda lebih mudah daripada mencoba css hacky, terutama jika Anda mencoba membuatnya berfungsi untuk IE6

Neil Richards
sumber
2

Misalnya jika Anda memiliki dua div dalam dokumen XHTML.

<div id='div1'>
    <p>hello, how are you?</p>
    <div id='div2'>
        <p>I am fine, thank you.</p>
    </div>
</div>

Kemudian coba ini di CSS.

#div1 > #div2 > p{
    color: red;
}

hanya mempengaruhi paragraf 'div2'.

#div1 > p {
    color: red;
} 

mempengaruhi hanya paragraf 'div1'.

pengguna2848911
sumber
2

Anda tidak memerlukan referensi kelas untuk lis. Daripada memiliki suka CSS

li.top-level-nav { color:black; }

kamu bisa menulis

ul#sidebar > li { color:black; }

Ini akan menerapkan gaya hanya ke lis yang langsung turun dari sidebar ul.

stevenvh.dll
sumber
0

cukup setel kembali ke default di pemilih "#sidebar ul li"

Matthew Vines
sumber
Terima kasih atas jawabannya. Ya, saya mengerti bahwa saya dapat mengaturnya kembali ke gaya sub-item, tetapi saya mencoba menghindarinya karena saya menggunakan tema yang tidak saya buat dan saya ingin tahu apakah saya dapat menghemat banyak waktu dengan hanya menggunakan beberapa aturan "jangan-tidak-kaskade: benar" atau sesuatu seperti itu, alih-alih menemukan semua gaya berbeda untuk ul dan li yang tersebar di semua tempat dan kemudian mengkhawatirkan konsekuensi yang tidak diinginkan di area lain dari situs .