Make a dynamic SCSS method to change variable values - css

I have done a project with a lot of code duplicity, so the problem occurs because I have to write the class in each query.
I'm trying to improve performance here. In order to do that, I want to use dynamic values for styling.
For example, the way CSS is being used here, but in ten different places using the same animation.
$center : 590px;
.container {
width: $center;
}
#media only screen and (max-width: 1660px){
//here I want to change $center to 490px;
// =================================================
// but the way that I found is to duplicate it
$center: 490px;
.container {
width: $center;
}
/*note : if I don't call the '.container' everytime that I'm changing the $center variable it does not work,
I have some animations that must use the variables .
*/
}

You can make use of #mixin and #include to avoid duplication.
#mixin media-container($center) {
#media only screen and (max-width: 1660px) {
.container {
width: $center;
}
}
}
In order to use the #mixin in any classes you want, you can add the following to the class you want to use this in:
.container-class {
#include media-container(540px);
}
Note that the 540px above can be replaced with any configuration you want for $center variable, which would change the width for your container.
Documentation: https://sass-lang.com/documentation/at-rules/mixin

SCSS variables are static (compile time) to do what you want you need to use CSSVariables that are dynamic (run time) - something like this
.container {
width: var(--width, 590px); /* default */
}
#media only screen and (max-width: 1660px){
.container {
--width: 490px;
}
}
If you need to set multiple values - you can use Sass nesting
to make it a little easier to type
.container {
width: var(--width, 50px);
#media (min-width: 100px) { --width: 100px; }
#media (min-width: 200px) { --width: 200px; }
#media (min-width: 300px) { --width: 300px; }
...
}
// output
.container {
width: var(--width, 50px);
}
#media (min-width: 100px) {
.container { --width: 100px; }
}
#media (min-width: 200px) {
.container { --width: 200px; }
}
#media (min-width: 300px) {
.container { --width: 300px; }
}

Related

Using variables in an #include block in SASS

I have this mixin:
#mixin mobile {
#media (max-width: 576px) {
#content;
}
}
And I'm trying to do the following:
height: calc($image_height - $spacing_between_items);
But the variables don't get evaluated. I think it might be because of how #content works, but I'm not a SASS expert.
Why is this happening and how can I fix it?
It's not the way #content works but the way calc() works. You have to interpolate the variables within the calc() function:
$image_height: 100%;
$spacing_between_items: 10px;
#include mobile {
.class {
height: calc(#{$image_height} - #{$spacing_between_items}});
}
}
Outputs:
#media (max-width: 576px) {
.class {
height: calc(100% - 10px});
}
}

CSS Media Query won't work unless I add "!important"

I am using SCSS trying to set up some media queries for max-width: 320px and max-width: 768px
I have a div with class item-content inside an Owl Carousel slide with width set to 600px but I want to reduce the width for smaller devices. I want to use 200px for resolution 320px wide and 300px for resolution that is anywhere between 320 and 768.
This is what I'm using in my _app-responsive.scss but as you can see, I have !important set to the width of item-content because otherwise it is getting overridden even though I am on resolution of the iPhone 5 which is 320px wide.
#media (max-width: 320px) {
.home {
section#top {
.owl-theme {
.owl-dots {
top: -10%;
}
.owl-stage-outer {
.owl-stage {
.owl-item {
.item {
.item-content {
width: 200px !important;
}
}
}
}
}
}
}
}
}
#media (max-width: 768px) {
.home {
section#top {
.owl-theme {
.owl-stage-outer {
.owl-stage {
.owl-item {
.item {
h2 {
font-size: 16px;
}
.item-content {
width: 300px;
}
}
}
}
}
}
}
}
}
This is my overall app.scss
I am importing the file with the media queries last, I tried importing it before the _app-custom.scss but that didn't change anything.
#import 'app-variables';
#import '../../vendor/bootstrap-sass/stylesheets/bootstrap';
#import '../../vendor/bootstrap-sass/stylesheets/bootstrap-compass';
#import '../../vendor/font-awesome/scss/font-awesome';
#import 'app-custom';
#import 'app-responsive';
The two media queries would make width: 200px when window is between 0px and 320px but also width: 300px when window is between 0px and 768px.
To solve this you can apply width: 200px without using a media query and only when windows size is greater than 320px use width: 300px:
.item-content {
width: 200px;
}
#media (min-width: 321px) {
...
.item-content {
width: 300px;
}
}
And:
#media (max-width: 320px) {
...
.item-content {
width: 200px;
}
}
#media (min-width: 321px) and (max-width: 768px) {
...
.item-content {
width: 300px;
}
}
Should also works because your issue is that the query with the max-width: 768px is always overwriting the media query with max-width: 320px

Use container width in Bootstrap 4

We have recently changed to Bootstrap 4, and I'm looking into all the new ways to set widths, breakpoints etc.
I want to make a div have a max-width of the current breakpoint's container width, but I can't find the standard SASS variable name for that specific width.
Note that I can't use classes (e.g. .col-xl-) for this, since I don't have access to this specific part of the HTML.
Have a look at this built-in mixin:
// For each breakpoint, define the maximum width of the container in a media query
#mixin make-container-max-widths($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {
#each $breakpoint, $container-max-width in $max-widths {
#include media-breakpoint-up($breakpoint, $breakpoints) {
width: $container-max-width;
max-width: 100%;
}
}
}
You can create a similar one to your needs like:
#mixin make-max-widths-container-width($max-widths: $container-max-widths, $breakpoints: $grid-breakpoints) {
#each $breakpoint, $container-max-width in $max-widths {
#include media-breakpoint-up($breakpoint, $breakpoints) {
max-width: $container-max-width;
}
}
}
and use it:
.my-custom-class{
#include make-max-widths-container-width();
}
"Compiled" CSS produced (with default values on breakpoints and container widths):
#media (min-width: 576px) {
.my-custom-class {
max-width: 540px;
}
}
#media (min-width: 768px) {
.my-custom-class {
max-width: 720px;
}
}
#media (min-width: 992px) {
.my-custom-class {
max-width: 960px;
}
}
#media (min-width: 1200px) {
.my-custom-class {
max-width: 1140px;
}
}

the media condition repeat in each column

hi I"m working in one project, and i have create media condition for my column in Sass.
this the code
// for Mobile media - 320px width
#mixin mobile{
#media only screen and (max-width:767px){
width: 300px;
}
}
and this my loop for my column
#for $col from 1 through $grid-cols{
.col-#{$col}{
#include mobile;
}
}
and my $grid-cols = 12
so this my css output
#media only screen and (max-width: 767px) {
.col-1 {
width: 300px; } }
#media only screen and (max-width: 767px) {
.col-2 {
width: 300px; } }
etc... till .co-12
i need my output like this
#media only screen and (max-width: 767px) {
.col-1, .col-2 {width:300px;}
please, any hint
I think you will need to use a SASS placeholder in order to achieve that output. Replace your mixin:
#mixin mobile{
#media only screen and (max-width:767px){
width: 300px;
}
}
with a placeholder:
%mobile {
#media only screen and (max-width:767px){
width: 300px;
}
}
and call it with the #extend %mobile; instead of #include mobile; in your loop.
See this article for a very nice explanation on differences between mixins and placeholders.

Avoiding multiple "#media" when using Bootstrap 3 less mixins

When using less mixins to build a Website with Bootstrap I do something like this:
#logo {
.make-sm-column(3);
.make-md-column(3);
.make-lg-column(3);
}
#menu {
.make-sm-column(5);
.make-md-column(5);
.make-lg-column(5);
}
This looks very neat in the .less file but it does bloat up the compiled css a lot, isn't it?
Every class and id with such a mixin gets it's own set of media-queries:
#media (min-width: 768px) {
#logo {
float: left;
width: 25%;
}
}
#media (min-width: 992px) {
#logo {
float: left;
width: 25%;
}
}
#media (min-width: 1200px) {
#logo {
float: left;
width: 25%;
}
}
#media (min-width: 768px) {
#menu {
float: left;
width: 41.66666666666667%;
}
}
#media (min-width: 992px) {
#menu {
float: left;
width: 41.66666666666667%;
}
}
#media (min-width: 1200px) {
#menu {
float: left;
width: 41.66666666666667%;
}
}
This gets repeated for every class/id with the column-mixin. I think it would be more elegant and more effective to combine these definitions in 3 media-query blocks.
Is there a way I can do this (semi-)automatically.
I am using Windows and compiling with WinLess at the moment, but havent found such an option.
There's .make-xs-column mixin in current Bootstrap version, it generates the same CSS without any media queries.
Little late, but if you note the min-width in those media queries, you don't need to make the medium and large columns if they're the same as the small. You only need to specify the medium and large columns if they're different than your small columns. This is all you need to do:
#logo {
.make-sm-column(3);
}
#menu {
.make-sm-column(5);
}
That will output the minimal amount of code to get your desired layout.

Resources