CSS, bir elemanın sahip olduğu çocuk sayısını tespit edebilir mi?


304

Muhtemelen kendi sorumu cevaplıyorum ama çok merak ediyorum.

CSS'nin bir ebeveynin bireysel çocuklarını seçebileceğini biliyorum, ancak ebeveyninin belirli bir miktarda çocuğu varsa, bir kabın çocuklarını şekillendirmek için destek var.

Örneğin

container:children(8) {
  // style the parent this way if there are 8 children
}

Kulağa garip geldiğini biliyorum, ama müdürüm benden kontrol etmemi istedi, kendi başıma bir şey bulamadı, bu yüzden aramayı bitirmeden önce SO'ya dönmeye karar verdim.


2
Miktar Sorgu SCSS
Jakob E

Yanıtlar:


695

Açıklama:

Orijinal sorudaki daha önceki ifadelerden dolayı, birkaç SO vatandaşı bu cevabın yanıltıcı olabileceği endişelerini dile getirmiştir. CSS3'te, stillerin sahip olduğu çocuk sayısına bağlı olarak bir üst düğüme uygulanamayacağını unutmayın . Ancak, stiller olabilir sayısına bağlı çocuk düğümler uygulanacak kardeşleri onlar var.


Orijinal cevap:

İnanılmaz bir şekilde, bu artık tamamen CSS3'te mümkün.

/* one item */
li:first-child:nth-last-child(1) {
/* -or- li:only-child { */
    width: 100%;
}

/* two items */
li:first-child:nth-last-child(2),
li:first-child:nth-last-child(2) ~ li {
    width: 50%;
}

/* three items */
li:first-child:nth-last-child(3),
li:first-child:nth-last-child(3) ~ li {
    width: 33.3333%;
}

/* four items */
li:first-child:nth-last-child(4),
li:first-child:nth-last-child(4) ~ li {
    width: 25%;
}

İşin püf noktası, ilk çocuğu aynı zamanda sondan n'inci çocukken seçmektir. Bu, kardeş sayısına göre etkili bir şekilde seçer.

Bu tekniğin kredisi André Luís (keşfedildi) ve Lea Verou'ya (rafine) gider.

Sadece CSS3'ü sevmiyor musunuz? 😄

CodePen Örneği:

Kaynaklar:


7
Çok kullanışlı. : Ben bu tekniğin kullanıldığı bir SUKDÖ'nün mixin yazdı codepen.io/anon/pen/pJeLdE?editors=110
SimpleJ

1
@IanSteffy Bunu Chrome 45.0.2454.85 (64 bit) üzerinde test ettim ve iyi çalışıyor…?
Matthemattics

2
Codepen çalışır ama benim proje ile değilse o zaman kesinlikle benim hatam. Benim hatam. Bu cevap doğru! Doğru diyorum!
Ian S

3
Bunun neden işe yaradığını eklemek güzel olabilir, çünkü birden fazla sahte seçiciye alışkın olmayan insanlar için (şimdiye kadar olduğum gibi). Burada olan şey, bunun aynı zamanda x başından / üstünden çocuğu ve sondan y çocuğunu seçmesidir. Ve bu sadece tam olarak x + y çocukları varsa bir şey seçer.
Legolas

7
Bunun yerine :first-child:nth-last-child(1)de kullanabileceğinizi unutmayın :only-child.
Adam Reis

40

Hayır. Pek değil. Sizi biraz yakınlaştırabilecek, ancak örneğinizde çalışmayacak ve en iyi tarayıcı uyumluluğuna sahip olmayan birkaç seçici var.

:only-child

Bu :only-child, yalnızca öğenin üst öğesinin bir alt öğesi olduğunda uygulandığı anlamında birkaç gerçek sayma seçicisinden biridir. İdealleştirilmiş örneğinizi kullanarak, children(1)muhtemelen yapacağınız gibi davranır .

:nth-child

:nth-childEğer gerçekten yapmak aradığınızı bağlı gitmek istediğiniz yere seçici aslında sizi alabilirsiniz. Eğer 8 çocuk varsa tüm unsurları şekillendirmek istiyorsanız, şansınız kalmaz. Bununla birlikte, 8. ve sonraki öğelere stiller uygulamak istiyorsanız şunu deneyin:

p:nth-child( n + 8 ){
    /* add styles to make it pretty */
}

Ne yazık ki, bunlar muhtemelen aradığınız çözümler değil. Sonunda, stilleri sayıya göre uygulamak için muhtemelen bazı Javascript sihirbazları kullanmanız gerekecektir. CSS çözümü.

Sahte sınıflarda W3 CSS3 Spec

EDIT Sorunuzu biraz farklı okuyorum - ebeveynleri şekillendirmenin birkaç yolu var , çocukları değil. Birkaç seçiciyi istediğin gibi atamama izin ver:

:empty ve :not

Bu, çocuğu olmayan öğeleri stilize eder. Tek başına yararlı değil, ancak :notseçiciyle eşleştirildiğinde , yalnızca çocuk sahibi olan öğelere stil uygulayabilirsiniz:

div:not(:empty) {
    /* We know it has stuff in it! */
}

Burada saf CSS ile kaç çocuk bulunduğunu sayamazsınız, ancak harika şeyler yapmanıza izin veren başka bir ilginç seçicidir.


Orijinal sorunun düzenlendiğini ve ilk "Hayır" ı biraz yanıltıcı hale getirdiğini belirtmek gerekir (sadece fyi 😛)
Matthemattics

18

NOT: Bu çözüm, istediğiniz gibi ana öğeyi değil, belirli uzunluktaki kümelerin alt öğelerini döndürür. Umarım, hala faydalıdır.

Andre Luis bir yöntem buldu: http://lea.verou.me/2011/01/styling-children-based-on-their-number-with-css3/ Ne yazık ki, sadece IE9 ve üzeri sürümlerde çalışıyor.

Temel olarak, nth-child () öğesini bir öğenin konumu ile ilgilenen diğer sözde sınıflarla birleştirirsiniz. Bu yaklaşım, belirli uzunluklara sahip eleman setlerinden elemanlar belirlemenizi sağlar .

Örneğin :nth-child(1):nth-last-child(3), bir kümedeki ilk öğeyle eşleşirken, kümenin sonundaki 3. öğedir. Bu iki şey yapar: setin sadece üç unsuru olduğunu ve bu üç unsurdan birincisine sahip olduğumuzu garanti eder. Üç eleman kümesinin ikinci elemanını belirtmek için kullanırız :nth-child(2):nth-last-child(2).


Örnek 1 - Sette üç öğe varsa tüm liste öğelerini seçin:

li:nth-child(1):nth-last-child(3),
li:nth-child(2):nth-last-child(2),
li:nth-child(3):nth-last-child(1) {
    width: 33.3333%;
}

Lea Verou'dan Örnek 1 Alternatifi :

li:first-child:nth-last-child(3),
li:first-child:nth-last-child(3) ~ li {
    width: 33.3333%;
}


Örnek 2 - Üç liste öğesiyle kümenin son öğesini hedefleyin:

li:nth-child(3):last-child {
    /* I'm the last of three */
}

Örnek 2 alternatifi:

li:nth-child(3):nth-last-child(1) {
    /* I'm the last of three */
}


Örnek 3 - Dört liste öğesiyle kümenin ikinci öğesini hedefleyin:

li:nth-child(2):nth-last-child(3) {
    /* I'm the second of four */
}

1
yine, bu çocuk değil kardeş sayısıdır
TMS

@TMS kabul edilen yanıtın düzenlemesine bakın - OP'nin sorusu garip bir şekilde ifade edildi
ifugu

Bu yaklaşım, her öğenin listedeki konumuna göre farklı bir şekilde şekillendirilmesi gerektiğinde, örneğin dairesel dönüşümler bile elde etmek için mükemmeldir: li:nth-child(3):nth-last-child(1) { transform: rotate(120deg); } li:nth-child(2):nth-last-child(2) { transform: rotate(240deg); }vb ...
Greg Smith

11

Matt'in çözümü üzerinde çalışırken, aşağıdaki Pusula / SCSS uygulamasını kullandım.

@for $i from 1 through 20 {
    li:first-child:nth-last-child( #{$i} ),
    li:first-child:nth-last-child( #{$i} ) ~ li {
      width: calc(100% / #{$i} - 10px);
    }
  }

Bu, öğe sayısını hızla genişletmenize olanak tanır.


4
Bunun yerine Flexbox'ı kolayca kullanabilirsiniz…
Michał Miszczyszyn

6

evet bunu nth-child kullanarak yapabiliriz

div:nth-child(n + 8) {
    background: red;
}

Bu, 8. div çocuğunu kırmızılaştıracaktır. Bu yardımcı olur umarım...

Ayrıca, birisi "hey, css kullanarak tarz ile yapılamaz, JS kullanın!" Onlardan hemen şüphe edin. CSS günümüzde son derece esnektir

Örnek :: http://jsfiddle.net/uWrLE/1/

Örnekte ilk 7 çocuk mavi, sonra 8 çocuk kırmızı ...


1
Belki de talihsiz destek eksikliği hakkında bir not ekleyin ?
Benesch

2
Bunun tam olarak Brodie'nin sorduğu şey olduğunu düşünmüyorum - bu, belirli bir miktardan sonra çocukları şekillendirecek, ancak çocuklarının sayısına göre ata / içeren öğeyi seçemez.
Ben Hull

Bu aslında oldukça iyi bir bilgi olsa da, teşekkürler alan ama arı haklı, "bir element bu kadar çocuk bize bu tarzda sahipse" demeye çalışıyordum. ilk 7 yalnız ve çıplak olurdu.
Brodie

@primatology - nth-child özelliğini desteklemeyen tek tarayıcı IE <9'dur. Tüm diğerleri iki veya daha fazla sürümü destekliyor.
Rob

-1 Bu div çocuğunu kırmızı yapmayacak, bu div'i kardeşleri içindeki numarasına göre kırmızı yapacaktır ! Div'in çocuğuyla hiçbir şekilde ilgili değildir!
TMS

5

Eğer saf CSS (scss kullanarak) yapacak ama aynı üst sınıf içinde farklı unsurları / sınıfları varsa bu sürümü kullanabilirsiniz !!

  &:first-of-type:nth-last-of-type(1) {
    max-width: 100%;
  }

  @for $i from 2 through 10 {
    &:first-of-type:nth-last-of-type(#{$i}),
    &:first-of-type:nth-last-of-type(#{$i}) ~ & {
      max-width: (100% / #{$i});
    }
  }

-1

Hayır, CSS'de böyle bir şey yok. Bununla birlikte, çocuk sayısını hesaplamak ve stil uygulamak için JavaScript kullanabilirsiniz.


1
@ Lübnah Bunun neden doğru olmadığını açıklayabilir misiniz?
Gabriel Santos
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.