Add an absolute selector in a nested style - css

I am trying to figure out the best way to accomplish reusing some of the nested styles in Less to prevent duplication, but I am not sure if I have found the best way.
Right now I have something like:
.category-link,
.caption-link {
background-color: #linkColour;
font-family: #linkFont;
max-width:2em;
a {
/* INNER LINK STYLES */
text-decoration:none;
white-space:nowrap;
/* ...INNER LINK STYLES CONTINUE... */
}
}
Now I want to apply those same inner link styles to the selector .action-link a without applying the outer styles to .action-link.
I get my intended output if I do it this way:
.inner-link-styles() {
/* INNER LINK STYLES */
text-decoration:none;
white-space:nowrap;
/* ...INNER LINK STYLES CONTINUE... */
}
.category-link,
.caption-link {
background-color: #linkColour;
font-family: #linkFont;
max-width:2em;
a {
.inner-link-styles;
}
}
.action-link a {
.inner-link-styles;
}
which doesn't require any duplication, but I'd prefer to keep those styles in their current location, where they are relevant, than to move them out to mixins.less and increase complexity for the next developer to troubleshoot.
What felt intuitive, but is clearly wrong, was something like this:
.category-link,
.caption-link {
background-color: #linkColour;
font-family: #linkFont;
max-width:2em;
& a,
.action-link a {
/* INNER LINK STYLES */
text-decoration:none;
white-space:nowrap;
/* ...INNER LINK STYLES CONTINUE... */
}
}
but is there some other prefix I can apply to a selector to have it based absolutely, rather than relative to it's nesting level?

Absolute selectors can't be added within a nested block because once we nest it under another block, the inner selector is considered as a child of the outer one (like in the DOM) unless we add &. to the selector (in which case, the inner one could be another class on the parent itself).
Using mixins or the :extend feature are the best options for your case because you are assigning a set of common properties to multiple elements.
Since parent selector is known (it is either .category-link a or .caption-link a), you can extend the properties of that selector into .action-link a also. This would extend only the properties of the inner link and not that of its parent.
I don't think this increases the complexity for the next developer to troubleshoot because changing the properties in the original .category-link a will change the properties for .action-link a also.
.category-link,
.caption-link {
background-color: blue;
font-family: Arial;
max-width:2em;
a {
/* INNER LINK STYLES */
text-decoration:none;
white-space:nowrap;
/* ...INNER LINK STYLES CONTINUE... */
}
}
.action-link {
a {
&:extend(.category-link a);
}
}

Related

CSS reset all styles in a div but allow lower styles to over write it

So have my main style sheet that sets all the styles for my site. But I have a div that opens as menu. I need it to have it's own style and I can't have it or it's decedents inherent any styles from the main style sheet. But after I reset the style I'm then styling the div like it's a whole new element. I found the all: initial; rest the elements. and #we_gallery_edit_window > * sort of works. But when I try to declare the new styles some of the new styles won't take because of precedence. here is my code so far:
h1
{
color: #000000;
background-color: #FFFFFF;
}
#my_div > * /*Clear all previous CSS for #mydiv only */
{
all: initial;
}
.my_div_child h1
{
color: #F0F0F0;
}
<h1>Hello</h1> //Should be black with background
<div id='my_div'>
<h1 class='my_div_child'>Good bye</h1> //Should be grey without background
</div>
<h1>Hello</h1> //Should be black with background
I need a selector that will override everything above it but has no precedence over anything below it. So remove the style set by h1 in the main div, then reset h1 of .my_div_child. it's not just the h1 element I'm having trouble with but that's the easiest example I can think of.
Okay, after seeing the updated post, I think I get the idea.
I think you may be simply using the wrong selectors. You may review CSS selectors if you're unsure.
For one thing, if you want to style an h1 with the class of my_div_child, the rule would be h1.my_div_child, or simply .my_div_child, if you don't have other, non-h1 elements with that class name. Using .my_div_child h1 will select h1 tags inside a parent container with the class of my_div_child, which is not what your HTML shows.
If you want to reset the styles of children of #my_div, you can use the all: initial selector with the wildcard like you did, but instead of using the direct child selector (>), just nest the wildcard regularly:
#my_div * {
all: initial;
}
If you use the direct child selector, only the first level of children in #my_div will be reset, but grandchildren of #my_div won't be, which is probably not what you want.
Those things cleared up, simply use the above statement to reset your styles and then start styling the contents of #my_div as needed, and it should work because various tags (e.g., h1) will be more specific than the wildcard. See code snippet below.
That said, you may find it easier to simply override certain styles that aren't what you want by using specificity than to reset everything in #my_div and start over. Odds are there are some styles the menu will share with the site overall. For example:
h1 {
font-style: italic;
}
#my_div h1 {
font-style: normal;
}
If these approaches don't work, and you're still having trouble with your styles not working, you'd have to post some more specific code so we can work out what the problem is.
Example reset:
html {
background-color: coral;
font-style: italic;
font-family: sans-serif;
}
h1 {
background-color: white;
}
#my_div * {
all: initial;
}
#my_div .my_div_child {
color: darkgray;
font-size: 4em;
/* note that font-style and font-family don't need rules b/c they have been reset by all: initial above */
}
<h1>Hello</h1> <!-- Should be black with background -->
<div id="my_div">
<h1 class="my_div_child">Good bye</h1> <!-- Should be grey without background -->
</div>
<h1>Hello</h1> <!-- Should be black with background -->

What is the simplest way to clear all pseudo classes on an element?

I am writing a stylesheet to extend a base stylesheet whose CSS has many pseudo classes applied to certain elements. I would like my stylesheet to override some of these styles with a single style that is applied to an element no matter what state it is in, whether hovered on, focussed etc.
For example, the base stylesheet might have the styles
.classname {
color:#f00;
}
.classname:hover {
color:#0f0;
}
.classname:active {
color:#00f;
}
but adding the following after these styles does not override the pseudo states...
.classname {
color:#fff;
}
The following works, but it feels a lot of code for something that seems simple.
.classname,
.classname:active,
.classname:hover,
.classname:focus,
.classname:visited,
.classname:valid{
color:#fff;
}
Likewise, I know an !important would work, but that's normally a warning sign of a poorly structured stylesheet.
Is there anything along the lines of a .classname:* that would cover every possible state, or some way to simply remove all pseudo classes?
If you are able to put the classes inside some wrapper id you can prevent the pseudo-classes to take effect due to specificity:
body {
background: black;
}
.classname {
color:#f00;
}
.classname:hover {
color:#0f0;
}
.classname:active {
color:#00f;
}
#a .classname {
color:#fff;
}
<div class="classname">all pseudo works</div>
<div id="a">
<div class="classname">none of the pseudo works</div>
</div>
I think, it could be solved with :any pseudo-class.
Google
<style>
a:link { color: blue; }
a:hover { color: red; }
a:-webkit-any(a) { color: green; }
</style>
https://jsfiddle.net/ycfokuju
Browser support is not perfect: https://developer.mozilla.org/en/docs/Web/CSS/:any
Edit:
Actually, as I discovered, this answer isn't very accurate. (Despite it was upvoted 4 times, lol).
First of all, you don't need :any fot this task. You need :any-link.
The second point is that :any itself is a former name of :matches. So, in our terminology we should use terms :any-link and :matches and don't use term :any.
Example of using :any-link: https://developer.mozilla.org/en-US/docs/Web/CSS/:any-link
Examples of using :mathes: https://css-tricks.com/almanac/selectors/m/matches/
I haven't edited the code itself, so fix it yourself according to this new information.

How to create css classes from existing ones? [duplicate]

Is it possible to make a CSS class that "inherits" from another CSS class (or more than one).
For example, say we had:
.something { display:inline }
.else { background:red }
What I'd like to do is something like this:
.composite
{
.something;
.else
}
where the ".composite" class would both display inline and have a red background
There are tools like LESS, which allow you to compose CSS at a higher level of abstraction similar to what you describe.
Less calls these "Mixins"
Instead of
/* CSS */
#header {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
#footer {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
You could say
/* LESS */
.rounded_corners {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
#header {
.rounded_corners;
}
#footer {
.rounded_corners;
}
You can add multiple classes to a single DOM element, e.g.
<div class="firstClass secondClass thirdclass fourthclass"></div>
Rules given in later classes (or which are more specific) override. So the fourthclass in that example kind of prevails.
Inheritance is not part of the CSS standard.
Yes, but not exactly with that syntax.
.composite,
.something { display:inline }
.composite,
.else { background:red }
Keep your common attributes together and assign specific (or override) attributes again.
/* ------------------------------------------------------------------------------ */
/* Headings */
/* ------------------------------------------------------------------------------ */
h1, h2, h3, h4
{
font-family : myfind-bold;
color : #4C4C4C;
display:inline-block;
width:900px;
text-align:left;
background-image: linear-gradient(0, #F4F4F4, #FEFEFE);/* IE6 & IE7 */
}
h1
{
font-size : 300%;
padding : 45px 40px 45px 0px;
}
h2
{
font-size : 200%;
padding : 30px 25px 30px 0px;
}
The SCSS way for the given example, would be something like:
.something {
display: inline
}
.else {
background: red
}
.composite {
#extend .something;
#extend .else;
}
More info, check the sass basics
An element can take multiple classes:
.classOne { font-weight: bold; }
.classTwo { font-famiy: verdana; }
<div class="classOne classTwo">
<p>I'm bold and verdana.</p>
</div>
And that's about as close as you're going to get unfortunately. I'd love to see this feature, along with class-aliases someday.
No you can't do something like
.composite
{
.something;
.else
}
This are no "class" names in the OO sense. .something and .else are just selectors nothing more.
But you can either specify two classes on an element
<div class="something else">...</div>
or you might look into another form of inheritance
.foo {
background-color: white;
color: black;
}
.bar {
background-color: inherit;
color: inherit;
font-weight: normal;
}
<div class="foo">
<p class="bar">Hello, world</p>
</div>
Where the paragraphs backgroundcolor and color are inherited from the settings in the enclosing div which is .foo styled. You might have to check the exact W3C specification. inherit is default for most properties anyway but not for all.
I ran into this same problem and ended up using a JQuery solution to make it seem like a class can inherit other classes.
<script>
$(function(){
$(".composite").addClass("something else");
});
</script>
This will find all elements with the class "composite" and add the classes "something" and "else" to the elements. So something like <div class="composite">...</div> will end up like so: <div class="composite something else">...</div>
You can do is this
CSS
.car {
font-weight: bold;
}
.benz {
background-color: blue;
}
.toyota {
background-color: white;
}
HTML
<div class="car benz">
<p>I'm bold and blue.</p>
</div>
<div class="car toyota">
<p>I'm bold and white.</p>
</div>
Don't forget:
div.something.else {
// will only style a div with both, not just one or the other
}
You can use the converse approach to achieve the same result - start from the composite and then remove styling using the unset keyword. For example, if you start with the following sample composition:
.composite {
color: red;
margin-left: 50px;
background-color: green
}
you can then increase selector specificity to selectively remove styles using unset:
.composite.no-color {
color: unset
}
.composite.no-margin-left {
margin-left: unset
}
.composite.no-background-color {
background-color: unset
}
Here is a JSFiddle demonstrating this approach.
One benefit of this approach is that because the specificity of the compound selectors is higher than the composite itself, you do not need all of the combinations of classes to achieve the desired results for multiple combinations:
/* Multi-unset compound selector combinations, such as the one that follows, ARE NOT NECESSARY because of the higher specificity of each individual compound selectors listed above. This keeps things simple. */
.composite.no-background-color.no-color.no-margin-left {
background-color: unset;
color: unset;
margin-left: unset
}
Furthermore, at 96% support for the unset keyword, browser coverage is excellent.
Perfect timing: I went from this question to my email, to find an article about Less, a Ruby library that among other things does this:
Since super looks just like footer, but with a different font, I'll use Less's class inclusion technique (they call it a mixin) to tell it to include these declarations too:
#super {
#footer;
font-family: cursive;
}
In Css file:
p.Title
{
font-family: Arial;
font-size: 16px;
}
p.SubTitle p.Title
{
font-size: 12px;
}
I realize this question is now very old but, here goes nothin!
If the intent is to add a single class that implies the properties of multiple classes, as a native solution, I would recommend using JavaScript/jQuery (jQuery is really not necessary but certainly useful)
If you have, for instance .umbrellaClass that "inherits" from .baseClass1 and .baseClass2 you could have some JavaScript that fires on ready.
$(".umbrellaClass").addClass("baseClass1");
$(".umbrellaClass").addClass("baseClass2");
Now all elements of .umbrellaClass will have all the properties of both .baseClasss. Note that, like OOP inheritance, .umbrellaClass may or may not have its own properties.
The only caveat here is to consider whether there are elements being dynamically created that won't exist when this code fires, but there are simple ways around that as well.
Sucks css doesn't have native inheritance, though.
Unfortunately, CSS does not provide 'inheritance' in the way that programming languages like C++, C# or Java do. You can't declare a CSS class an then extend it with another CSS class.
However, you can apply more than a single class to an tag in your markup ... in which case there is a sophisticated set of rules that determine which actual styles will get applied by the browser.
<span class="styleA styleB"> ... </span>
CSS will look for all the styles that can be applied based on what your markup, and combine the CSS styles from those multiple rules together.
Typically, the styles are merged, but when conflicts arise, the later declared style will generally win (unless the !important attribute is specified on one of the styles, in which case that wins). Also, styles applied directly to an HTML element take precedence over CSS class styles.
Don't think of css classes as object oriented classes, think of them as merely a tool among other selectors to specify which attribute classes an html element is styled by. Think of everything between the braces as the attribute class, and selectors on the left-hand side tell the elements they select to inherit attributes from the attribute class. Example:
.foo, .bar { font-weight : bold; font-size : 2em; /* attribute class A */}
.foo { color : green; /* attribute class B */}
When an element is given the attribute class="foo", it is useful to think of it not as inheriting attributes from class .foo, but from attribute class A and attribute class B. I.e., the inheritance graph is one level deep, with elements deriving from attribute classes, and the selectors specifying where the edges go, and determining precedence when there are competing attributes (similar to method resolution order).
The practical implication for programming is this. Say you have the style sheet given above, and want to add a new class .baz, where it should have the same font-size as .foo. The naive solution would be this:
.foo, .bar { font-weight : bold; font-size : 2em; /* attribute class A */}
.foo { color : green; /* attribute class B */}
.baz { font-size : 2em; /* attribute class C, hidden dependency! */}
Any time I have to type something twice I get so mad! Not only do I have to write it twice, now I have no way of programatically indicating that .foo and .baz should have the same font-size, and I've created a hidden dependency! My above paradigm would suggest that I should abstract out the font-size attribute from attribute class A:
.foo, .bar, .baz { font-size : 2em; /* attribute base class for A */}
.foo, .bar { font-weight : bold; /* attribute class A */}
.foo { color : green; /* attribute class B */}
The main complaint here is that now I have to retype every selector from attribute class A again to specify that the elements they should select should also inherit attributes from attribute base class A. Still, the alternatives are to have to remember to edit every attribute class where there are hidden dependencies each time something changes, or to use a third party tool. The first option makes god laugh, the second makes me want to kill myself.
That's not possible in CSS.
The only thing supported in CSS is being more specific than another rule:
span { display:inline }
span.myclass { background: red }
A span with class "myclass" will have both properties.
Another way is by specifying two classes:
<div class="something else">...</div>
The style of "else" will override (or add) the style of "something"
As others have said, you can add multiple classes to an element.
But that's not really the point. I get your question about inheritance. The real point is that inheritance in CSS is done not through classes, but through element hierarchies. So to model inherited traits you need to apply them to different levels of elements in the DOM.
While direct inheritance isn't possible.
It is possible to use a class (or id) for a parent tag and then use CSS combinators to alter child tag behaviour from it's heirarchy.
p.test{background-color:rgba(55,55,55,0.1);}
p.test > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
<p class="test"><span>One <span>possible <span>solution <span>is <span>using <span>multiple <span>nested <span>tags</span></span></span></span></span></span></span></span></p>
I wouldn't suggest using so many spans like the example, however it's just a proof of concept. There are still many bugs that can arise when trying to apply CSS in this manner. (For example altering text-decoration types).
I was looking for that like crazy too and I just figured it out by trying different things :P... Well you can do it like that:
composite.something, composite.else
{
blblalba
}
It suddenly worked for me :)
In specific circumstances you can do a "soft" inheritance:
.composite
{
display:inherit;
background:inherit;
}
.something { display:inline }
.else { background:red }
This only works if you are adding the .composite class to a child element. It is "soft" inheritance because any values not specified in .composite are not inherited obviously. Keep in mind it would still be less characters to simply write "inline" and "red" instead of "inherit".
Here is a list of properties and whether or not they do this automatically:
https://www.w3.org/TR/CSS21/propidx.html
Less and Sass are CSS pre-processors which extend CSS language in valuable ways. Just one of many improvements they offer is just the option you're looking for. There are some very good answers with Less and I will add Sass solution.
Sass has extend option which allows one class to be fully extended to another one. More about extend you can read in this article
I think this one is a better solution:
[class*=“button-“] {
/* base button properties */
}
.button-primary { ... }
.button-plain { ... }
Actually what you're asking for exists - however it's done as add-on modules. Check out this question on Better CSS in .NET for examples.
Check out Larsenal's answer on using LESS to get an idea of what these add-ons do.
CSS doesn't really do what you're asking. If you want to write rules with that composite idea in mind, you may want to check out compass. It's a stylesheet framework which looks similar to the already mentioned Less.
It lets you do mixins and all that good business.
For those who are not satisfied with the mentioned (excellent) posts, you can use your programming skills to make a variable (PHP or whichever) and have it store the multiple class names.
That's the best hack I could come up with.
<style>
.red { color: red; }
.bold { font-weight: bold; }
</style>
<? define('DANGERTEXT','red bold'); ?>
Then apply the global variable to the element you desire rather than the class names themselves
<span class="<?=DANGERTEXT?>"> Le Champion est Ici </span>
Have a look at CSS compose:
https://bambielli.com/til/2017-08-11-css-modules-composes/
according to them:
.serif-font {
font-family: Georgia, serif;
}
.display {
composes: serif-font;
font-size: 30px;
line-height: 35px;
}
I use it in my react project.
If you want a more powerful text preprocessor than LESS, check out PPWizard:
http://dennisbareis.com/ppwizard.htm
Warning the website is truly hideous and there's a small learning curve, but it's perfect for building both CSS and HTML code via macros. I've never understood why more web coders don't use it.
You can achieve what you want if you preprocess your .css files through php.
...
$something='color:red;'
$else='display:inline;';
echo '.something {'. $something .'}';
echo '.else {'. $something .'}';
echo '.somethingelse {'. $something .$else '}';
...

CSS Applying wildcard to pseudo classes

Hopefully this isn't a stupid question but I can't seem to work out how to do this. Can you apply a wildcard to an anchor hover/focus so that the style is applied to all classes?
Something like
a:hover * { color: #ff0000; }
Say I have
a { color: #DD0000; }
a.link { color: #ffffff; }
a.link2 { color: #000000; }
a.user { ...
a.anything { ...
The easiest way to explain what I'm looking for is to have a global :hover style, but multiple :link styles.
Thanks
There are a number of ways you can do this. As mentioned by others, you can apply the same style to multiple classes like so:
div a.class1:hover, div a.class2:hover, div a.class3:hover { ... }
You can also create a custom class just for the style you want to apply:
div a.customClass:hover { ... }
You could use * like you mentioned in the question, but apply hover to it:
div *:hover { ... }
There's also this option, where you just apply the style for all a's, although you probably know about this option already:
a:hover { ... }
Edit: If your style is being "overwritten" by something else, a quick and easy way to check would be to use your browser's developer tools to inspect the element. You can even apply pseudo-classes (ie. apply :hover pseudo-class even when you're not hovering over the element) with the developer tools included with Chrome and Firefox (you may need to download Firebug to do this with Firefox).
Another option would be to use !important to increase the selector's specificity. For example:
a:hover { background: red !important; }
You can read more about how the specificity is calculated here.
If you want to apply a global css rule for a specific tag, write (for anchors):
a:link{/*your styles go here*/}
a:hover{/*your styles go here*/}
a:active{/*your styles go here*/}
a:visited{/*your styles go here*/}
If you would like a special link styled in a different way (maybe making it a button), just apply a class to it and style the class:
a.customlink{/*your styles go here*/}
EDIT: if you want only some properties of the link to change on hover, which are going to be the same for two different links (let's say one ha yellow, while the other red colored background, and you wanted them both to have a black background), add another same class to the two links, and stylize it.
JsFiddle Example
You could separate them by commas like a:hover link, a:hover link2, a:hover etc { color: #ff0000; }
Does a:hover { color: #ff0000; } not do what you want it to?

Can a CSS class inherit one or more other classes?

Is it possible to make a CSS class that "inherits" from another CSS class (or more than one).
For example, say we had:
.something { display:inline }
.else { background:red }
What I'd like to do is something like this:
.composite
{
.something;
.else
}
where the ".composite" class would both display inline and have a red background
There are tools like LESS, which allow you to compose CSS at a higher level of abstraction similar to what you describe.
Less calls these "Mixins"
Instead of
/* CSS */
#header {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
#footer {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
You could say
/* LESS */
.rounded_corners {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
border-radius: 8px;
}
#header {
.rounded_corners;
}
#footer {
.rounded_corners;
}
You can add multiple classes to a single DOM element, e.g.
<div class="firstClass secondClass thirdclass fourthclass"></div>
Rules given in later classes (or which are more specific) override. So the fourthclass in that example kind of prevails.
Inheritance is not part of the CSS standard.
Yes, but not exactly with that syntax.
.composite,
.something { display:inline }
.composite,
.else { background:red }
Keep your common attributes together and assign specific (or override) attributes again.
/* ------------------------------------------------------------------------------ */
/* Headings */
/* ------------------------------------------------------------------------------ */
h1, h2, h3, h4
{
font-family : myfind-bold;
color : #4C4C4C;
display:inline-block;
width:900px;
text-align:left;
background-image: linear-gradient(0, #F4F4F4, #FEFEFE);/* IE6 & IE7 */
}
h1
{
font-size : 300%;
padding : 45px 40px 45px 0px;
}
h2
{
font-size : 200%;
padding : 30px 25px 30px 0px;
}
The SCSS way for the given example, would be something like:
.something {
display: inline
}
.else {
background: red
}
.composite {
#extend .something;
#extend .else;
}
More info, check the sass basics
An element can take multiple classes:
.classOne { font-weight: bold; }
.classTwo { font-famiy: verdana; }
<div class="classOne classTwo">
<p>I'm bold and verdana.</p>
</div>
And that's about as close as you're going to get unfortunately. I'd love to see this feature, along with class-aliases someday.
No you can't do something like
.composite
{
.something;
.else
}
This are no "class" names in the OO sense. .something and .else are just selectors nothing more.
But you can either specify two classes on an element
<div class="something else">...</div>
or you might look into another form of inheritance
.foo {
background-color: white;
color: black;
}
.bar {
background-color: inherit;
color: inherit;
font-weight: normal;
}
<div class="foo">
<p class="bar">Hello, world</p>
</div>
Where the paragraphs backgroundcolor and color are inherited from the settings in the enclosing div which is .foo styled. You might have to check the exact W3C specification. inherit is default for most properties anyway but not for all.
I ran into this same problem and ended up using a JQuery solution to make it seem like a class can inherit other classes.
<script>
$(function(){
$(".composite").addClass("something else");
});
</script>
This will find all elements with the class "composite" and add the classes "something" and "else" to the elements. So something like <div class="composite">...</div> will end up like so: <div class="composite something else">...</div>
You can do is this
CSS
.car {
font-weight: bold;
}
.benz {
background-color: blue;
}
.toyota {
background-color: white;
}
HTML
<div class="car benz">
<p>I'm bold and blue.</p>
</div>
<div class="car toyota">
<p>I'm bold and white.</p>
</div>
Don't forget:
div.something.else {
// will only style a div with both, not just one or the other
}
You can use the converse approach to achieve the same result - start from the composite and then remove styling using the unset keyword. For example, if you start with the following sample composition:
.composite {
color: red;
margin-left: 50px;
background-color: green
}
you can then increase selector specificity to selectively remove styles using unset:
.composite.no-color {
color: unset
}
.composite.no-margin-left {
margin-left: unset
}
.composite.no-background-color {
background-color: unset
}
Here is a JSFiddle demonstrating this approach.
One benefit of this approach is that because the specificity of the compound selectors is higher than the composite itself, you do not need all of the combinations of classes to achieve the desired results for multiple combinations:
/* Multi-unset compound selector combinations, such as the one that follows, ARE NOT NECESSARY because of the higher specificity of each individual compound selectors listed above. This keeps things simple. */
.composite.no-background-color.no-color.no-margin-left {
background-color: unset;
color: unset;
margin-left: unset
}
Furthermore, at 96% support for the unset keyword, browser coverage is excellent.
Perfect timing: I went from this question to my email, to find an article about Less, a Ruby library that among other things does this:
Since super looks just like footer, but with a different font, I'll use Less's class inclusion technique (they call it a mixin) to tell it to include these declarations too:
#super {
#footer;
font-family: cursive;
}
In Css file:
p.Title
{
font-family: Arial;
font-size: 16px;
}
p.SubTitle p.Title
{
font-size: 12px;
}
I realize this question is now very old but, here goes nothin!
If the intent is to add a single class that implies the properties of multiple classes, as a native solution, I would recommend using JavaScript/jQuery (jQuery is really not necessary but certainly useful)
If you have, for instance .umbrellaClass that "inherits" from .baseClass1 and .baseClass2 you could have some JavaScript that fires on ready.
$(".umbrellaClass").addClass("baseClass1");
$(".umbrellaClass").addClass("baseClass2");
Now all elements of .umbrellaClass will have all the properties of both .baseClasss. Note that, like OOP inheritance, .umbrellaClass may or may not have its own properties.
The only caveat here is to consider whether there are elements being dynamically created that won't exist when this code fires, but there are simple ways around that as well.
Sucks css doesn't have native inheritance, though.
Unfortunately, CSS does not provide 'inheritance' in the way that programming languages like C++, C# or Java do. You can't declare a CSS class an then extend it with another CSS class.
However, you can apply more than a single class to an tag in your markup ... in which case there is a sophisticated set of rules that determine which actual styles will get applied by the browser.
<span class="styleA styleB"> ... </span>
CSS will look for all the styles that can be applied based on what your markup, and combine the CSS styles from those multiple rules together.
Typically, the styles are merged, but when conflicts arise, the later declared style will generally win (unless the !important attribute is specified on one of the styles, in which case that wins). Also, styles applied directly to an HTML element take precedence over CSS class styles.
Don't think of css classes as object oriented classes, think of them as merely a tool among other selectors to specify which attribute classes an html element is styled by. Think of everything between the braces as the attribute class, and selectors on the left-hand side tell the elements they select to inherit attributes from the attribute class. Example:
.foo, .bar { font-weight : bold; font-size : 2em; /* attribute class A */}
.foo { color : green; /* attribute class B */}
When an element is given the attribute class="foo", it is useful to think of it not as inheriting attributes from class .foo, but from attribute class A and attribute class B. I.e., the inheritance graph is one level deep, with elements deriving from attribute classes, and the selectors specifying where the edges go, and determining precedence when there are competing attributes (similar to method resolution order).
The practical implication for programming is this. Say you have the style sheet given above, and want to add a new class .baz, where it should have the same font-size as .foo. The naive solution would be this:
.foo, .bar { font-weight : bold; font-size : 2em; /* attribute class A */}
.foo { color : green; /* attribute class B */}
.baz { font-size : 2em; /* attribute class C, hidden dependency! */}
Any time I have to type something twice I get so mad! Not only do I have to write it twice, now I have no way of programatically indicating that .foo and .baz should have the same font-size, and I've created a hidden dependency! My above paradigm would suggest that I should abstract out the font-size attribute from attribute class A:
.foo, .bar, .baz { font-size : 2em; /* attribute base class for A */}
.foo, .bar { font-weight : bold; /* attribute class A */}
.foo { color : green; /* attribute class B */}
The main complaint here is that now I have to retype every selector from attribute class A again to specify that the elements they should select should also inherit attributes from attribute base class A. Still, the alternatives are to have to remember to edit every attribute class where there are hidden dependencies each time something changes, or to use a third party tool. The first option makes god laugh, the second makes me want to kill myself.
That's not possible in CSS.
The only thing supported in CSS is being more specific than another rule:
span { display:inline }
span.myclass { background: red }
A span with class "myclass" will have both properties.
Another way is by specifying two classes:
<div class="something else">...</div>
The style of "else" will override (or add) the style of "something"
As others have said, you can add multiple classes to an element.
But that's not really the point. I get your question about inheritance. The real point is that inheritance in CSS is done not through classes, but through element hierarchies. So to model inherited traits you need to apply them to different levels of elements in the DOM.
While direct inheritance isn't possible.
It is possible to use a class (or id) for a parent tag and then use CSS combinators to alter child tag behaviour from it's heirarchy.
p.test{background-color:rgba(55,55,55,0.1);}
p.test > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
p.test > span > span > span > span > span > span > span > span{background-color:rgba(55,55,55,0.1);}
<p class="test"><span>One <span>possible <span>solution <span>is <span>using <span>multiple <span>nested <span>tags</span></span></span></span></span></span></span></span></p>
I wouldn't suggest using so many spans like the example, however it's just a proof of concept. There are still many bugs that can arise when trying to apply CSS in this manner. (For example altering text-decoration types).
I was looking for that like crazy too and I just figured it out by trying different things :P... Well you can do it like that:
composite.something, composite.else
{
blblalba
}
It suddenly worked for me :)
In specific circumstances you can do a "soft" inheritance:
.composite
{
display:inherit;
background:inherit;
}
.something { display:inline }
.else { background:red }
This only works if you are adding the .composite class to a child element. It is "soft" inheritance because any values not specified in .composite are not inherited obviously. Keep in mind it would still be less characters to simply write "inline" and "red" instead of "inherit".
Here is a list of properties and whether or not they do this automatically:
https://www.w3.org/TR/CSS21/propidx.html
Less and Sass are CSS pre-processors which extend CSS language in valuable ways. Just one of many improvements they offer is just the option you're looking for. There are some very good answers with Less and I will add Sass solution.
Sass has extend option which allows one class to be fully extended to another one. More about extend you can read in this article
I think this one is a better solution:
[class*=“button-“] {
/* base button properties */
}
.button-primary { ... }
.button-plain { ... }
Actually what you're asking for exists - however it's done as add-on modules. Check out this question on Better CSS in .NET for examples.
Check out Larsenal's answer on using LESS to get an idea of what these add-ons do.
CSS doesn't really do what you're asking. If you want to write rules with that composite idea in mind, you may want to check out compass. It's a stylesheet framework which looks similar to the already mentioned Less.
It lets you do mixins and all that good business.
For those who are not satisfied with the mentioned (excellent) posts, you can use your programming skills to make a variable (PHP or whichever) and have it store the multiple class names.
That's the best hack I could come up with.
<style>
.red { color: red; }
.bold { font-weight: bold; }
</style>
<? define('DANGERTEXT','red bold'); ?>
Then apply the global variable to the element you desire rather than the class names themselves
<span class="<?=DANGERTEXT?>"> Le Champion est Ici </span>
Have a look at CSS compose:
https://bambielli.com/til/2017-08-11-css-modules-composes/
according to them:
.serif-font {
font-family: Georgia, serif;
}
.display {
composes: serif-font;
font-size: 30px;
line-height: 35px;
}
I use it in my react project.
If you want a more powerful text preprocessor than LESS, check out PPWizard:
http://dennisbareis.com/ppwizard.htm
Warning the website is truly hideous and there's a small learning curve, but it's perfect for building both CSS and HTML code via macros. I've never understood why more web coders don't use it.
You can achieve what you want if you preprocess your .css files through php.
...
$something='color:red;'
$else='display:inline;';
echo '.something {'. $something .'}';
echo '.else {'. $something .'}';
echo '.somethingelse {'. $something .$else '}';
...

Resources