66 * found in the LICENSE file at https://angular.dev/license
77 */
88
9- import { Rule , SchematicContext } from '@angular-devkit/schematics' ;
9+ import { chain , Rule , SchematicContext } from '@angular-devkit/schematics' ;
1010import {
1111 createMigrationSchematicRule ,
1212 NullableDevkitMigration ,
@@ -22,14 +22,72 @@ const materialMigrations: NullableDevkitMigration[] = [
2222 ExplicitSystemVariablePrefixMigration ,
2323] ;
2424
25- /** Entry point for the migration schematics with target of Angular Material v19 */
25+ /** Entry point for the migration schematics with target of Angular Material v20 */
2626export function updateToV20 ( ) : Rule {
27- return createMigrationSchematicRule (
28- TargetVersion . V20 ,
29- materialMigrations ,
30- materialUpgradeData ,
31- onMigrationComplete ,
32- ) ;
27+ return chain ( [
28+ createMigrationSchematicRule (
29+ TargetVersion . V20 ,
30+ materialMigrations ,
31+ materialUpgradeData ,
32+ onMigrationComplete ,
33+ ) ,
34+ renameMdcTokens ( ) ,
35+ renameComponentTokens ( ) ,
36+ ] ) ;
37+ }
38+
39+ // Renames any CSS variables beginning with "--mdc-" to be "--mat-". These CSS variables
40+ // refer to tokens that used to be derived from a mix of MDC and Angular. Now all the tokens
41+ // are converged on being prefixed "--mat-".
42+ function renameMdcTokens ( ) : Rule {
43+ return tree => {
44+ tree . visit ( path => {
45+ const content = tree . readText ( path ) ;
46+ const updatedContent = content . replace ( '--mdc-' , '--mat-' ) ;
47+ tree . overwrite ( path , updatedContent ) ;
48+ } ) ;
49+ } ;
50+ }
51+
52+ // Renames Angular Material component token CSS variables that were renamed so that the base
53+ // component's name came first or otherwise renamed to match our terminology instead of MDC's.
54+ function renameComponentTokens ( ) : Rule {
55+ const tokenPrefixes = [
56+ { old : '--mat-circular-progress' , replacement : '--mat-progress-spinner' } ,
57+ { old : '--mat-elevated-card' , replacement : '--mat-card-elevated' } ,
58+ { old : '--mat-extended-fab' , replacement : '--mat-fab-extended' } ,
59+ { old : '--mat-filled-button' , replacement : '--mat-button-filled' } ,
60+ { old : '--mat-filled-text-field' , replacement : '--mat-form-field-filled' } ,
61+ { old : '--mat-full-pseudo-checkbox' , replacement : '--mat-pseudo-checkbox-full' } ,
62+ { old : '--mat-legacy-button-toggle' , replacement : '--mat-button-toggle-legacy' } ,
63+ { old : '--mat-linear-progress' , replacement : '--mat-progress-bar' } ,
64+ { old : '--mat-minimal-pseudo-checkbox' , replacement : '--mat-pseudo-checkbox-minimal' } ,
65+ { old : '--mat-outlined-button' , replacement : '--mat-button-outlined' } ,
66+ { old : '--mat-outlined-card' , replacement : '--mat-card-outlined' } ,
67+ { old : '--mat-outlined-text-field' , replacement : '--mat-form-field-outlined' } ,
68+ { old : '--mat-plain-tooltip' , replacement : '--mat-tooltip' } ,
69+ { old : '--mat-protected-button' , replacement : '--mat-button-protected' } ,
70+ { old : '--mat-secondary-navigation-tab' , replacement : '--mat-tab' } ,
71+ { old : '--mat-standard-button-toggle' , replacement : '--mat-button-toggle' } ,
72+ { old : '--mat-switch' , replacement : '--mat-slide-toggle' } ,
73+ { old : '--mat-tab-header' , replacement : '--mat-tab' } ,
74+ { old : '--mat-tab-header-with-background' , replacement : '--mat-tab' } ,
75+ { old : '--mat-tab-indicator' , replacement : '--mat-tab' } ,
76+ { old : '--mat-text-button' , replacement : '--mat-button-text' } ,
77+ { old : '--mat-tonal-button' , replacement : '--mat-button-tonal' } ,
78+ ] ;
79+ return tree => {
80+ tree . visit ( path => {
81+ const content = tree . readText ( path ) ;
82+ let updatedContent = content ;
83+ for ( const tokenPrefix of tokenPrefixes ) {
84+ updatedContent = updatedContent . replace ( tokenPrefix . old , tokenPrefix . replacement ) ;
85+ }
86+ if ( content !== updatedContent ) {
87+ tree . overwrite ( path , updatedContent ) ;
88+ }
89+ } ) ;
90+ } ;
3391}
3492
3593/** Function that will be called when the migration completed. */
0 commit comments