Select Every Second Element of a Series of Nested Elements (Each Has Only One Child)

:nth-child() issue selecting every second div

You need nth-of-type instead of nth-child. This will only take <div> tags into account, regardless of what is in between of them.

selector for nth nested elements

In CSS the selector string is largely describing the nesting structure, and there does not currently exist any generational skipping selectors such that you might theoretically do something like .item:nth-grandchild(4) to replace your fifth example.

If reducing verbosity of your css is of high importance to you (lets say you have up 10 or even 100 levels of nesting you are switching on), then really you need to look into modifying the html itself in order to reduce the css needed. That can be done dynamically via server-side scripting (PHP, etc.), or client-side scripting (Javascript), or statically by you. Which way you choose will depend on a variety of factors.

The html modification can be in the form of more specific classes or direct style properties, but I recommend the former. Here are at least four ways css would be reduced:

#1 Multiple Classes, One Indicating Level

Sample HTML

<div class="item L-1">
<div class="item L-2">
<div class="item L-3">
</div>
</div>
</div>

Sample CSS

.item.L-1 {
border-left-color: #somecolor1;
}
.item.L-2 {
border-left-color: #somecolor2;
}
.item.L-3 {
border-left-color: #somecolor3;
}

#2 Multiple Classes, One Indicating Color

Sample HTML

<div class="item LBC-1"> 
<div class="item LBC-2">
<div class="item LBC-3">
</div>
</div>
</div>

Sample CSS

.item.LBC-1 {
border-left-color: #somecolor1;
}
.item.LBC-2 {
border-left-color: #somecolor2;
}
.item.LBC-3 {
border-left-color: #somecolor3;
}

#3 Single Class Name Indicating Level

Sample HTML

<div class="item-L1"> 
<div class="item-L2">
<div class="item-L3">
</div>
</div>
</div>

Sample CSS

[class *= "item-"] {
/* common css properties for the items goes here */
}

.item-L1 {
border-left-color: #somecolor1;
}
.item-L2 {
border-left-color: #somecolor2;
}
.item-L3 {
border-left-color: #somecolor3;
}

#4 Style Properties for Each Item

Sample HTML

<div class="item" style="border-left-color: #somecolor1"> 
<div class="item" style="border-left-color: #somecolor2">
<div class="item" style="border-left-color: #somecolor3">
</div>
</div>
</div>

Sample CSS

/* none to control color */

Discussion of "Best"

Often dynamic solutions end up producing html like that of #4, which ends up making the html very verbose, and I personally would not recommend it. However, those dynamic solutions do not need to do that, but could instead add class names like #1-3.

What is ultimately "best" depends a lot on what you are trying to achieve, how much control you have, and what other properties need changing as well. Personally, I would avoid #2 as well, because it begins to tie presentation too much to html by having a class name associated with the "left border color." To me, solution #1 or #3 would be best, as those are simply setting classes that help the css to know what "level" the .item is at, which then allows for specific targeting to that level for anything you may need it for.

Of course, if you were really dealing with 100 nested levels, then even for solutions #1-3, you might want to look into some css preprocessor to generate the 100 levels of code needed. But the css output would still be far less than the long selector strings needed using the current method you are doing.

Selecting second children of first div children in javascript

Assuming that structure is static you can do this:

var mainDiv = document.getElementById('mainDiv'),
childDiv = mainDiv.getElementsByTagName('div')[0],
requiredDiv = childDiv.getElementsByTagName('div')[1];

Further reading: .getElementsByTagName() (from MDN).

Select child in order even if it's inside another div

I don't think css can solve your problem, but a simple js can.

document.querySelectorAll("a").forEach((el, index) => {
if (index % 4 == 0)
el.classList.add("pink");
else if (index % 4 == 1)
el.classList.add("blue");
else if (index % 4 == 2)
el.classList.add("green");
else if (index % 4 == 3)
el.classList.add("yellow");
});
.pink {
color: pink;
}

.blue {
color: blue;
}

.yellow {
color: yellow;
}

.green {
color: green;
}
<div>
<a class="first">pink</a>
<a class="second">blue</a>
<a class="third">green</a>
<a class="fourth">yellow</a>
<a class="fifth">pink</a>
<div>
<a class="sixth">blue</a>
<a class="seventh">green</a>
<div>
<a class="eighth">yellow</a>
<a class="ninth">pink</a>
</div>
</div>
<a class="tenth">blue</a>
</div>

CSS select direct children, but not if inside another nested child

Use div.parent > p.p

> is the child combinator. It matches only those elements matched by the second selector that are the direct children of elements matched by the first.

div.parent > p.p {color:green;}
<div class="parent">    <div class="ignore-me">        <p class="p">don't select me</p>        <p class="p">don't select me</p>        <p class="p">don't select me</p>        <!-- I don't know how many <p> gonna be here  -->    </div>    <p class="p">select me</p>    <p class="p">select me too</p></div>

How to select nth-child in SASS within a nested selectors

If you need to group the selectors in this way - I recommend using the @at-root directive.

The @at-root directive causes one or more rules to be emitted at the
root of the document, rather than being nested beneath their parent
selectors.

.group-left {
.clip-item & {
padding: 0;
}
@at-root .clip-item &:nth-child(2n+1) {
background: blue;
}
@at-root .clip-item &:nth-child(2n+2) {
background: gray;
}
}

.group-right {
.clip-item & {
padding: 0;
}
@at-root .clip-item &:nth-child(2n+1) {
background: blue;
}
@at-root .clip-item &:nth-child(2n+2) {
background: gray;
}
}

Codepen demo (View compiled CSS)

Also, this CSS-tricks post may help:

The & doesn't allow you to selectively traverse up your nested
selector tree to a certain place and only use a small portion of the
compiled parent selector that you want to use.


By the way:

Even though it's working, I don't think it's the right way

Well actually, your SCSS is not currently producing the requested CSS.



Related Topics



Leave a reply



Submit