CSS3 :not() selector not working on sibling element - html

I have a simple layout where I want the text red if it is not in the footer element. It works with p tags, a tags etc.
But when I try it with footer tag it doesn't work.
My code is below:
p {
color: #000000;
}
:not(footer) {
color: #ff0000;
}
<h1>This is a heading</h1>
<footer>This is a footer.</footer>
<div>This is some text in a div element.</div>
Link to W3Schools!

You need to select the parent which is body (otherwise footer will inherit red from body as per your rule stated), in order for :not(footer) to work.
Regards to p its a matter of CSS specificity
p {
color: #000;
}
body > *:not(footer) { /* note that having :not(footer) is the same as *:not(footer), the wildcard is not necessary */
color: #f00;
}
<h1>This is a heading</h1>
<footer>This is a footer.</footer>
<div>This is some text in a div element.</div>
<p>This is some text in a p element.</p>
Link to W3Schools!

you need a parent element to nested for :not() selector to work so here in your code body tag'll work as parent element
body > :not(footer){
color: #ff0000;
}

This is your code:
:not(footer) {
color: #ff0000;
}
That sets all elements to red, except the footer.
The problem is that the rule sets the body element to red. Then the footer inherits the color.
So your rule actually works (the sibling is excluded), but the footer gets the color nonetheless through inheritance.
Instead or targeting all siblings (except footer), target all children (except footer). This eliminates the inheritance loophole:
body > :not(footer) {
color: #ff0000;
}
<h1>This is a heading</h1>
<footer>This is a footer.</footer>
<div>This is some text in a div element.</div>
Link to W3Schools!

Related

Why does the background turn black but the text remains purple (HTML CSS)?

For some reason, a black background shows up out of nowhere on the p tags under the div when you put the CSS selector to #div1. If I fix it and change the selector from #div1 to #div1 > h4 like my little tutorial text was explaining, it fixes itself. Why is that? I just need to know if it's a glitch or not. Thanks!
Please advise. Thanks.
body {
}
h2 {
color: red;
}
p {
color: pink;
}
p {
color: green;
}
p {
color: purple;
}
.orange > p {
color:orange;
}
.blue {
color: blue;
}
#red {
color: red;
}
#div1 > h4 {
background-color: black;
color: white;
}
<!DOCTYPE html>
<html>
<head>
<title>CSS Basics</title>
<link rel="stylesheet" type="text/css" href="basics.css">
</head>
<body>
<p>This is the color purple not pink or green because CSS always takes the selector that is last in the cascade.</p>
<div class="orange">
<h1>This will not be orange</h1>
<p>This will be orange because our selector in CSS for the class="orange" is like this: .orange > p making the h1 unchanged even though it is under the same class="orange" and the p will be the only one that changes to orange text!</p>
</div>
<p class="blue">This will be blue.</p>
<p class="blue">This will also be blue, because you can use classes more than once unlike ID's.</p>
<p id="red">This is an ID stating it is red.</p>
<p id="red">This is using the same ID to say it is red, and as you can see it still works. But, be warned, using the same ID to multiple elements is invalid HTML and should be avoided!</p>
<div id="div1">
<p>This paragraph is wrapped in a div with the id of "div1" which gives a black background and white text.</p>
<p>This paragraph is also wrapped in the div with the id of "div1". Notice that neither this paragraph or the paragraph before this one has white text or a black background. This is because we didn't specify in the selector to give p tags white text by using a > symbol between #div1 and p. In fact, it remained purple since that is the last thing applicable that the cascade found to work.</p>
<h4>This h4 text on the other hand (which is also inside of the div as the other two paragraphs above it) works because we specified it to be #div1 > h4 for its selector. (side note: the two paragraphs above this h4 element do in fact get a black background until we write in #div > h4. I do not know why the text remains purple but the background changed to black...It fixed itself to not having a black background after we wrote in the code "#div1 > h4" so idk what to make of it...)
</h4>
</div>
</body>
</html>
#div1 is the parent of the p elements. This means that some properties (such as background) of #div1 will be applied to the child element(s). However, when you add the > h4 it is specifying that those properties should only apply to the h4 child element of #div1 element. So no, it is not a glitch but is intended CSS behavior.
To note, you have 3 distinct p {} statements, each with a different color...only the final one will be used (because they all have the same specificity) and you can delete the top two.
If I'm understanding your question correctly, the reason the black background only applies to the h4 element once you add the angled bracket is because the angled bracket is a CSS child selector.
In this instance, #div1 > h4 applies styling to all h4 that are children of the #div1 div, whereas #div1 itself applies styling to everything contained in the div (including p)
I hope this answers your question my friend.
#div1 is the part element that your p tags contain. since that p tags are inside the div, the back ground color will be black. because it applies its styles to all the child elements.
when you give #div1 > h4 ; this styles only affects on h4 tag since it only applies to #div1 's child h4 elements.

CSS :not selector being ignored

So I have a div with class='content' and inside that, another div with attribute style='background-color:#FF0000' so my code looks like the following:
<div class='content'>
Here is some text outside the red background div
<div style='background-color:#FF0000'>
Here is some text inside the red background div
</div>
</div>
And in my stylesheet I have the following:
[style^='background'] {
color:#00FF00
}
This works and I get green text inside the red background. However:
:not([style^='background']) {
color:#00FF00
}
This still makes the red background text green, along with everything else in the document. I have tried the following:
div:not([style^='background']) {
color:#00FF00
}
.content :not([style^='background']) {
color:#00FF00
}
:not([style]) {
color:#00FF00
}
Yet all of these make the red-background text green, when clearly I have the :not selector.
However, I have elsewhere:
.content div:not([style^='text-align']) {
color:#1f1f1f;
}
.content div :not(span[style^='font-size: 150%']) {
color:#EEE;
}
And these work just fine.
So I don't understand why the red background div won't work at all and is selected by the :not selector?
Example:
:not(.content) {
color:#FF0000
}
<div class='content'>
Here is some text that shouldn't be red
</div>
color is an inherited property. So if your element has no color set, it inherits the color from the next ancestor element that has a color defined. In your example,
:not(.content) { color: #F00; }
this also targets the body element, so your div.content inherits color: #F00;.
To avoid this, specify inherited properties on the elements you don't want inheritance on.
.content { color: green; }
:not(.content) {
color: red;
}
<div class="content">
Here is some text that shouldn't be red
</div>
Quirks, tricks, and unexpected results of :not
:not(.foo) will match anything that isn't .foo, including <html> and <body>.
You need to increase specificity to avoid this, e.g. div:not(.content).
In addition:
div:not([style^='background']) {
/* also targets parent divs */
color: #00FF00;
}
.content :not([style^='background']) {
/* You have a space here - this targets _children_ of .content
that are :not([style^='background']. Is this what you want? */
color: #00FF00;
}
Remember that the "C" in "CSS" stands for cascading, and one aspect of that is inherited styles. Many styles (such as color) affect children of matched elements too, not just the element itself.

:not() pseudo selector works incorrect with some tags

HTML:
<p>I`m p</p>
<a>I`m a</a>
<h2>I`m h2</h2>
CSS:
:not(p){
color:red;}
:not() pseudo class should select all the elements inside the HTML document, that aren`t "p", and give them red color, but when i run the code "p" is red too, just like all other elements.
here you need to specify color for all html elements. as there is no color set to elements, the color from your selector is getting set to all elements available.
Here is what you need to add in your style:
*{
color: black;/* the color you will want for all or p elements. */
}
Notorious Zet you can fix this error by giving the p element a class and then using the not pseudo selector
The HTML
<p class = "notRed"> This is a p element </p>
<h1>This is a h1 element</h1>
The CSS
p:not(notRed){
color: red /*This will apply to all p elements with the class of notRed*/
}
Need to specify the color of <p> tag first. See the example from w3schools.
p {
color: black;
}
:not(p) {
color: red;
}
<p> I am p </p>
I am a
<h1> I am h1 </h1>

In CSS, does a space between a html tag and a class name mean the style is applied to any element within that tag?

On this answer: https://stackoverflow.com/a/1725486/2519402 to a question, it states:
It sounds like you had h1 .myClass instead of h1.myClass - there's an
important distinction:
h1 .myClass { } /* any element with class="myClass" within an <h1> */
h1.myClass { } /* any <h1> with class="myClass" */
I don't have enough points to ask my question as a comment on that answer.
So, based on what is said above, shouldn't the following code work:
<style>
h3 .h3nobtmgn {
margin-bottom:-20px;
}
</style>
<h3><strong class="h3nobtmgn">Why would I need or want this item?</strong></h3>
Yes, but vertical margin styles won't work on an inline element like <strong>. http://www.w3.org/TR/CSS21/box.html#propdef-margin-top
So your CSS selector will target the correct element but the style you applied will have no effect.
For that to work you can try:
<style>
h3 .h3nobtmgn {
display: block;
margin-bottom:-20px;
}
</style>
<h3><strong class="h3nobtmgn">Why would I need or want this item?</strong></h3>
Yes it does.
h1.myClass would change the appearance of
<h1 class="myClass">...</h1>
And h1 .myClass would change the appearance of
<h1> ... <span class="myClass">...</span></h1>
You will see through http://www.w3schools.com/cssref/trysel.asp that when you are doing div p it will select all p inside of div. So, the answer is yes.
here is a sample: https://jsfiddle.net/r5d0kkb5/
which shows selectors for div p and div .B and also div .A for your thoughts.
Code:
<div class="A">
<p >
A
</p>
<p class="B">
B
</p>
</div>
Css:
div p {
background-color: cyan;
}
div .B{
font-size: 32px;
}
div .A{
color: red;
}

How to prevent child element from inheriting CSS styles

I have a <div> element with a <p> element inside:
<div style="font-size:10pt; color:red;">
This is my Parent Div.
<p>This is my Child Paragraph.</p>
My parent Div Ends Here.
</div>
How can I prevent my paragraph from inheriting the CSS properties set to the <div>?
In your case the best way is to just over right the styles that the <p> element is inheriting:
So in your CSS file, which you should be using instead of inline styles:
.parent-div {
font-size: 10pt;
color: red;
}
.child-paragraph {
font-size: 12pt;
color: black;
}
In your child node -
<p style="font-size:12pt; color:black;">This is my child</p>
Just set the inline style to whatever you want.
You can use the > selector in CSS to select the immediate child p of div.
Fiddle link
div > p {
font-size:1.2 em;
color: green;
}