Abstract superclass - sass

I'm trying to get SASS to do something akin to an abstract superclass in programming. I'm getting as far as the superclass part
.box {
#include span-columns(1);
#include border-radius(5px);
height: 360px;
overflow: hidden;
}
article {
#extend .box;
}
figure {
#extend .box;
}
This is a way to define commonalities of boxes without duplicating them in the generated CSS, as would happen with a mixin. However, this solution has the blemish of defining a rule for a (CSS) class "box" that I don't really need and want.
To be sure, this is a minor issue, still I'd like to know if there is a way to make ".box" into a label that is only used during SASS preprocessing and does not appear in CSS.

You want to define your "superclass" using a % instead of a .
%box {
#include span-columns(1);
#include border-radius(5px);
height: 360px;
overflow: hidden;
}
article {
#extend %box;
}
figure {
#extend %box;
}
Note that this requires version 3.2+

Related

Combine raw selector with mixin into single query

I have the following SASS rules:
p {
margin: 0;
}
#include desktop() {
p {
margin: 0;
}
}
The mixin is like this:
#mixin desktop() {
#media screen and (min-width: 1200px) {
#content;
}
}
Elsewhere in the codebase there's a margin being set on desktop, hence in this case I need to explicitly remove it on the desktop breakpoint too, just having the first p selector rule doesn't cut it.
Is there a neat way to combine the selectors as it feels verbose having the same margin: 0 rule twice? I realise there's probably something more fundamentally wrong here with the inheritance, but that's outside the scope of the question. I don't want to use !important.
Many thanks.
Is there a neat way to combine the selectors? Sure there is… Just use another mixin:
#mixin para {
p {
margin: 0;
}
}
#include para;
#include desktop {
#include para;
}
You clearly already know how to use mixins, so I'm assuming your question is really about whether you can nest one mixin within another (yes), or whether you can include selectors within a mixin (yes).

Ampersand and mixins in SCSS

Searched but can't find an answer..
I have an element which gets generated (by an external platform) with the following classes: p-button and button.
Now the SCSS is like this:
.p-button {
&.button {
margin: 10px;
}
}
But I want to refactor using mixin includes (this is a big project so there is no other way of making this code better except using mixins). The mixin takes the given selector and applies a . to it. I can't change the mixin, as it is used by many other teams, so I can't pass the ampersand together with the selector. I tried this:
.p-button {
& {
#include button-appearance("button") {
margin: 10px;
}
}
}
But that doesn't work (puts a space between it). You can't do this:
.p-button {
&#include button-appearance("button") {
margin: 10px;
}
}
Anyone have a clue?
EDIT: Here is the mixin
#mixin button-appearance(
$appearance-class,
$show,
$background-color,
$background-image,
$background-position) {
$sel: $button-selector;
#if $appearance-class {
$sel: $sel + '.' + $appearance-class;
}
#{$sel} {
#include normalized-background-image($background-image);
#include show($show);
background-color: $background-color;
background-position: $background-position;
}
#content;
}
EDIT 2: Here is the $button-selector (I can not edit this in the platform, but maybe overwrite it in my own project?)
$button-class: 'p-button';
$button-selector: '.#{$button-class}';
Everyone, finally found the solution. I just removed the &.button from the .p-button mixin include and now it works:
#include button-appearance ("button") { *styles* }
#include button-appearance () { *styles* }
Edited the answer after the original question was edited adding the used and un modifiable mixin
The original mixin does not append the ‘#content’ passed to the mixin to the generated selector. So if you cannot modify the original mixin, the only way is to add your properties outside the mixin. According to the mixin the selector will match a predefined ‘$button-selector’ variable, so it won’t use your class.
So, if you want to use the same class defined in ‘$button-class’, try the following:
#{$button-selector}.button {
margin: 10px;
}
Will output:
.p-button.button {
margin: 10px;
}

SASS/SCSS change variable value before extend

I have Bootstrap 3.3.7 and custom scss files.
I want to override $grid-float-breakpoint only once before #extend evaluates. Right now I have 3 classes which extend base bootstrap class (they use default value, so i don't want to mess with them).
In doc when using mixins and include it's possible. Is it possible using .class and #extend?
I'm looking for something like
$foo : 1px;
.normal-class {
font-size: $foo;
}
.extended-normal-class {
#extend .normal-class;
font-color: yellow;
}
-- This is what I'm trying to do: ---------------------
.override-class {
$foo: 3px;
#extend .normal-class;
// font-size in this class after compile should have 3px;
}
To achiev what you need, you must use #mixin instead of #extend, heres follow an example:
#mixin size($size: 1px){
font-size: $size;
}
.extended-normal-class{
#include size();
}
.override-class{
#include size(3px);
}

compiling sass with grunt produce invalid property name

I don't know why but while compiling with grunt or anything there is an error called invalid property name
#flotTip {
border: none !important;
font-size: $font-size-small !important;
line-height: 1px !important;
#extend .tooltip-inner() !important;
}
in the above code in the line-height it produces an undefined property. My task was to convert all less files into sass files. Used many solutions to convert all of them to sass as far as I can find. But this one I can't find any solution. Can anyone answer what might be the problem?
Extend is only for extending simple selectors, like class, element, or id. You cannot use !important with #extend. This is the correct way to use extend:
.foo {
color: red;
}
#flotTip {
#extend .foo;
}
You may be confused confusing extends with mixins, which also cannot use !important. This is the correct way to use mixins:
#mixin foo() {
color: red;
}
#flotTip {
#include foo();
}
The line-height: 1px !important; line looks fine. The problem is with the following line. If you're trying to include a mixin, use #include and don't prefix the mixin's name with . (dot). Also, don't put !important after it.
I would guess that you are using #extend incorrectly. See the docs here: http://sass-lang.com/documentation/file.SASS_REFERENCE.html#how_it_works

sass dynamic width

I'm using
.w400 {
width: 400px;
}
.w110 {
width: 110px;
}
.w600 {
width: 600px;
}
is it possible to make dynamic class with sass?
something like
.w(size) {
width: size+px
}
If you want to be able to use arbitrary .w(something) classes, I believe (see below) that is not possible with Sass. However, if you know beforehand what sizes you need, you could use mixins with arguments to generate the classes. Something like this:
#mixin width-class($size) {
.w#{$size} {
width: $size * 1px;
}
}
You would use it like this:
#include width-class(400);
#include width-class(110);
This generates the following CSS:
.w400 {
width: 400px; }
.w110 {
width: 110px; }
Now, if you want to avoid writing a new #include line for each of the classes, you can create another mixins (or combine the two mixins into one):
#mixin dynwidths($size-list) {
#each $size in $size-list {
#include width-class($size)
}
}
Now you can pass it a list of widths. This generates the same CSS as above:
#include width-classes(400 110);
Note: This is just a guess, but wildcard class names might be possible by extending Sass with Ruby. However, I'm not sure if this is a desirable feature.

Resources