Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

access SASS values ($colors from variables.scss) in Typescript (Angular2 ionic2)

In Ionic 2, I would like to access the $colors variables from the file "[my project]\src\theme\variables.scss".

This file contains:

$colors: (   primary:    #387ef5,   secondary:  #32db64,   danger:     #f53d3d,   light:      #f4f4f4,   dark:       #222,   favorite:   #69BB7B ); 

In a component, I draw a canvas. It looks like that:

import {Component, Input, ViewChild, ElementRef} from '@angular/core';  @Component({     selector: 'my-graph', }) @View({     template: `<canvas #myGraph class='myGraph'      [attr.width]='_size'      [attr.height]='_size'></canvas>`, })  export class MyGraphDiagram {     private _size: number;      // get the element with the #myGraph on it     @ViewChild("myGraph") myGraph: ElementRef;       constructor(){         this._size = 150;     }      ngAfterViewInit() { // wait for the view to init before using the element        let context: CanvasRenderingContext2D = this.myGraph.nativeElement.getContext("2d");       // HERE THE COLOR IS DEFINED AND I D LIKE TO ACCESS variable.scss TO DO THAT       context.fillStyle = 'blue';       context.fillRect(10, 10, 150, 150);     }  } 

As one can see, at some point in this code the color of the shape is defined: context.fillStyle = 'blue' , I would like to use instead something like context.fillStyle = '[variables.scss OBJECT].$colors.primary '.

Has anyone an idea?

like image 804
nyluje Avatar asked Nov 04 '16 09:11

nyluje


People also ask

Can I use typescript variable in SCSS?

Sometimes you need to share variables between CSS (or SCSS) and Typescript, for example, if you have a list of colors in your SCSS file and need to check the variable names in typescript to be sure is an available color.

How do I color a variable in SCSS?

$color-red: #FF0000; $color-green: #00FF00; $color-blue: #0000FF; Remember, in order to use variables, or any of the benefits of SCSS for that matter, the stylesheet must have the '. scss' extension, and a preprocessor must be part of your website build system.

What is the correct way to define a variable in Sass primary color?

Sass variables are simple: you assign a value to a name that begins with $ , and then you can refer to that name instead of the value itself.

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.


2 Answers

Unfortunately, there is no way to access SASS variable directly from typescript/javascript code. However, we can make a workaround to access those variables.

Let me describe briefly the steps to access SASS variables from within typescript source code:

1. Creating a SASS Helper Component

Create ../providers/sass-helper/sass-helper.component.scss:

$prefix: "--"; //Prefix string for custom CSS properties  //Merges a variable name with $prefix @function custom-property-name($name) {     @return $prefix + $name; }  // Defines a custom property @mixin define-custom-property($name, $value) {     #{custom-property-name($name)}: $value; }  body {     // Append pre-defined colors in $colors:     @each $name, $value in $colors {         @include define-custom-property($name, $value);     }      // Append SASS variables which are desired to be accesible:     @include define-custom-property('background-color', $background-color); } 

In this SCSS file, we simply create custom properties inside the body section of the DOM. You should add each SASS variable that you want to be accessible into this SCSS file by using the mixin called define-custom-property which expects two parameters: variable name and variable value.

As an example, I have added entries for all the colors defined in $colors as well as an entry for the SASS variable $background-color defined in my theme/variables.scss file. You can add as many variables as you wish.

Create ../providers/sass-helper/sass-helper.component.ts:

import { Component } from '@angular/core';  export const PREFIX = '--';  @Component({     selector: 'sass-helper',     template: '<div></div>' }) export class SassHelperComponent {      constructor() {      }      // Read the custom property of body section with given name:     readProperty(name: string): string {         let bodyStyles = window.getComputedStyle(document.body);         return bodyStyles.getPropertyValue(PREFIX + name);     } } 

2. Integrating SASS Helper Component

From now on, we can follow standard Ionic2 framework principles for component integration and usage.

  • Add the component class name (SassHelperComponent) into the declarations section of your NgModule in app.module.ts
  • Insert the following HTML code into the HTML template of your page from where you want to access those magic variables:

    <sass-helper></sass-helper>


3. Using Helper Component

In your page's TS file, you should insert the following lines into your page class:

@ViewChild(SassHelperComponent) private sassHelper: SassHelperComponent; 

Finally, you can read the value of any SASS variable by just calling the child class method as follows:

// Read $background-color: this.sassHelper.readProperty('background-color');  // Read primary: this.sassHelper.readProperty('primary'); 
like image 77
Mete Cantimur Avatar answered Nov 11 '22 18:11

Mete Cantimur


One possibility is to generate a .ts file from the .scss file. A simple example of this process:

1) Install npm i --save-dev scss-to-json.

2) Put this in your package.json:

  "scripts": {     ...     "scss2json": "echo \"export const SCSS_VARS = \" > src/app/scss-variables.generated.ts && scss-to-json src/variables.scss >> src/app/scss-variables.generated.ts"   }, 

and run it with npm run scss2json. Windows users will need to adjust the example.

3) Access the variables:

import {SCSS_VARS} from './scss-variables.generated'; ... console.log(SCSS_VARS['$color-primary-1']); 

One advantage of this is, that you'll get type completion from IDE's and it's a quite simple means to achieve your goal in general.

Of course you could make this more advanced, for example by making the generated file read only and by putting the script into it's own .js file and make it work on every OS.

like image 35
bersling Avatar answered Nov 11 '22 17:11

bersling