How to use :not selector with links [duplicate] - css

This question already has answers here:
CSS negation pseudo-class :not() for parent/ancestor elements
(2 answers)
Closed 7 years ago.
i have a hover effect for the links on my website. i want these to apply to every link EXCEPT ones in a particular div.
Example HTML
<div id="menu">
<div class="menu_item">
<a href="index.html" title="Home" target="_self">
<img src="_images/_menu/Home.png"
onmouseover="this.src='_images/_menu/homeHover.png'"
onmouseout="this.src='_images/_menu/Home.png'"
onclick="this.src='_images/_menu/homePressed.png'" alt=""/></a>
</div>
</div>
The CSS i have been trying to us
a:hover:not(.menu_item) {
background-color: #D6910E;
color: #FFE1A7;
} *no change*
a:hover:not(#menu) { *no change*
a:hover:not(#menu.menu_item) { *turns off hover on all links*
a:hover:not(#menu .menu_item) { *turns off hover on all links*

want these to apply to every link EXCEPT ones in a particular div
The standard approach to such problems in CSS is to give the general rule first, then the specific rule to override it. Using :not is a slippery slope and should be reserved for special cases. So:
/* State the general rule first */
a:hover {
background-color: #D6910E;
color: #FFE1A7;
}
/* Give the exception */
.menu_item a:hover {
background-color: transparent;
color: inherit;
}
If you do want to use :not, you have to understand that the predicate applies to the current element:
a:hover:not(#menu)
does not mean a tags being hovered which are not children of #menu; it means a tags being hovered which are not themselves #menu (which will always match). To do what you are trying to do with :not, you would want to try something like
:not(#menu) a:hover
However, this will also not work, because it means "a tags being hovered which have any ancestor which is not #menu", which will also almost always match.

Why you don't make it easier ?
Like
a:hover {
background-color:red;
color:red;
}
#menu .menu_item:hover{
/* Default color */
}
In your case , you can repair it by change the position of "hover"
a:not(.menu_item):hover {
background-color: #D6910E;
color: #FFE1A7;
} /*no change*/
a:not(#menu):hover { /*no change*/ }
a:not(#menu.menu_item) :hover { /*turns off hover on all links*/
a:not(#menu .menu_item):hover { /*turns off hover on all links*/
Hope it 'll help you

Related

Css selectors - a:visited childs [duplicate]

This question already has an answer here:
Why did browsers limit :visited selector?
(1 answer)
Closed 3 years ago.
I'm able to select child of a like so:
a > img {
/*change something*/
}
But I want first select a:visited, than its child. Something like:
a:visited > img {
/*change something*/
}
But the latter seems not working.
Example of HTML. Want change appearance of the image (adding border border: 2px solid; for example), if it is visited.
<!DOCTYPE html>
<body id="body-html">
<a href="https://stackoverflow.com/questions/56418220/css-selectors-avisited-childs?noredirect=1#comment99432271_56418220" class="test">
<img src="https://i.stack.imgur.com/nzzXb.png">
</a>
</body>
How can I achieve this?
Most CSS rules on :visited links have been blocked for security reasons.
However, you can still apply border-color to them.
The only gotcha here is that the border must be also applied on non-visited links, since you can only change the border-color.
a img {
border: 2px solid white;
}
a:visited img {
border-color: green;
}
fiddle
Though direct styling for :visited links is limited, there are lots of clever ways to extend your options for styling visited links. In 2015 there was a bumper crop of blog posts sharing new ideas for styling :visited links:
https://css-tricks.com/almanac/selectors/v/visited/

CSS :not selector behavior [duplicate]

This question already has answers here:
Is the CSS :not() selector supposed to work with distant descendants?
(2 answers)
Closed 6 years ago.
Using CSS, I'm trying to target all ul elements inside the #include element, except for the ones inside the #exclude element. Here's the markup:
<div id="include">
<ul><li>Include List</li></ul>
<div id="exclude">
<ul><li>Exclude List</li></ul>
</div>
</div>
I thought I could do this using the :not CSS selector like this:
#include :not(#exclude) ul {
color: blue !important;
}
The result I'm seeing is that neither ul gets the blue color. Clearly I am misunderstanding how this :not selector works. Is what I'm trying to do possible? Here's a fiddle:
https://jsfiddle.net/flyingL123/gmpLgx4y/
You need to use the > operator. This gets the immediate children of the element preceding. This will then get the ul immediately descending from #include. Updated:
JSFiddle
Updated code:
#include > ul {
color: blue !important;
}
You would not be able to to implicitly set styles by inheritance. They don't exclude ancestors because they don't trickle down. You will need to add new rules for other elements like so:
#include ul {
color: blue;
}
#exclude ul {
color: black;
}
Fiddle: Here

CSS selector: Style the first "a" inside a div

I am having trouble finding the correct CSS selector, the structure I have looks like this:
<div>
</div>
<div>
</div>
<div>
</div>
I would like to style the a element of the first div
I have tried with this selector but with no luck
div:first-child a{}
first-child should work absolutely well, you can try
div:nth-of-type(1) a { /* Or div:first-child a */
color: red;
}
The above selector will select all 1st div element and will apply color to all a which are inside 1st div
Demo
If you are willing to style 1st occurrence of a in every div tag than you need to use
div a:nth-of-type(1) { /* Or div a:first-child */
color: red;
}
Here every 1st a will be selected in every div tag
Last but not the least if you want to select 1st a only in 1st div than use the below selector
div:nth-of-type(1) a:nth-of-type(1) { /* Or div:first-child a:first-child */
color: red;
}
Note: If still the above selectors doesn't work, than the possibility
is either some rule is more specific than the rules you are declaring,
or !important is used somewhere, or (least chances) you are testing
on older browsers
Your own example is working too.
http://jsfiddle.net/7Pea3/
div:first-child a {
color: #f00;
}
The first div will be selected and all a recive the color #CCC. I don't understand why this isn't working.
div:first-child a {
color: #CCC;
}
Else test this solution, that selects the first div and styles the first a tag in the div:
div:first-child a:first-child(1) {
color: #CCC;
}
Else you have problems with the :first-child selector use the :nth-of-type({ number expression | odd | even }) selector.

Why CSS selectors on links are tricky with underline with hover?

Here are two examples based on this HTML.
<a href="#">
<div class="foo">
hello
<span class="bar">world</span>
</div>
</a>
In the first one, I make the link not underline on hover, then make a sub-portion of the link underline, and that works fine:
a {
text-decoration:none;
}
a:hover {
text-decoration: none;
}
a:hover .bar {
text-decoration: underline;
}
http://jsfiddle.net/3qPyX/1/
In the second, I now reverse the selectors so that the second word should be un-underlined. However, now something strange happens. The entire link remains underlined even though the selectors seem like they should remove underline from the second word. <-- (this is the question. why does this happen?)
a {
text-decoration:none;
}
a:hover {
text-decoration: underline;
}
a:hover .bar {
text-decoration: none;
}
http://jsfiddle.net/EAmwt/
Can someone explain what's going wrong in the second example? Inspecting with Chrome shows the span.bar has a computed style of text-decoration:none.
Update: a few answers explaining how to get around the problem, which is great except that's not really my question. What I want to know is why is this behavior different than, say, bold? For instance, if I try the 2nd example with bold, I get the expected results: http://jsfiddle.net/3qPyX/4/
Explanation:
The problem is that some properties (like text-decoration) get drawn to the whole parent inline element, whereas others - like font styling (that get inherited) - get overriden by the children properties.
Just for illustration: simmilarly, if you set a background color to a parent element it will paint the background of the parent ... and you would have to set another color to a child to lay it over (default - transparent - will still show the parent style through), but if you set font-weight at a child it will apply to the text inside the child element and override the parent settings.
You can find more detailed stuff on the text-decoration property in the CSS Level 2 and Level 3 Specifications.
A simple solution
withot changing the markup, you could just display .bar as inline-block.
Like so:
a {
text-decoration:none;
}
a:hover {
text-decoration: underline;
}
a:hover .bar {
display:inline-block;
}
And the inline-block breaks out of the inline/text styling of the parent anchor element =) And you can then style it independently:
DEMO
When you do the text-decoration it is applied to the entire line at once. So the a:hover .bar doesn't cause any effect, because the underline is not being applied in the .bar but on the a.
Here is the specification: http://www.w3.org/TR/CSS21/text.html#lining-striking-props
UPDATE! (As #Cam suggested) :
You need the add in separate elements the parts of your text: http://jsfiddle.net/3qPyX/5/
The CSS:
.foo, a:hover .bar, a {
text-decoration:none;
}
a:hover .foo {
text-decoration: underline;
}

Any way to stop CSS :hover text-decoration underline on child? [duplicate]

This question already has answers here:
Closed 12 years ago.
Possible Duplicate:
How do I get this CSS text-decoration issue to work?
I'm using the jquery toggle effect to show or hide more information about list elements:
jQuery(document).ready(function($) {
$("ul p").hide();
$("ul li").addClass("link");
$("ul li").click(function () {
$("p", this).toggle(300);
});
});
which works fine with a structure like:
<ul>
<li>List element 1<p>Additional info 1</p></li>
<li>List element 2<p>Additional info 2</p></li>
</ul>
In order to make it look 'clickable' I'm styling .link with css:
ul li.link {
color: #0066AA;
}
ul li.link:hover {
text-decoration: underline;
cursor: pointer;
}
But I don't want the text that's revealed to look like a link so:
ul li.link p{
color: black;
text-decoration: none;
}
ul li.link p:hover {
cursor: text;
text-decoration: none;
}
But the <p> is still underlined (in blue) on hover, despite throwing text-decoration:none; in every free space! From what I understand this is because the child styles are applied on top of the parent so what I'm effectively doing is trying to put 'nothing' on top of an underline and have it disappear.
So my question (eventually!) is this: Is there any way to get rid of that underline without taking the <p> out of the <li> (which I don't want to do for other reasons)?
Can you control the markup? I'd wrap the text inside the <li/> in a <span/> and write the CSS to target just the span with text-decoration:underline;.
Really though the clickable area should be an <a/> element with an href of "#". Bind a click handler to the anchor instead of the li. Then you have more pseudo-selectors like a:visited to work with and the behavior of clicking it is documented. I'm not sure if p:hover is actually supposed to work in CSS. I know it is possible to bind to any element with jQuery, but with CSS I'd stick with an anchor element.

Resources