After-Before pseudo in CSS3 for multiple classes - css

How to assign after & before pseudo classes to multiple CSS-classes
For example:
[class*="divclass-"]::before, ::after{
border-radius: 50%;
width: 30%;
height : 30%;
border: 3px solid red;
}

Consider this HTML structure, where you have a <div> which have children <span> and <p>. And another <span> and <p> as siblings.
<div>
<span>abc</span>
<p>xyz</p>
</div>
<span>123</span>
<p>456</p>
For example, if we need to change the colour of the children, we could write on your way,
div span, p{
color: red;
}
This problem with this is that, it will change the colour of the sibling <p>456</p> too as the style is applied globally to all the paragraph tags.
And the solution is to follow specificity as we did with the <span> and write the selectors as
div span,
div p{
color: red;
}
The same rule applies to pseudo-elements as well. Hence the solution is,
[class*="divclass-"]::before,
[class*="divclass-"]::after{
border-radius: 50%;
width: 30%;
height : 30%;
border: 3px solid red;
}
Note 1
If you are working on SASS, your syntax could be,
[class*="divclass-"]{
&::before,
&::after{
border-radius: 50%;
width: 30%;
height : 30%;
border: 3px solid red;
}
}
Note 2
The before and after pesudo-elements require the content property.
Hope this helps.

The comma does not mean that the following elements are children of the same selector (here [class*="divclass-"]).
It just allows you to chain the selectors.
#see https://www.thoughtco.com/comma-in-css-selectors-3467052
Here is the solution:
[class*="divclass-"]::before,
[class*="divclass-"]::after {
border-radius: 50%;
width: 30%;
height : 30%;
border: 3px solid red;
content: '';
}
<div class="divclass-1" style="height: 10px; width: 10px"></div>

Related

Can you combine CSS declarations?

You can combine CSS selectors by using a comma, such as in the following example:
.one, .two {
color: #F00;
}
<div class="one">One</div>
<div class="two">Two</div>
This has the same result as specifying the two selectors independently:
.one {
color: #F00;
}
.two {
color: #F00;
}
<div class="one">One</div>
<div class="two">Two</div>
Combining selectors as above is incredibly useful, as it means that you only have to worry about changing one value if you want to alter multiple elements. This comes in really handy for colour scheme changes.
But is it possible to combine CSS declarations?
For example, let's say I'm trying to vertically centralise text in an element, where line-height should always equal height:
.test {
border: 1px solid #000;
padding-left: 10px;
height: 100px;
line-height: 100px;
}
<div class="test">Test</div>
The expected combined declaration of height, line-height: 100px; doesn't apply either declaration, raising an invalid property value.
In SASS, it would be possible to make line-height dependent on height with something as simple as:
$height = 100px;
.test {
border: 1px solid #000;
padding-left: 10px;
height: $height;
line-height: $height;
}
Is there any way to specify that one property should utilise the same value from another property with raw CSS?
Sure you can:
:root {
--height: 100px;
}
.test {
border: 1px solid #000;
padding-left: 10px;
height: var(--height);
line-height: var(--height);
}
<div class="test">Test</div>
But not all browsers support CSS variables - http://caniuse.com/#feat=css-variables

:not() selector on CSS

I have a problem with the :not() selector on CSS.
I have this code:
<div class="group">
<div role="layer" class="one">Layer</div>
<div role="layer" class="two">Layer</div>
<div role="layer" class="three">Layer</div>
<div role="layer" class="four">Layer</div>
</div>
and this CSS:
div[role="layer"]{
width: 100px;
height: 25px;
border: 1px solid red;
border-radius: 5px;
float: left;
}
.group > [role="layer"]:first-child{
border-top-right-radius: 0;
border-bottom-right-radius: 0;
}
.group > [role="layer"]:last-child{
border-top-left-radius: 0;
border-bottom-left-radius: 0;
}
.group [role="layer"]:not(:first-child){
border-radius: 0;
}
JSFiddle Example
What I want to do is to make the first and last layer to have rounded corners but not the other layer. As you can see I can make the first layer not to have a border radius, but when the :not(:first-child) selector is applied, it makes the last layer to change.
If someone can understand my point, I'd really appreciate your help.
What you want to do is say "layers that are neither the first child nor the last child should have border-radius: 0". You can achieve this by having multiple :not() selectors:
.group [role="layer"]:not(:first-child):not(:last-child){
border-radius: 0;
}
Updated jsFiddle
I think you need 2 changes here:
Move the last CSS declaration (the one with :not) up above the :last-child declaration (in CSS order matters)
Replace
.group > [role="layer"]:last-child {
border-top-left-radius: 0;
border-bottom-left-radius: 0;
}
with
.group > [role="layer"]:last-child {
border-top-right-radius: 5px;
border-bottom-right-radius: 5px;
}

Preventing Hover event of a Div triggering on parent Div?

When I mouseover .mensal DIV it will trigger the mouseover the parent .opera DIV, which seems wrong to me. I just want the "highlight" effect to to work on the child .opera DIV.
#operaContent {
padding: 0 50px 0 50px;
position: relative;
overflow: visible;
}
#operaContent .opera {
display: block;
border: 1px solid #FFFFFF;
border-bottom: 1px solid #DDDDDD;
padding: 5px;
margin-bottom: 10px;
height: 120px;
background-color: #0A8ECC;
}
#operaContent .opera:hover {
border: 1px solid #AAAAAA;
background-color: #DDDDDD;
cursor: pointer;
}
.mensal {
position: absolute;
top: 1px;
left: 8px;
z-index: 3;
display: block;
}
<div id="operaContent">
<div class="opera">
<div class="mensal">
DIV
</div>
</div>
</div>
By definition, hovering over a child, hovers over the parent as well. There is no "blocking" in html events.
There are two method chains, the bubble and the capture.
Any event taking place in the W3C event model is first captured until
it reaches the target element and then bubbles up again.
http://www.quirksmode.org/js/events_order.html
The only way you're going to stop this is to prevent the bubbling by adding javascript to your page to prevent the chain. This is simple in jQuery
$('.mensal').hover(function(e){
e.stopPropagation();
});
It occurs to me that this answer is completely unhelpful when dealing with CSS. Javascript events dont deal with CSS selectors or preventing them.
Unfortunately, with CSS alone, I do not know of a way to accomplish this (and even in javascript it can get tricky). CSS 4 selectors will allow you to specify the subject of the selector http://dev.w3.org/csswg/selectors4/#subject so that you can do something like
#operaContent .opera:hover! .mensal:not(:hover) { /*your css*/ }
but this isnt implemented yet, and is still under development for the draft.
EDIT:
Here is a javascript (jQuery) implementation that should work for you
​
$(function(){
$('.opera').hover(function() {$(this).addClass('hoverIntent')},
function(){ $(this).removeClass('hoverIntent'); }
);
$('.opera .mensal').hover(function() {
$(this).parent('.opera').removeClass('hoverIntent');
});
})​
and the modified CSS
#operaContent {
padding: 0 50px 0 50px;
position: relative;
overflow: visible;
}
#operaContent .opera {
display: block;
border: 1px solid #FFFFFF;
border-bottom: 1px solid #DDDDDD;
padding: 5px;
margin-bottom: 10px;
height: 120px;
background-color: #0A8ECC;
}
#operaContent .opera.hoverIntent {
border: 1px solid #AAAAAA;
background-color: #DDDDDD;
cursor: pointer;
}
.mensal {
position: absolute;
top: 1px;
left: 8px;
z-index: 3;
display: block;
}​
and the obligitory working demo: http://jsfiddle.net/WB6Ty/

Can't figure out why CSS work like this

How come the #r3 isn't pink? (see jsfiddle.net/aAqKf/):
<!DOCTYPE HTML>
<html>
<head>
<style>
#r1 { width: 100px; height: 100px; border: solid 1px red; }
#r2 { width: 50px; height: 50px; border: solid 1px green; }
#r3 { width: 25px; height: 25px; border: solid 1px blue; }
.pink div {
background: pink;
}
.red div {
background: red;
}
</style>
</head>
<body>
<div id="r1" class="red">
<div id="r2" class="pink">
<div id="r3"></div>
</div>
</div>
</body>
</html>
I would expect the pink class to apply the pink background to the div children. It doesn't work like that. Why?
Though, it works if I change the CSS as follows (jsfiddle.net/aAqKf/1/):
<style>
#r1 { width: 100px; height: 100px; border: solid 1px red; }
#r2 { width: 50px; height: 50px; border: solid 1px green; }
#r3 { width: 25px; height: 25px; border: solid 1px blue; }
.red div {
background: red;
}
.pink div {
background: pink;
}
</style>
Please help me figure out how come it works that way. Also, please do not suggest that I use !important along with the background: pink declaration because it will work only until I change the HTML as follows:
<div id="r1" class="pink">
<div id="r2" class="red">
<div id="r3"></div>
</div>
</div>
NB: I am more interested in figuring out why it works that way than finding out how to make it work my way.
Both rules .pink div and .red div are equally specific. The latter rule overrides the former.
You almost never have to use !important, by the way. Using the selector body .pink div, or div.pink div is enough to give the selector more weight.
From this page
To make it easy, when two rules have the same weight, the last rule specified wins.
In your first fiddle, the red wins. In the second the pink wins.
Because the properties of class inheritance differ from that of the actual element.
For example, if you changed
.pink div { background: pink; }
to:
#r2 div { background: pink; }
it would work as you intended it, because the nested block level elements inherit based on their closest parent.
Classes, on the other hand, have much looser inheritance and properties get overwritten based on the parents, unless specifically said otherwise using !important, when two selectors have the same weight.
To further demonstrate this point, changing .pink div to div.pink div would also demonstrate the correct effect because, again, CSS is referring to an element and not a class selector.

How to remove the bottom border of a box with CSS

I have a rectangular div, like the one above. I want to remove the bottom border (from C to D) in my div. How can I do this?.
Edit: Here is my CSS:
#index-03 {
position: absolute;
border: .1px solid #900;
border-width: .1px;
border-style: solid;
border-color: #900;
left: 0px;
top: 102px;
width: 900px;
height: 27px;
}
<div id="index-03"
style="background-color:limegreen; width:300px; height:75px;">
</div>
Just add in: border-bottom: none;
#index-03 {
position:absolute;
border: .1px solid #900;
border-bottom: none;
left:0px;
top:102px;
width:900px;
height:27px;
}
You can either set
border-bottom: none;
or
border-bottom: 0;
One sets the border-style to none.
One sets the border-width to 0px.
div {
border: 3px solid #900;
background-color: limegreen;
width: 28vw;
height: 10vw;
margin: 1vw;
text-align: center;
float: left;
}
.stylenone {
border-bottom: none;
}
.widthzero {
border-bottom: 0;
}
<div>
(full border)
</div>
<div class="stylenone">
(style)<br><br>
border-bottom: none;
</div>
<div class="widthzero">
(width)<br><br>
border-bottom: 0;
</div>
Side Note:
If you ever have to track down why a border is not showing when you expect it to,
It is also good to know that either of these could be the culprit.
Also verify the border-color is not the same as the background-color.
You seem to misunderstand the box model - in CSS you provide points for the top and left and then width and height - these are all that are needed for a box to be placed with exact measurements.
The width property is what your C-D is, but it is also what A-B is. If you omit it, the div will not have a defined width and the width will be defined by its contents.
Update (following the comments on the question:
Add a border-bottom-style: none; to your CSS to remove this style from the bottom only.
You could just set the width to auto. Then the width of the div will equal 0 if it has no content.
width:auto;

Resources