I know that there does not exist a CSS parent selector, but is it possible to style a parenting element when hovering a child element without such a selector?
To give an example: consider a delete button that when hovered will highlight the element that is about to become deleted:
<div>
<p>Lorem ipsum ...</p>
<button>Delete</button>
</div>
By means of pure CSS, how to change the background color of this section when the mouse is over the button?
I know it is an old question, but I just managed to do so without a pseudo child (but a pseudo wrapper).
If you set the parent to be with no pointer-events, and then a child div with pointer-events set to auto, it works:)
Note that <img> tag (for example) doesn't do the trick.
Also remember to set pointer-events to auto for other children which have their own event listener, or otherwise they will lose their click functionality.
div.parent {
pointer-events: none;
}
div.child {
pointer-events: auto;
}
div.parent:hover {
background: yellow;
}
<div class="parent">
parent - you can hover over here and it won't trigger
<div class="child">hover over the child instead!</div>
</div>
Edit:
As Shadow Wizard kindly noted: it's worth to mention this won't work for IE10 and below. (Old versions of FF and Chrome too, see here)
Well, this question is asked many times before, and the short typical answer is: It cannot be done by pure CSS. It's in the name: Cascading Style Sheets only supports styling in cascading direction, not up.
But in most circumstances where this effect is wished, like in the given example, there still is the possibility to use these cascading characteristics to reach the desired effect. Consider this pseudo markup:
<parent>
<sibling></sibling>
<child></child>
</parent>
The trick is to give the sibling the same size and position as the parent and to style the sibling instead of the parent. This will look like the parent is styled!
Now, how to style the sibling?
When the child is hovered, the parent is too, but the sibling is not. The same goes for the sibling. This concludes in three possible CSS selector paths for styling the sibling:
parent sibling { }
parent sibling:hover { }
parent:hover sibling { }
These different paths allow for some nice possibilities. For instance, unleashing this trick on the example in the question results in this fiddle:
div {position: relative}
div:hover {background: salmon}
div p:hover {background: white}
div p {padding-bottom: 26px}
div button {position: absolute; bottom: 0}
Obviously, in most cases this trick depends on the use of absolute positioning to give the sibling the same size as the parent, ánd still let the child appear within the parent.
Sometimes it is necessary to use a more qualified selector path in order to select a specific element, as shown in this fiddle which implements the trick multiple times in a tree menu. Quite nice really.
Another, simpler "alternate" approach (to an old question)..
would be to place elements as siblings and use:
Adjacent Sibling Selector (+)
or
General Sibling Selector (~)
<div id="parent">
<!-- control should come before the target... think "cascading" ! -->
<button id="control">Hover Me!</button>
<div id="target">I'm hovered too!</div>
</div>
#parent {
position: relative;
height: 100px;
}
/* Move button control to bottom. */
#control {
position: absolute;
bottom: 0;
}
#control:hover ~ #target {
background: red;
}
Demo Fiddle here.
there is no CSS selector for selecting a parent of a selected child.
you could do it with JavaScript
As mentioned previously "there is no CSS selector for selecting a parent of a selected child".
So you either:
use a CSS hack as described in NGLN's answer
use javascript - along with jQuery most likely
Here is the example for the javascript/jQuery solution
On the javascript side:
$('#my-id-selector-00').on('mouseover', function(){
$(this).parent().addClass('is-hover');
}).on('mouseout', function(){
$(this).parent().removeClass('is-hover');
})
And on the CSS side, you'd have something like this:
.is-hover {
background-color: red;
}
In 2022:
This can be now achieved with CSS only, using the :has pseudo-class and the following expression:
div:has(button:hover) {}
Here's a snippet showcasing the original proposition:
div:has(button:hover) {
background-color: cyan;
}
<div>
<p>Lorem ipsum ...</p>
<button>Delete</button>
</div>
See browser support here. At the time of writing, all major browser support it—except Firefox, which still has a flawed experimental implementation.
This solution depends fully on the design, but if you have a parent div that you want to change the background on when hovering a child you can try to mimic the parent with a ::after / ::before.
<div class="item">
design <span class="icon-cross">x</span>
</div>
CSS:
.item {
background: blue;
border-radius: 10px;
position: relative;
z-index: 1;
}
.item span.icon-cross:hover::after {
background: DodgerBlue;
border-radius: 10px;
display: block;
position: absolute;
z-index: -1;
top: 0;
left: 0;
right: 0;
bottom: 0;
content: "";
}
See a full fiddle example here
This is extremely easy to do in Sass! Don't delve into JavaScript for this. The & selector in sass does exactly this.
http://thesassway.com/intermediate/referencing-parent-selectors-using-ampersand
i have 2 div elements in html :
<body>
<div id="one"></div>
<div></div>
</body>
I want to hide div elements after div with id="one" from CSS, I tried this :
#one:after{display:none}
This doesn't work any other way to do?
No, :after pseudo doesn't do that, you need to use
#one + div {
display: none;
}
Demo
And if you want to hide ALL div followed by #one you will have to use
#one ~ div {
display: none;
}
Demo 2
:after applies to generated content. You want the adjacent sibling combinator:
#one + * {
}
If you know the exact position of the child element (like in you case its 2nd child), you can use nth-child pseudo class
div:nth-child(2)
{
display:none;
}
Fiddle:http://jsfiddle.net/ankur1990/HDq2T/
I can't find how to do this online, how do I go about selecting any elements within a element and apply styles to them. For example:
HTML:
<div class="cont">
<div class="txt">Hello World!</div>
<img src="img1.jpg">
<img src="img2.jpg">
</div>
CSS:
.txt:hover + img {
display:none;
}
I want that class style to hide ALL images next to it. It only hides ONE image at the moment though...
If you want to hide all succeeding image elements, use the general sibling combinator, ~.
.txt:hover ~ img {
display:none;
}
EXAMPLE HERE
You were using the adjacent sibling combinator, +, which will only hide the adjacent element.
You can do this in two ways; With CSS-only, and with jQuery:
CSS-way:
.txt:hover ~ img {
display:none;
}
jQuery-way:
$(function() {
$('.txt').hover(function() {
$('img').toggle();
});
});
If .text is hovered, how do I also haver .imageis?
All My Clipboards
<a class="imageis sprite_image_base" href="#"></a>
I tried doing something like this in my CSS:
.text:hover, .imageis:hover + .text {
background-position: -107px -311px !important;
height: 16px;
margin-right: 8px;
vertical-align: middle;
width: 23px;
}
Note: I want to do this with pure css without jquery.
I don't know why others are taking about Javascript, this is easily done with CSS.
You use the adjacent sibling combinator or general sibling combinator.
First, declare that you want .text to be hovered for something to happen, like this: .text:hover, then add a sibling combinator: ~ or +, and finally select the sibling you want to affect, in this case: .imageis.
Put it together and you get:
.text:hover + .imageis {
/* css-stuff */
}
You could also select both elements' parent and do a regular descendant selector, like this:
.parent:hover .imageis {
/* css-stuff */
}
I want to change another element property on hover of a element. So far I've I came up with the following CSS:
#test3:hover #test4
{
background-color: red;
}
<div id="test3">three</div>
<div id="test4">four</div>
However, this is not working. Is this possible at all? What would you suggest?
#test3:hover #test4
This means, target an element test4 that is a child of test3. You want the + sibling selector instead:
#test3:hover + #test4
{
background-color: red;
}
Browser compatibility table