Styling sibling elements on hover

Hey all! I've a navbar where I want the sibling nav-items to have a particular css when I hover over a nav-item. For example, if I've 5 nav-items and I hover on the 1st one, the next 4 nav-items should have another css. I'm not able to figure out how to do that. Please help! Here's the code:
<nav id="navbar">
<div className="nav-item">
<a href="/">// Home</a>
</div>
<div className="nav-item">
<a href="/#expertise">// Expertise</a>
</div>
<div className="nav-item">
<a href="/#work">// Work</a>
</div>
<div className="nav-item">
<a href="/#experience">// Experience</a>
</div>
<div className="nav-item">
<a href="/#contact">// Contact</a>
</div>
</nav>
<nav id="navbar">
<div className="nav-item">
<a href="/">// Home</a>
</div>
<div className="nav-item">
<a href="/#expertise">// Expertise</a>
</div>
<div className="nav-item">
<a href="/#work">// Work</a>
</div>
<div className="nav-item">
<a href="/#experience">// Experience</a>
</div>
<div className="nav-item">
<a href="/#contact">// Contact</a>
</div>
</nav>
#navbar {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
gap: 1.75em;
height: 50px;
.nav-item {
a {
text-decoration: none;
color: #fff;
font-weight: 500;
}
}
}
#navbar {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
gap: 1.75em;
height: 50px;
.nav-item {
a {
text-decoration: none;
color: #fff;
font-weight: 500;
}
}
}
17 Replies
Joao
Joao•12mo ago
With only CSS... I tried just now and I got stuck on two things: I can make it work but only for items after the one I'm currently hovering over. Or, I can make it work but I have to apply the hover over the navbar itself which means there's a short period where the cursor is not hovering over any link and it applies to all of them. I'm curious how could this one be solved, maybe using :has() or :where()?
Mannix
Mannix•12mo ago
with :has() you can do
#navbar:has(:hover) .nav-item a:not(:hover){
color:blue;
}
#navbar:has(:hover) .nav-item a:not(:hover){
color:blue;
}
Joao
Joao•12mo ago
Ah unfortunately :has still doesn't work on Firefox
Mannix
Mannix•12mo ago
yup firefox team is slacking big time
Joao
Joao•12mo ago
Works great, nice and concise Yes, they need to catch up on this one it's such a game changer
Satya
Satya•12mo ago
Thank you @mannix_ and @joao6246 A quick follow-up, I've added a transition to the color and it works on hover but when we hover out there's a sudden change How do I add a transition for that?
&:has(:hover) .nav-item a:not(:hover) {
color: #7a7a7a;
transition: color 0.5s ease-in-out;
}
&:has(:hover) .nav-item a:not(:hover) {
color: #7a7a7a;
transition: color 0.5s ease-in-out;
}
Jochem
Jochem•12mo ago
Put the transition in the non hover selector The color is the only thing that needs to go in the selector with has
Satya
Satya•12mo ago
Thanks a lot @jochemm ! Hi, I'm sorry to keep bothering you I want the navbar to be sticky and visible only after the user has scrolled to a certain section. Can you please give some pointers?
Jochem
Jochem•12mo ago
you can either use https://caniuse.com/css-sticky or toggle position: fixed using javascript and an onscroll handler / intersection observer it's best to make new threads for new topics btw, you get fresh eyes and it keeps things organized in case anyone is trying to find info. We started this talking about hover states, and now we're talking about sticky elements
Satya
Satya•12mo ago
Hello! I used scrollY to get the page offset and an useEffect to handle it. Yeah, sorry for that
Jochem
Jochem•12mo ago
ah, yeah, that's the react way of doing the latter option
Satya
Satya•12mo ago
is the approach correct?
Jochem
Jochem•12mo ago
it's a valid option yeah
skinnyK
skinnyK•12mo ago
Be careful with :has firefox is only using it when the user has it flagged Caniuse.com
Joao
Joao•12mo ago
On the other hand, once Firefox has a feature behind a flag as experimental it usually means there are plans to integrate it soon. According to this bug report there were planning to start working on this feature throughout the first half of the year, although progress or ETA are not very detailed. https://bugzilla.mozilla.org/show_bug.cgi?id=418039#c62
Kevin Powell
Kevin Powell•12mo ago
Yeah, the ETA for it has already past, but it seems like they have a number of bugs still holding things up. I know Safari shipped theirs with a few bugs and has been fixing them since shipping... I sort of prefer the "we'll take longer and get it right" approach though. I know that's the hold-up with subgrid for Chrome as well.
Joao
Joao•12mo ago
Yes, me too. I mean afterall CSS is getting so many new features so quickly I don't even have time to use them so might as well get them right 😄