Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Angular 6 library shared stylesheets

How can you setup a index.scss and import global stylesheets for variables, mixins, etc, to an angular 6 library?

Angular CLI generates a lib with a root component & component scss, but the styles added or imported to the root component are not available to children components. Which makes sense by default to encapsulate the styles, but I just can't find any information or examples on how to set this up yet.

The angular.json "styles": [...] paths that can be used for this with "projectType": "application", don't seem to work with "projectType": "library" either.

Thanks in advance for your help!


UPDATE: My project was initiated using angular cli v6.0.5, following this guide: https://medium.com/@tomsu/how-to-build-a-library-for-angular-apps-4f9b38b0ed11

TL;DR for the guide:

ng new my-app --style=scss ng generate library my-library --prefix ml 

This is the file structure angular 6 generates:

    my-app       projects/         my-library/           src/             lib/               shared/..               widgets/..               my-library.component.ts               my-library.module.ts             sass/               _variables.scss               styles.scss // <<< This is where I want to `@import 'variables';`, and for it to be available in all the components of the "my-library" project.             public_api.ts       src/         app/           app.module.ts // << imports projects/my-library/lib/my-library.module as "my-library".         main.ts         index.scss         index.html       README.md 

Package Versions:

    Angular CLI: 6.0.5     Node: 10.2.1     OS: darwin x64     Angular: 6.0.3     ... animations, common, compiler, compiler-cli, core, forms     ... http, language-service, platform-browser     ... platform-browser-dynamic, router      Package                            Version     ------------------------------------------------------------     @angular-devkit/architect          0.6.5     @angular-devkit/build-angular      0.6.5     @angular-devkit/build-ng-packagr   0.6.5     @angular-devkit/build-optimizer    0.6.5     @angular-devkit/core               0.6.5     @angular-devkit/schematics         0.6.5     @angular/cli                       6.0.5     @ngtools/json-schema               1.1.0     @ngtools/webpack                   6.0.5     @schematics/angular                0.6.5     @schematics/update                 0.6.5     ng-packagr                         3.0.0     rxjs                               6.2.0     typescript                         2.7.2     webpack                            4.8.3 
like image 868
xaunlopez Avatar asked May 29 '18 10:05

xaunlopez


People also ask

Which stylesheet format for angular is best?

Angular applications are styled with standard CSS. That means you can apply everything you know about CSS stylesheets, selectors, rules, and media queries directly to Angular applications. Additionally, Angular can bundle component styles with components, enabling a more modular design than regular stylesheets.

Is ng-deep deprecated?

The documentation at https://angular.io/guide/component-styles states this about :ng-deep : The shadow-piercing descendant combinator is deprecated and support is being removed from major browsers and tools.

Where is the path of your custom angular library defined?

Let us first find out the default Angular Component Library that has been created. We can go to project/dist/angular-components-library/lib/ angular-components-library-module.


2 Answers

For global styles, I've answered it in this question.

Update

For ng-packgr versions 9.x and above

Copying assest to output folder is now directly supported as explained in this page

{   "$schema": "./node_modules/ng-packagr/package.schema.json",   "name": "@my/library",   "version": "1.0.0",   "ngPackage": {     "assets": [       "CHANGELOG.md",       "./styles/**/*.theme.scss"     ],     "lib": {       ...     }   } } 

Old Answer

**For other versions**
  1. Create an index.scss file in your library's root folder. If you follow this guide from Angular, then your path will be my-project/projects/my-library/index.scss. This is also the folder where your package.json is.

So, index.scss will be the file with your variables and mixins

$grey: #222; @mixin mymixin {     background: #222; } 
  1. Include this in you library scss files using import
@import '../../index.scss'; 

or whatever relative path your component scss file is at.

  1. Now in order to have this file in your app project, copy it post build to the dist directory. To do this, edit your angular library's project's package.json file (NOT THE LIBRARY'S).
{     "name": "my-project",     "version": "1.0.0",     "scripts": {         "ng": "ng",         "start": "ng serve",         "build": "ng build && npm run copyScss",         "test": "ng test",         "lint": "ng lint",         "e2e": "ng e2e",         "copyScss": "xcopy \"projects\my-library\index.scss\" \"dist\\my-library\\\""     },      ... } 
  1. Now, very important, DO NOT use ng build to build your library, instead use npm run build. This will automatically execute the copy command. Now the index.scss file is exported along with your library in the my-project/dist folder.

  2. Include the index.scss in your app project's scss files

// ~ stands for the node_modules folder @import '~my-library/index.scss'; 

Now you have all your library mixins in all of the projects you installed your library.

Cheers!

PS Workarounds are not the most elegant solutions, but when nothing else works, they work around!

like image 150
Xpleria Avatar answered Sep 25 '22 04:09

Xpleria


Have you tried setting the encapsulation level of the component to none as part of the component metadata? Like this:

@Component({   selector: 'app-component',   templateUrl: './app.component.html',   styleUrls: ['./app.component.scss'],   encapsulation: ViewEncapsulation.None }) 

The ViewEncapsulation levels are:

  • ViewEncapsulation.Emulated: The default, Angular emulates a Shadow DOM.
  • ViewEncapsulation.Native: Use the browser's own Shadow DOM.
  • ViewEncapsulation.None: Styles are Global

Check out the Angular Docs on ViewEncapsulation and I wrote a blog post on it.

like image 39
JeffryHouser Avatar answered Sep 23 '22 04:09

JeffryHouser