Skip to content

docs: clean up and clarify theming docs #13435

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Oct 5, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
119 changes: 69 additions & 50 deletions guides/theming-your-components.md
Original file line number Diff line number Diff line change
@@ -1,80 +1,99 @@
# Theming your custom components
In order to style your own components with Angular Material's tooling, the component's styles must be defined with Sass.
### Theming your custom component with Angular Material's theming system
In order to style your own components with Angular Material's tooling, the component's styles must
be defined with Sass.

### Using `@mixin` to automatically apply a theme

#### Why using `@mixin`
The advantage of using a `@mixin` function is that when you change your theme, every file that uses it will be automatically updated.
Calling the `@mixin` with a different theme argument allows multiple themes within the app or component.

#### How to use `@mixin`
We can better theme our custom components by adding a `@mixin` function to its theme file, and then call this function to apply a theme.

All you need is to create a `@mixin` function in the custom-component-theme.scss
#### 1. Define all color and typography styles in a "theme file" for the component
First, create a Sass mixin that accepts an Angular Material theme and outputs the color-specific
styles for the component. An Angular Material theme definition is a Sass map.

For example, if building a custom carousel component:
```scss
// Import all the tools needed to customize the theme and extract parts of it
// Import library functions for theme creation.
@import '~@angular/material/theming';

// Define a mixin that accepts a theme and outputs the color styles for the component.
// Define a mixin that accepts a theme and outputs the theme-specific styles.
@mixin candy-carousel-theme($theme) {
// Extract whichever individual palettes you need from the theme.
// Extract the palettes you need from the theme definition.
$primary: map-get($theme, primary);
$accent: map-get($theme, accent);

// Use mat-color to extract individual colors from a palette as necessary.
// Define any styles affected by the theme.
.candy-carousel {
// Use mat-color to extract individual colors a palette.
background-color: mat-color($primary);
border-color: mat-color($accent, A400);
}
}
```
Now you just have to call the `@mixin` function to apply the theme:

```scss
// Import a pre-built theme
@import '~@angular/material/prebuilt-themes/deeppurple-amber.css';
// Import your custom input theme file so you can call the custom-input-theme function
@import 'app/candy-carousel/candy-carousel-theme.scss';
Second, create another Sass mixin that accepts an Angular Material typography definition and outputs
typographic styles. For example:

// Using the $theme variable from the pre-built theme you can call the theming function
@include candy-carousel-theme($theme);
```scss
@mixin candy-caroursel-typography($config) {
.candy-carousel {
font: {
family: mat-font-family($config, body-1);
size: mat-font-size($config, body-1);
weight: mat-font-weight($config, body-1);
}
}
}
```

For more details about the theming functions, see the comments in the
[source](https://github.com/angular/material2/blob/master/src/lib/core/theming/_theming.scss).
See the [typography guide](https://material.angular.io/guide/typography) for more information on
typographic customization.

#### Best practices using `@mixin`
When using `@mixin`, the theme file should only contain the definitions that are affected by the passed-in theme.
#### 2. Define all remaining styles in a normal component stylesheet.
Define all styles unaffected by the theme in a separate file referenced directly in the component's
`styleUrl`. This generally includes everything except for color and typography styles.

All styles that are not affected by the theme should be placed in a `candy-carousel.scss` file.
This file should contain everything that is not affected by the theme like sizes, transitions...

Styles that are affected by the theme should be placed in a separated theming file as
`_candy-carousel-theme.scss` and the file should have a `_` before the name. This file should
contain the `@mixin` function responsible for applying the theme to the component.
#### 3. Include the theme mixin in your application
Use the Sass `@include` keyword to include a component's theme mixin wherever you're already
including Angular Material's built-in theme mixins.

```scss
// Import library functions for theme creation.
@import '~@angular/material/theming';

// Include non-theme styles for core.
@include mat-core();

// Define your application's custom theme.
$primary: mat-palette($mat-indigo);
$accent: mat-palette($mat-pink, A200, A100, A400);
$theme: mat-light-theme($primary, $accent);

// Include theme styles for Angular Material components.
@include angular-material-theme($theme);

// Include theme styles for your custom components.
@include candy-carousel-theme($theme);
```

### Using colors from a palette
You can consume the theming functions and Material palette variables from
`@angular/material/theming`. You can use the `mat-color` function to extract a specific color
from a palette. For example:

#### Note: using the `mat-color` function to extract colors from a palette
You can consume the theming functions and Material Design color palettes from
`@angular/material/theming`. The `mat-color` Sass function extracts a specific color from a palette.
For example:

```scss
// Import theming functions
@import '~@angular/material/theming';
// Import your custom theme
@import 'src/unicorn-app-theme.scss';

// Use mat-color to extract individual colors from a palette as necessary.
// The hue can be one of the standard values (500, A400, etc.), one of the three preconfigured
// hues (default, lighter, darker), or any of the aforementioned prefixed with "-contrast".
// For example a hue of "darker-contrast" gives a light color to contrast with a "darker" hue.
// Note that quotes are needed when using a numeric hue with the "-contrast" modifier.
// Available color palettes: https://material.io/design/color/

.candy-carousel {
background-color: mat-color($candy-app-primary);
border-color: mat-color($candy-app-accent, A400);
color: mat-color($candy-app-primary, '100-contrast');
// Get the default hue for a palette.
color: mat-color($primary);

// Get a specific hue for a palette.
// See https://material.io/archive/guidelines/style/color.html#color-color-palette for hues.
background-color: mat-color($accent, 300);

// Get a relative color for a hue ('lighter' or 'darker')
outline-color: mat-color($accent, lighter);

// Get a constrast color for a hue by adding `-contrast` to any other key.
border-color: mat-color($primary, '100-constrast');
}
```
11 changes: 3 additions & 8 deletions guides/theming.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ ensures that the proper theme background is applied to your page.
When you want more customization than a pre-built theme offers, you can create your own theme file.

A custom theme file does two things:
1. Imports the `mat-core()` sass mixin. This includes all common styles that are used by multiple
1. Imports the `mat-core()` Sass mixin. This includes all common styles that are used by multiple
components. **This should only be included once in your application.** If this mixin is included
multiple times, your application will end up with multiple copies of these common styles.
2. Defines a **theme** data structure as the composition of multiple palettes. This object can be
Expand Down Expand Up @@ -104,8 +104,8 @@ node-sass src/unicorn-app-theme.scss dist/unicorn-app-theme.css
```
and then include the output file in your index.html.

The theme file **should not** be imported into other SCSS files. This will cause duplicate styles
to be written into your CSS output. If you want to consume the theme definition object
Your custom theme file **should not** be imported into other SCSS files. This will duplicate styles
in your CSS output. If you want to consume your theme definition object
(e.g., `$candy-app-theme`) in other SCSS files, then the definition of the theme object should be
broken into its own file, separate from the inclusion of the `mat-core` and
`angular-material-theme` mixins.
Expand Down Expand Up @@ -214,8 +214,3 @@ $candy-app-theme: mat-light-theme($candy-app-primary, $candy-app-accent);
### Theming your own components
For more details about theming your own components,
see [theming-your-components.md](./theming-your-components.md).

### Future work
* Once CSS variables (custom properties) are available in all the browsers we support,
we will explore how to take advantage of them to make theming even simpler.
* More prebuilt themes will be added as development continues.