Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to use CSS variables in Twitter-bootstrap 4 $theme-colors array?

In bootstrap 4 you can define and/or override default colors using the following array: (as documented here)

$theme-colors: (
    "primary": #001122, /*override*/
    "color-1": red, /*new color*/
    "color-2": black, /*new color*/
    "color-3": white /*new color*/
);

I want to make custom theme colors for different users. Users can choose different color palettes which I have defined based on the class of the body.

I made a new file to make my own styles, defining my theme colors in CSS variables in the body tag:

body {
  &.color-pallette-red {
    --theme-color-1: red;
    --theme-color-2: black;
    --theme-color-3: white;

    color: var(--theme-color-1); /*red*/
  }

  &.color-pallette-yellow {
    --theme-color-1: yellow;
    --theme-color-2: black;
    --theme-color-3: white;

    color: var(--theme-color-1); /*yellow*/
  }
}

But in this way, the bootstrap colors are of course not overwritten...

I tried to paste my CSS variables in the bootstrap array mentioned earlier, to make sure that bootstrap used my colors:

$theme-colors: (
    "color-1": var(--theme-color-1),
    "color-2": var(--theme-color-2),
    "color-3": var(--theme-color-3)
);

But this returns Error: $color2: var(--theme-color-1) is not a color. @return mix($color-base, $color, $level * $theme-color-interval); after running the compiling script. So bootstrap/compiler didn't recognize my CSS variables as a color...

Summarized what I want is: Change bootstrap colors based on body class. Does anyone know a way to achieve this?

like image 826
Dirk Jan Avatar asked Feb 11 '19 14:02

Dirk Jan


People also ask

Does bootstrap use CSS variables?

Use Bootstrap's CSS custom properties for fast and forward-looking design and development. Bootstrap includes around two dozen CSS custom properties (variables) in its compiled CSS, with dozens more on the way for improved customization on a per-component basis.

Can I use CSS color variables?

CSS variables have access to the DOM, which means that you can create variables with local or global scope, change the variables with JavaScript, and change the variables based on media queries. A good way to use CSS variables is when it comes to the colors of your design.

Does SCSS support CSS variables?

We are all gladly using SCSS and benefiting from its features. In addition to that, we didn't want to give up on CSS variables, because they are strong, especially when it comes to changing them in run-time, it can't be achieved using SCSS, SASS, or LESS variables.

What is Twitter Bootstrap?

Twitter Bootstrap or simply Bootstrap is an open-source HTML, CSS and JavaScript Framework that is used in front-end web development. Bootstrap has an authoritative presence in the front-end development world with hundreds of thousands of websites including some really popular website built based on the framework.

How to call bootstrap variables in Sass?

Each application has an exclusive Bootstrap module and it can be launched using Bower or NPM. After that you can call Bootstrap variables (check all the variables available in your_modules_path_here/bootstrap/_variables.scss), for example in SASS:

How to check all variables available in Bootstrap?

To check all variables available in the Bootstrap module, you can see it in /node_modules/bootstrap-sass/assets/stylesheets/bootstrap/_variables.scss or bootstrap/_variables.scss (inside your module manager path, if your are not using npm) Hope it helps! Show activity on this post.


2 Answers

I like my other answer, but I would also like to offer another solution, provided that one doesn't fit the project scopes needs. Another option, and I think more direct to your needs, is you could just cascade your style sheets. Assuming a project tree resembles the following:

`css\
  `--main.css
  `--themes.css <- compiled themes.sass
  `--themes.sass
`index.html

Where index.html:

  ...
  <head>
    <link rel="stylesheet" type="text/css" media="screen" href="css/main.css">
    <link rel="stylesheet" type="text/css" media="screen" href="css/themes.css">
  </head>

  <body>
    <main class="theme-purple">
      <h1>Hello World</h1>
      <h2>SASS is fun!</h2>
    </main>

    <main class="theme-red">
      <h1>Hello World</h1>
      <h2>SASS is fun!</h2>
    </main>
  </body>
  ...

Where main.css:

.theme-red {
  --theme-color-1: red;
  --theme-color-2: black;
  --theme-color-3: white;
}
.theme-purple {
  --theme-color-1: purple;
  --theme-color-2: cornflowerblue;
  --theme-color-3: white;
}

Where themes.sass:

@import "node_modules/bootstrap/scss/bootstrap";

$theme-colors: (
  "primary": #001122, 
  "color-1": var(--theme-color-1), 
  "color-2": var(--theme-color-2), 
  "color-3": var(--theme-color-3)
);

main { 
  background-color: theme-color("color-1");
}
h1 { 
  color: theme-color("color-2");
}
h2 { 
  color: theme-color("color-3")
}

That way your CSS variables have had a chance to be compiled. I tested on a node.js server, so you should change the import statement as needed

like image 106
soulshined Avatar answered Oct 10 '22 22:10

soulshined


Why you cannot use CSS variables for colors in SASS

The reason you are not able to use CSS variables for colors are functions like darken() and lighten() in SASS. You can imagine that the computer will not know what to do when it gets the instruction: darken( var(--color), 20%); You cannot modify a value you don't know about.

What if we just don't use functions that change colors?

In fact that should actually work. The bootstrap library has scss-files that use those functions. You could go through all the bootstrap code and remove the functions that modify colors. Of course that would be a bit of work. Updating bootstrap in the future would cause your site's styling to mysteriously crash and someone will be very mad at you. So this option is not a good idea.

But...But... If CSS can do it you can with SASS?

YES! This is the answer. And it's going to be quite a bit of work. If you set the colors using another variable, you can use a SASS variable like --color for those colors. E.g.:

  $color1: var(--color-1);

  /* It may seem completely redundant to  
     to define CSS variable here. But 
     it isn't. You can change the variables in 
     your browser now with JavaScript, which 
     may affect multiple elements.
  */
  :root{
    --color-1: purple;
  }
  /* An example on how to change the page
     styling with an id.        
  */
  :root#dark-mode{
    --color-1: black;
  }

  .alert-success{
    background-color: $color1;
  }
  .alert-danger{
    background-color: $color1;
  }

Luckily the bootstrap 4 developers have done a pretty good job at keeping their selectors simple, so it won't be too hard to overwrite. Remember to load your CSS after the bootstrap css. You may want to search the bootstrap scss files for the SASS variable you are overriding to make sure you cover all cases.

Goodluck!

like image 31
Rob Monhemius Avatar answered Oct 10 '22 20:10

Rob Monhemius