CSS Select Sibling of An Element with A Specific Sub-Element? - css

The snippet below is a part of a much larger structure with many .step elements.
I need to match all .stepText elements that are next to .stepTitleAndImages ul.standard
In other words, match all .stepText elements that have .step parent that has .stepTitleAndImages child that has .stepImages.standard child
<div class="step">
<div class="stepTitleAndImages">
<h3 class="stepTitle"></h3>
<ul class="stepImages standard"></ul>
<div class="clearer"></div>
</div>
<div class="stepText "></div> **HOW TO SELECT ALL ELEMENTS LIKE THIS ONE?**
<div class="clearer"></div>
</div>
<div class="step">
<div class="stepTitleAndImages">
<h3 class="stepTitle"></h3>
<ul class="stepImages medium"></ul>
<div class="clearer"></div>
</div>
<div class="stepText "></div>
<div class="clearer"></div>
</div>
PS: I cannot modify the HTML. Cannot use anything other than pure CSS.

Just use this for selecting first case
.step:nth-child(1) .stepText {
... Your CSS here
}
For second one use
.step:nth-child(2) .stepText {
... Your CSS here
}
For selecting both use
.step .stepText {
... Your CSS here
}
Then you should require jquery for that
Selecting Parents sibling is not possible only with pure CSS yet, You can achieve this by a single line of jquery:
$('ul.standard').parent().siblings(".stepText").css(...your CSS here);

This cannot be done with your HTML structure and with pure CSS. The closest solution to your problem, changing the HTML structure and with pure CSS, would be to move the standard class to its parent tag:
<div class="stepTitleAndImages standard">
<h3 class="stepTitle"></h3>
<ul class="stepImages"></ul>
<div class="clearer"></div>
</div>
This would allow you to use the adjacent sibling selector (+), which matches the second selector if it's the direct next sibling of the first, like this:
.stepTitleAndImages.standard + .stepText {
/* Styles */
}
A more flexible approach would be to use the general sibling selector which would match any sibling preceded by the first selector, not only the direct next one:
.stepTitleAndImages.standard ~ .stepText {
/* Styles */
}
The :has pseudo-class is in development by Mozilla, but it hasn't hit any stable browsers yet. With it, and with your HTML structure, you could go:
.stepTitleAndImages:has(.standard) + .stepText {
/* Styles */
}
Unfortunately, currently you can't solve this in any other way with CSS (and with your HTML structure) only.

Related

How do i style two same class divs differently?

So basically I've got a setup that spits out the code in the following fashion..
<div class="parent">
<div class="subparent">
<div class="TARGETCLASS"></div>
</div>
<div class="subparent">
<div class="TARGETCLASS"></div>
</div>
</div> //close for the parent class
Now what I'm trying to do is to style "TARGETCLASS" that comes above one way and the "TARGETCLASS" that comes second in another way. I tried n-th child, but unable to achieve the result I'm looking for. There's no way to add additional classes or ID to the existing "TARGETCLASS" class. Otherwise I wouldn't be posting this question :)
Also, the "subparent" class also is same. for both the targetclass classes. That's the issue
Thanks in advance for taking your time to answer this question for me.
Cheers!
Looks like you've got some mal-formed tags in your html. And nth-child should work just fine. Also, make sure you place the nth-child selector on the subparent class, and not TARGETCLASS. It's common to mis-place the child selector. Try this:
<div class="parent">
<div class="subparent">
<div class="TARGETCLASS">
first-child
</div>
</div>
<div class="subparent">
<div class="TARGETCLASS">
second-child
</div>
</div>
</div>
<style>
.parent .subparent .TARGETCLASS {
background-color:#f00;
}
.parent .subparent:nth-child(1) .TARGETCLASS {
background-color:#0f0;
}
</style>
fiddle: https://jsfiddle.net/8ejxokuj/
I would use nth-of-type selector like so:
.parent{}
.parent > .subparent {} //targets both subparents
.parent > .subparent:nth-of-type(2) {} //targets the second subparent
.parent > .subparent:nth-of-type(2) > .TARGETCLASS{} //targets the child of the second subparent
The nth-of-type() selector enables you to style a specific element amongst a series, in this case we targeted the second .subparent then specified the child we needed.
I hope this helps!
It seems, it is working by the nth child.
it is about how childrens are called. Not like "Ask parent to find nth child, but ask child, how far is he from parent"
.parent .subparent:nth-child(1) {background: #FEE; color:RED;}
.parent .subparent:nth-child(2) {background: #EEF; color:blue;}
<div class="parent">
<div class="subparent">
<div class="TARGETCLASS">aaa</div>
</div>
<div class="subparent">
<div class="TARGETCLASS">bbb</div>
</div>
//close for the parent class
</div>

Using CSS :hover to change style but only when adjacent to particular class

I'm experimenting with Bootstrap.js panels that can collapse. I'd like to see if it's possible to change styling of a panel-heading element but only when it's adjacent to a panel-collapse element. The selector below will change all headings obviously.
.panel-heading:hover {}
Because I'm trying to look ahead to see if the target element is followed by a particular class I'm not sure I see if CSS can support this.
<!-- This should change style of panel-heading when hovering over the panel-heading element -->
<div class="panel">
<div class="panel-heading">
</div>
<div class="panel-collapse">
</div>
</div>
<!-- This should NOT change the style of the panel-heading when hovering over the panel-heading element -->
<div class="panel">
<div class="panel-heading">
</div>
<div class="panel-body">
</div>
</div>
There is no way to currently do this in CSS3, however there is something being proposed in CSS Selectors Level 4. This feature has been widely requested.
Relational Pseudo-class: :has()
Such that you could do something like:
.panel:has(.panel-collapse) .panel-heading {
}
Meaning, apply styles to all .panel-heading classes that are a child of .panel classes containing .panel-collapse
This is a great article on upcoming CSS Selectors Level 4: https://www.sitepoint.com/future-generation-css-selectors-level-4/
In the meantime, you'll have to use something like jQuery. You could add a class like .panel-hoverable to all .panel elements that contain elements with the class .panel-collapse

How to get different class selectors using nth-child in css

I have these codes
<div class="test">
<div class="tag1"></div>
<div class="tag1"></div>
<div class="tag1"></div>
<div class="tag2"></div>
<div class="tag2"></div>
<div class="tag2"></div>
</div>
Now I want to get second child of .tag2 selector.
I try this code and it's not working, but when I use .tag1 it's working.
.test .tag2:nth-child(2) {
background-color: #000;
}
How can i fix this?
:nth-child works on elements, not on other selectors. Here your .tag2 element is the 4th element in the list.
When browsers begin to implement the Selectors Level 4 standards we'll be able to achieve this using the :nth-match structural pseudo-class selector, but unfortunately that's quite a way off yet.
A Potential CSS Solution (Markup-dependant)
If your markup will always be that the first .tag2 will only ever follow .tag1 and the second .tag2 will only ever follow .tag2, you can fake it with this:
.tag1 + .tag2 + .tag2 {
background-color: #000;
}
This selects the .tag2 element which immediately follows a .tag2 element which immediately follows a .tag1 element.
A JavaScript Solution
If you can't do that then you'll have to go for a JavaScript solution instead (or implement something on the back-end which generates the content).
The below example pulls all .tag2 elements within your .test container, then grabs the 2nd one ([1] here, remember the 0 index: [1] = 2nd), then applies the style to that element.
You'll need to add in some checks to ensure this element exists before applying the style.
document.querySelector('.test').querySelectorAll('.tag2')[1].style.background = '#000'
<div class="test">
<div class="tag1">tag1</div>
<div class="tag1">tag1</div>
<div class="tag1">tag1</div>
<div class="tag2">tag2</div>
<div class="tag2">tag2</div>
<div class="tag2">tag2</div>
</div>
I know your question isn't tagged with JavaScript, but a good solution with JS is as follows:
var alltagtwos = document.getElementsByClassName("tag2");
alltagtwos[1].className += " secondel";
.tag2.secondel {
background-color: #000;
color: #fff;
}
<div class="test">
<div class="tag1">tag1 - 1</div>
<div class="tag1">tag1 - 2</div>
<div class="tag1">tag1 - 3</div>
<div class="tag2">tag2 - 1</div>
<div class="tag2">tag2 - 2</div>
<div class="tag2">tag2 - 3</div>
</div>
What I've done here is add all elements with the class .tag2 into an array-like object using getElementsByClassName. I then select the second element which has the class .tag2 (index starts at zero, so I've select [1]) and appended another class to it (.secondel) which I've then styled with CSS.

CSS selector - not under direct parent

I have a nested display and I'm trying to style all nested collection besides the first one
<div class="container">
<div class="main-collection">
<div class="collection">
<!-- lots of code -->
<div class="collection"></div>
<!-- lots of code -->
<div class="collection"></div>
<!-- lots of code -->
<div class="collection">
<!-- lots of code -->
<div class="collection"></div>
<!-- lots of code -->
<div class="collection"></div>
</div>
</div>
</div>
</div>
I want all but the one directly under main-collection
I'm using less.
.main-collection > .collection .collection {
/* your styles here */
}
Working demo
Select all .collection elements that are descendants of a .collection element that is it's self a DIRECT descendant (>) of .main-collection
try to this in less css
.main-collection{
>.collection{
// here style
>.collection{
// here style
>.collection{
// here style
}
}
}
}
The most obvious way to do this is to use nth-child, although support is limited for older browsers. If you have control over your markup, have you considered using a class to identify the element you want to style differently, in particular?
Do the css for all of the elements first and then below that select only the first one and do your styles for it. The css below overrides the other stuff above. You can do it with :nth-child(1) or I guess :first-childor probably even :first-of-type and :nth-of-type(1)
.main-collection .collection {
css for all of them
}
.main-collection .collection:nth-child(1) {
this will only target the first one
}

css :target on children

Suppose we have this html
<div class="a">
<div>...</div>
...
<div id="b">xyz</div>
</div>
<div class="a">
<div>...</div>
...
<div id="c">abc</div>
</div>
Applying some style on #b upon targeting it in url is easy to do with the css :target selector.
Is it possible to apply some some style on the parent div with class="a" as well?
No, since you would need a CSS parent selector for that. Nothing in CSS2 and CSS3 has been specified for that. CSS4 does have (a somewhat) parent selector (called the subject selector) using the ! symbol, but no browser supports it (yet).
You can add an extra id to your <div class="a"> and make it:
<div class="a" id="abc">
...and still use the :target.
No, CSS cascades (CSS = Cascading Style Sheets), it doesn't go up.
You will need to explicitly apply styling to the parent element.
You would be better doing something like #otinanai suggested and adding a class to your child divs. e.g.
HTML
<div class="a">
<div>...</div>
...
<div class="aItem" id="b">xyz</div>
</div>
<div class="a">
<div>...</div>
...
<div class="aItem" id="c">abc</div>
</div>
CSS
.a {
border: 1px solid #000;
}
.aItem {
color: #999;
}
So you will use classes to consistently style your elements. Otherwise you will have to write CSS for D, E, F G through to Z, and only use the ID's for bookingmarking/URL purposes.

Resources