Select child css without a specific element - html

I want to apply css style in all mat-tab-group element without impacting the style of app-form element
<div class="area">
<childhere></childhere>
<mat-tab-group>
<mat-tab *ngFor="..." [label]="label">
<form [formGroup]="formGroup">
<div class="inside-tab">
<mat-form-field>...</mat-form-field>
<mat-form-field>...</mat-form-field>
<mat-form-field>...</mat-form-field>
<mat-form-field>...</mat-form-field>
</div>
<app-form></app-form>
</form>
</mat-tab>
</mat-tab-group>
</div>
I've try using :not property but it's not working
mat-tab-group > mat-tab > form :not(:last-child){
background-color: #009926; //to test
}
Any suggestions?

mat-tab-group > mat-tab > form {
background-color: #009926; //to test
}
mat-tab-group > mat-tab > form:last-child {
background-color: unset;
}
This way, last child background will fallback to default.
stackblitz example
Snippet:
div > div > * {
background-color: blue;
color: white
}
div > div > *:last-child {
background-color: green;
}
<div>
<div>
<p>first</p>
<p>secont</p>
<p>last</p>
</div>
</div>

Related

css - set different styles to other nodes where the class applies

I've been trying to set different styles to the same class (when it appears for the second time in the markup) using the Subsequent-sibling combinator "~" but it seems it didn't work , maybe I'm omitting a detail with the use of "~" , also... Unfortunately I cannot change the html because it is generated by a cms
<div class="root">
<div class="container">
<div class="mosaic big">
<div>Red</div>
</div>
</div>
<div class="container">
<div class="mosaic medium">
<div>3</div>
</div>
</div>
<div class="container">
<div class="mosaic big">
<div>Blue</div>
</div>
</div>
<div class="container">
<div class="mosaic medium">
<div>4</div>
</div>
</div>
</div>
and this is the css
.root > .container > .mosaic.big {
color: red
}
.root > .container > .mosaic.big ~ .root > .container > .mosaic.big {
color: blue
}
also... here's a jsfiddle https://jsfiddle.net/chinoche/wd1rhg11/
Thanks in advance
Try this styling.
.root > .container > .mosaic.big {
color: red
}
.root > .container:nth-child(3) > .mosaic.big {
color: blue
}
OR
.root > .container > .mosaic.big {
color: red
}
.root > .container:nth-child(n+2) > .mosaic.big {
color: blue
}
From what ather answers suggested, i assumed this is what you want (you can comment if it doesn't fit edge cases):
So as i said, ~ only works with elements that have the same parent.
Note: it doesn't make it blue because it's the second .mosaic.big in a container, but because the container itself is not the first. To have a fully working solution without experimental features, you should need JS
CSS:
.root > .container > .mosaic.big {
color: red
}
.root > .container ~ .container > .mosaic.big {
color: blue
}
https://jsfiddle.net/wd1rhg11/5/
Sadly without changing the html you will not be able to use the subsequent sibling selector
The CSS next sibling selector will only match the immediate siblings of the class to the left of the operator. So for this to work the elements you use with this operator must have the same parent.
In addition the matching on the right hand side will begin at the element matched on the left hand side therefore you dont need to add the parent structure
.root > .container > .mosaic.big {
color: red
}
.root > .container > .mosaic.big ~ .mosaic.big {
color: blue
}
See updated
https://jsfiddle.net/wd1rhg11/4/
You may be able to acheive what you are trying to with javascript if possible
You can use nth-child(n) of '.mosaic' class:
.root > .container > .mosaic:nth-child(1).big {
color: red;
}
.root > .container > .mosaic:nth-child(3).big {
color: blue;
}
here`s jsfiddle
https://jsfiddle.net/andrewsilent/w8jjjsbz/

CSS - Only select the first descendant

I'm trying to style all my main tags based on a certain theme.
If a section's class is red, all of of it's inner tags should use the red style regardless of if that section is inside another section which uses the yellow style.
So my question is how do I restrict the inner tags of a section/div/nav etc, to only use the style of the first descendant it encounters.
Note: I do not want to rely on the order of which I declare my tags.
.red input {
background-color: red;
}
.red article {
background-color: red;
}
.red p {
background-color: red;
}
/*.. other tags.. */
.yellow input {
background-color: yellow;
}
.yellow article {
background-color: yellow;
}
.yellow p {
background-color: yellow;
}
/*.. other tags.. */
.blue input {
background-color: blue;
}
.blue article {
background-color: blue;
}
.blue p {
background-color: blue;
}
/*.. other tags.. */
<section class="yellow">
<section class="blue">
<form>
<input type="button" value="This should use the blue theme" />
</form>
</section>
<section class="red">
<article>
<p>This should use the red theme</p>
<!-- This is instead yellow, how do I fix that? -->
</article>
</section>
<section class="yellow">
<nav>
<p>This should use the yellow theme</p>
</nav>
</section>
<p>This should be yellow.</p>
</section>
UPDATE
Okay so I've tried the given solutions and they work with the given example but as soon as I expand the html code to something more complex it doesn't work anymore.
The thing is that since I have to build a general theme, I cannot use css rules that depend on the order of how the html is built. A user should be able to build its website and regardless of how the html is built the correct styles should be applied.
So if the user gives a container tag (nav, section, div, aside, etc.) the class dark-theme, yellow-theme or whatever other theme, all of its children should use that style UNLESS a child container has also specified its own theme.
Is it just not possible? :(
Ex:
section class=yellow-theme
p: use yellow-theme
aside: use yellow-theme
div class=red-theme
ul: use red-theme *not yellow
p: use red-theme *not yellow
footer class=blue-theme
a: use blue-theme *not red not yellow
h3: use blue-theme *not red not yellow
div class=yellow-theme
header: use yellow-theme *not blue * not red
form: user yellow-theme *not blue *not red
<!--This could go on forever and in any order with any tags-->
css:
.yellow-theme anytag{
/* Style any attributes needed: borders, colors, fonts, margins, paddings, etc. */
}
/* Do this for all the tags that needs to be styled */
.red-theme anytag{
/* Style any attributes needed: borders, colors, fonts, margins, paddings, etc. */
}
/* Do this for all the tags that needs to be styled */
.blue-theme anytag{
/* Style any attributes needed: borders, colors, fonts, margins, paddings, etc. */
}
/* Do this for all the tags that needs to be styled */
Any selector-only solution requires you to make assumptions about your markup that may or may not be within your control since the specificity of two contextual selectors is always the same regardless of how close the ancestor is to each descendant that is matched, and any solution that makes use of inheriting the actual properties themselves requires you to apply them to the .red, .yellow and .blue sections, which may not be desired. For example, you'd have to apply background-color to the sections in order for background-color: inherit to work on the descendants, but you may not want the sections themselves to have any background color, so that won't be an option to you.
Custom properties allow descendants to inherit values from their closest ancestors without polluting other properties in this manner, and without other cascading rules getting in the way (competing rules with equally specific contextual selectors, etc). You'll only be able to do this reliably with custom properties for this reason.
.red {
--color: red;
}
.yellow {
--color: yellow;
}
.blue {
--color: blue;
}
input, article, p {
background-color: var(--color);
}
<section class="yellow">
<section class="blue">
<form>
<input type="button" value="This should use the blue theme" />
</form>
</section>
<section class="red">
<article>
<p>This should use the red theme</p>
</article>
</section>
<section class="yellow">
<nav>
<p>This should use the yellow theme</p>
</nav>
</section>
<p>This should be yellow.</p>
</section>
This porblem is a little bit difficult if you want to solve it with all elements.
You have to think the other way: NOT "a rule is valid until there is another rule" BUT "the closest rule is valid".
How to achieve this?
First set a rule for all elements that are grandchildren except the form tag (perhaps also the ol, ul, nav, ... tags) that the background-color shell inherit. Now all this elements inherit theire background-color from the parent element.
Second set one rule for each theme that defines the background-color of all direct children. Here you have to take a look at the problem with the form tag. the form tag has no inheritage (see above) so the children of the form will not get the rule from the closest theme parent. So you have to setup an extra rule for this case.
All in all:
*.color * > *:not(form):not(html):not(body) {
background-color:inherit!important;
}
.red > *:not(form):not(.color), .red > form > *:not(.color) {background-color: red!important}
.yellow > *:not(form):not(.color), .yellow > form > *:not(.color) {background-color: yellow!important}
.blue > *:not(form):not(.color), .blue > form > *:not(.color) {background-color: blue!important}
(.color is a css class that all sections have, that also have the css class .red or .yellow or .blue)
the > - signs are important
you can mix up all the rules.
EDIT Now I see that !important is not neccessary :)
You can also write
*.color * > *:not(form):not(html):not(body) {
background-color:inherit;
}
.blue > *:not(form):not(.color), .blue > form > *:not(.color) {background-color: blue}
.red > *:not(form):not(.color), .red > form > *:not(.color) {background-color: red}
.yellow > *:not(form):not(.color), .yellow > form > *:not(.color) {background-color: yellow}
EDIT2 if you want to style a specific tag in a theme, you have to add the rules in the following way.
1) Add all css attributes that you want to style to the first rule of the set:
*.color * > *:not(form):not(html):not(body) {
background-color:inherit;
color:inherit;
}
2) replace the asterisk by the tag name
.blue > *:not(form):not(.color), .blue > form *:not(.color) {background-color: blue}
.red > *:not(form):not(.color), .red > form *:not(.color) {background-color: red}
.yellow > *:not(form):not(.color), .yellow > form *:not(.color) {background-color: yellow}
.blue > input:not(form):not(.color), .blue > form input:not(.color) { color:white; }
.red > input:not(form):not(.color), .red > form input:not(.color) { color: green; }
.yellow > input:not(form):not(.color), .yellow > form input:not(.color) { color: purple; }
3) have a look at the > - signs! I removed it at one position to make it work with all tags.
To target only the direct descendant of an element, you can use the direct descendant operator: >:
.red > input {
background-color: red;
}
And to go one step better, you can replace all repetitions like so, instead of having to manually declare each element:
.red > * {
background-color: red;
}
.yellow > * {
background-color: yellow;
}
.blue > * {
background-color: blue;
}
Try This :
.yellow > *:not(form):not(section), .yellow form * {background-color: yellow !important}
.blue > *:not(form):not(section), .blue form * {background-color: blue !important}
.red > *:not(form):not(section), .red form * {background-color: red !important}
.yellow > *:not(form):not(section), .yellow form * {background-color: yellow !important}
.blue > *:not(form):not(section), .blue form * {background-color: blue !important}
.red > *:not(form):not(section), .red form * {background-color: red !important}
<section class="yellow">
<section class="blue">
<form>
<input type="button" value="This should use the blue theme" />
</form>
</section>
<section class="red">
<article>
<p>This should use the red theme</p>
<!-- This is instead yellow, how do I fix that? -->
</article>
</section>
<section class="yellow">
<nav>
<p>This should use the yellow theme</p>
</nav>
</section>
<p>This should be yellow.</p>
</section>
Not sure if I understand your question, so just comment if I'm wrong.
Increase the specificity of the style so that will not be overridden that easily.
.red > article > p {
background-color: red;
}
.red input {
background-color: red;
}
.red article {
background-color: red;
}
.red > article > p {
background-color: red;
}
/*.. other tags.. */
.yellow input {
background-color: yellow;
}
.yellow article {
background-color: yellow;
}
.yellow p {
background-color: yellow;
}
/*.. other tags.. */
.blue input {
background-color: blue;
}
.blue article {
background-color: blue;
}
.blue p {
background-color: blue;
}
/*.. other tags.. */
<section class="yellow">
<section class="blue">
<form>
<input type="button" value="This should use the blue theme" />
</form>
</section>
<section class="red">
<article>
<p>This should use the red theme</p>
<!-- This is instead yellow, how do I fix that? -->
</article>
</section>
<section class="yellow">
<nav>
<p>This should use the yellow theme</p>
</nav>
</section>
<p>This should be yellow.</p>
</section>
I tried this and it works, regardless of what element is it as long as you define the parent, hope this helps
body > :first-child
{
background-color: #ff0000;
}

How can I color text in <p> that it contains in a <div>

How to color a text in a <p> that it contains in a <div> when the user hovers with the mouse.
Suppose I have this html code:
<div id="riga_ristorante_1" >
<div>
<p>HI</p>
</div>
<div><p>HOME</p></div>
<div><p>DOG</p></div>
</div>
I want color the "hi","HOME","DOG" in black when the user go on the <p> element, so I use CSS:
#riga_ristorante_1:hover > p {
text-align: center;
color: black;
}
But it doesn't work. Anyone can help me?
You are using a child combinator (a greater than sign: >), but the div with the id your selector matches is the grandparent of the paragraphs, not the parent.
Use a descendant combinator (a space: ) instead.
You are targeting the paragraph directly after your ID div which in your html you don't have a paragraph tag that is a immediate child of your riga_ristorante_1
for more info on > selector
https://developer.mozilla.org/en/docs/Web/CSS/Child_selectors
With your given html you can do
#riga_ristorante_1:hover p { ... }
or
#riga_ristorante_1:hover div > p { ... }
or
#riga_ristorante_1 div:hover > p { ... }
or even
#riga_ristorante_1 p:hover { ... }
css selector will be riga_ristorante_1:hover > div > p {}
#riga_ristorante_1:hover > div > p {
text-align: center;
color: blue;
}
<div id="riga_ristorante_1" >
<div>
<p>HI</p>
</div>
<div><p>HOME</p></div>
<div><p>DOG</p></div>
</div>
You have your p as second level in deep, so you can't use > as it applies to first level only. Use
#riga_ristorante_1:hover p {
color: red;
}
#riga_ristorante_1:hover p {
color: red;
}
<div id="riga_ristorante_1" >
<div>
<p>HI</p>
</div>
<div><p>HOME</p></div>
<div><p>DOG</p></div>
</div>
Try with #riga_ristorante_1 p:hover just give toggle effect
#riga_ristorante_1 p:hover {
text-align: center;
color: blue;
}
<div id="riga_ristorante_1" >
<div>
<p>HI</p>
</div>
<div><p>HOME</p></div>
<div><p>DOG</p></div>
</div>
Leave the HTML Code but change your css selector to #riga_ristorante_1 div > p:hover then set your preferred styles
HTML Code
<div id="riga_ristorante_1" >
<div><p>HI</p></div>
<div><p>HOME</p></div>
<div><p>DOG</p></div>
</div>
The css selector should be #riga_ristorante_1 div > p:hover so the css will look like below and add more styles if you like like the text-align in the original css code.
CSS Code
#riga_ristorante_1 div > p:hover {
color: blue;
}

id:hover id in css ? is it possible?

Here is my html code
<div id="id_1"></div>
<div id="id_2"></div>
<div id="id_3"></div>
<div id="id_4"></div>
And here is my css code
<style>
#id_1:hover #id_2{background-color:red;}
#id_1:hover #id_3{background-color:red;}
#id_1:hover #id_4{background-color:red;}
#id_2:hover #id_4{background-color:red;}
</style>
This hover is why not working ? Someone help me ?
I need when i hover #id_1, will change backgroundcolor #id_2
Because those divs are siblings so you need to use general sibling selector or ~
#id_1:hover ~ div
This will match all sibling elements of #id_1 with type of div, and you can use that instead of writing separate selector for each div
#id_2:hover ~ #id_4
This will match only sibling element of id_2 that has #id_4, if you only want to match div you can add div#id_4
#id_1:hover ~ div {
background-color: red;
}
#id_2:hover ~ #id_4 {
background-color: red;
}
<div id="id_1">div</div>
<div id="id_2">div</div>
<div id="id_3">div</div>
<div id="id_4">div</div>
If you just want to change color of next sibling element when you hover over #id_1 you can use adjacent sibling selector or +
#id_1:hover + div {
background-color: red;
}
<div id="id_1">div</div>
<div id="id_2">div</div>
<div id="id_3">div</div>
<div id="id_4">div</div>
You can use CSS attribute selector. More specifically, [attr^=value] which
Represents elements with an attribute name of attr whose value is
prefixed (preceded) by value.
and in your case it would be div[id^='id_']:hover.
As an example adapted from Andrzej GorgoĊ„
div {
background: red;
width: 50px;
height: 100px;
float: left;
margin-right: 5px;
}
div[id^='id_']:hover {
background: blue;
}
<div id="id_1"></div>
<div id="id_2"></div>
<div id="id_3"></div>
<div id="id_4"></div>
This selector:
element1 element2
Works when element2 is child of element1
Your css is true when the #id_2 is a child of #id_1
You can change your code to this:
#id_1:hover + div{background-color: red;}

css to hide the near div when this div is clicked (working for hover)

My code :
<div>
<div class='top-class'>
Header Name
</div>
<div class='body-class'>
This is body a
</div>
</div>
<div>
<div class='top-class'>
Another Header Name
</div>
<div class='body-class'>
Another body
</div>
</div>
css code I tried:
.top-class:hover + .body-class { display: block; } /* This is working */
But, I want that to happen when header is clicked. So, i tried this:
.top-class:visited + .body-class { display: block; } /* DIDNT work */
The pseudo class "active" seems to do the job
.top-class:active + .body-class { display: block; background-color: red; }
You can check my jsfiddle
You can use tabindex in you first div then it can have focus event on.
<div class='top-class' tabindex=1>Header Name</div>
Then in css you test focus pseudo class
.top-class:focus + .body-class { display: block; background-color: red; }
Check this jsfiddle