@@ -134,13 +134,9 @@ function detectDisabledThemes($mdThemingProvider) {
134
134
* {{primary-color-0.7}} - Apply 0.7 opacity to each of the above rules
135
135
* {{primary-contrast}} - Generates .md-hue-1, .md-hue-2, .md-hue-3 with configured contrast (ie. text) color shades set for each hue
136
136
* {{primary-contrast-0.7}} - Apply 0.7 opacity to each of the above rules
137
- *
138
- * Foreground expansion: Applies rgba to black/white foreground text
139
- *
140
- * {{foreground-1}} - used for primary text
141
- * {{foreground-2}} - used for secondary text/divider
142
- * {{foreground-3}} - used for disabled text
143
- * {{foreground-4}} - used for dividers
137
+ * {{primary-contrast-divider}} - Apply divider opacity to contrast color
138
+ * {{background-default-contrast}} - Apply primary text color for contrasting with default background
139
+ * {{background-50-contrast-icon}} - Apply contrast color for icon on background's shade 50 hue
144
140
*
145
141
*/
146
142
@@ -150,21 +146,14 @@ var GENERATED = { };
150
146
// In memory storage of defined themes and color palettes (both loaded by CSS, and user specified)
151
147
var PALETTES ;
152
148
153
- // Text Colors on light and dark backgrounds
149
+ // Text colors are automatically generated based on background color when not specified
150
+ // Custom palettes can provide override colors
154
151
// @see https://www.google.com/design/spec/style/color.html#color-text-background-colors
155
152
var DARK_FOREGROUND = {
156
153
name : 'dark' ,
157
- '1' : 'rgba(0,0,0,0.87)' ,
158
- '2' : 'rgba(0,0,0,0.54)' ,
159
- '3' : 'rgba(0,0,0,0.38)' ,
160
- '4' : 'rgba(0,0,0,0.12)'
161
154
} ;
162
155
var LIGHT_FOREGROUND = {
163
156
name : 'light' ,
164
- '1' : 'rgba(255,255,255,1.0)' ,
165
- '2' : 'rgba(255,255,255,0.7)' ,
166
- '3' : 'rgba(255,255,255,0.5)' ,
167
- '4' : 'rgba(255,255,255,0.12)'
168
157
} ;
169
158
170
159
var DARK_SHADOW = '1px 1px 0px rgba(0,0,0,0.4), -1px -1px 0px rgba(0,0,0,0.4)' ;
@@ -201,6 +190,34 @@ var DARK_DEFAULT_HUES = {
201
190
'hue-3' : 'A200'
202
191
}
203
192
} ;
193
+
194
+ // use inactive icon opacity from https://material.google.com/style/color.html#color-text-background-colors
195
+ // not inactive icon opacity from https://material.google.com/style/icons.html#icons-system-icons
196
+
197
+ var DARK_CONTRAST_OPACITY = {
198
+ 'icon' : 0.54 ,
199
+ 'secondary' : 0.54 ,
200
+ 'disabled' : 0.38 ,
201
+ 'hint' : 0.38 ,
202
+ 'divider' : 0.12 ,
203
+ } ;
204
+
205
+ var LIGHT_CONTRAST_OPACITY = {
206
+ 'icon' : 0.87 ,
207
+ 'secondary' : 0.7 ,
208
+ 'disabled' : 0.5 ,
209
+ 'hint' : 0.5 ,
210
+ 'divider' : 0.12
211
+ } ;
212
+
213
+ var STRONG_LIGHT_CONTRAST_OPACITY = {
214
+ 'icon' : 1.0 ,
215
+ 'secondary' : 0.7 ,
216
+ 'disabled' : 0.5 ,
217
+ 'hint' : 0.5 ,
218
+ 'divider' : 0.12
219
+ } ;
220
+
204
221
THEME_COLOR_TYPES . forEach ( function ( colorType ) {
205
222
// Color types with unspecified default hues will use these default hue values
206
223
var defaultDefaultHues = {
@@ -617,20 +634,44 @@ function parseRules(theme, colorType, rules) {
617
634
618
635
var themeNameRegex = new RegExp ( '\\.md-' + theme . name + '-theme' , 'g' ) ;
619
636
// Matches '{{ primary-color }}', etc
620
- var hueRegex = new RegExp ( '(\'|")?{{\\s*(' + colorType + ')-(color|contrast)-?(\\d\\.?\\d*)?\\s*}}(\"|\')?' , 'g' ) ;
621
- var simpleVariableRegex = / ' ? " ? \{ \{ \s * ( [ a - z A - Z ] + ) - ( A ? \d + | h u e \- [ 0 - 3 ] | s h a d o w | d e f a u l t ) - ? ( \d \. ? \d * ) ? ( c o n t r a s t ) ? \s * \} \} ' ? " ? / g;
637
+ var hueRegex = new RegExp ( '(?: \'|")?{{\\s*(' + colorType + ')-? (color|default)?-?( contrast)? -?((?: \\d\\.?\\d*)|(?:[a-zA-Z]+) )?\\s*}}(\"|\')?' , 'g' ) ;
638
+ var simpleVariableRegex = / ' ? " ? \{ \{ \s * ( [ a - z A - Z ] + ) - ( A ? \d + | h u e \- [ 0 - 3 ] | s h a d o w | d e f a u l t ) - ? ( c o n t r a s t ) ? - ? ( (?: \d \. ? \d * ) | (?: [ a - z A - Z ] + ) ) ? \s * \} \} ' ? " ? / g;
622
639
var palette = PALETTES [ color . name ] ;
640
+ var defaultBgHue = theme . colors [ 'background' ] . hues [ 'default' ] ;
641
+ var defaultBgContrastType = PALETTES [ theme . colors [ 'background' ] . name ] [ defaultBgHue ] . contrastType ;
623
642
624
643
// find and replace simple variables where we use a specific hue, not an entire palette
625
644
// eg. "{{primary-100}}"
626
645
//\(' + THEME_COLOR_TYPES.join('\|') + '\)'
627
- rules = rules . replace ( simpleVariableRegex , function ( match , colorType , hue , opacity , contrast ) {
646
+ rules = rules . replace ( simpleVariableRegex , function ( match , colorType , hue , contrast , opacity ) {
647
+ var regexColorType = colorType ;
628
648
if ( colorType === 'foreground' ) {
629
649
if ( hue == 'shadow' ) {
630
650
return theme . foregroundShadow ;
631
- } else {
632
- return theme . foregroundPalette [ hue ] || theme . foregroundPalette [ '1' ] ;
651
+ } else if ( theme . foregroundPalette [ hue ] ) {
652
+ // Use user defined palette number (ie: foreground-2)
653
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ hue ] ) ) ;
654
+ } else if ( theme . foregroundPalette [ '1' ] ) {
655
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ '1' ] ) ) ;
656
+ }
657
+ // Default to background-default-contrast-{opacity}
658
+ colorType = 'background' ;
659
+ contrast = 'contrast' ;
660
+ if ( ! opacity && hue ) {
661
+ // Convert references to legacy hues to opacities (ie: foreground-4 to *-divider)
662
+ switch ( hue ) {
663
+ // hue-1 uses default opacity
664
+ case '2' :
665
+ opacity = 'secondary' ;
666
+ break ;
667
+ case '3' :
668
+ opacity = 'disabled' ;
669
+ break ;
670
+ case '4' :
671
+ opacity = 'divider' ;
672
+ }
633
673
}
674
+ hue = 'default' ;
634
675
}
635
676
636
677
// `default` is also accepted as a hue-value, because the background palettes are
@@ -639,13 +680,51 @@ function parseRules(theme, colorType, rules) {
639
680
hue = theme . colors [ colorType ] . hues [ hue ] ;
640
681
}
641
682
642
- return rgba ( ( PALETTES [ theme . colors [ colorType ] . name ] [ hue ] || '' ) [ contrast ? 'contrast' : 'value' ] , opacity ) ;
683
+ var colorDetails = ( PALETTES [ theme . colors [ colorType ] . name ] [ hue ] || '' ) ;
684
+
685
+ // If user has specified a foreground color, use those
686
+ if ( colorType === 'background' && contrast && regexColorType !== 'foreground' && colorDetails . contrastType == defaultBgContrastType ) {
687
+ // Don't process if colorType was changed
688
+ switch ( opacity ) {
689
+ case 'secondary' :
690
+ case 'icon' :
691
+ if ( theme . foregroundPalette [ '2' ] ) {
692
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ '2' ] ) ) ;
693
+ }
694
+ break ;
695
+ case 'disabled' :
696
+ case 'hint' :
697
+ if ( theme . foregroundPalette [ '3' ] ) {
698
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ '3' ] ) ) ;
699
+ }
700
+ break ;
701
+ case 'divider' :
702
+ if ( theme . foregroundPalette [ '4' ] ) {
703
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ '4' ] ) ) ;
704
+ }
705
+ break ;
706
+ default :
707
+ if ( theme . foregroundPalette [ '1' ] ) {
708
+ return rgba ( colorToRgbaArray ( theme . foregroundPalette [ '1' ] ) ) ;
709
+ }
710
+ break ;
711
+ }
712
+ }
713
+
714
+ if ( contrast && opacity ) {
715
+ opacity = colorDetails . opacity [ opacity ] || opacity ;
716
+ }
717
+
718
+ return rgba ( colorDetails [ contrast ? 'contrast' : 'value' ] , opacity ) ;
643
719
} ) ;
644
720
645
721
// For each type, generate rules for each hue (ie. default, md-hue-1, md-hue-2, md-hue-3)
646
722
angular . forEach ( color . hues , function ( hueValue , hueName ) {
647
723
var newRule = rules
648
- . replace ( hueRegex , function ( match , _ , colorType , hueType , opacity ) {
724
+ . replace ( hueRegex , function ( match , colorType , hueType , contrast , opacity ) {
725
+ if ( contrast && opacity ) {
726
+ opacity = palette [ hueValue ] . opacity [ opacity ] || opacity ;
727
+ }
649
728
return rgba ( palette [ hueValue ] [ hueType === 'color' ? 'value' : 'contrast' ] , opacity ) ;
650
729
} ) ;
651
730
if ( hueName !== 'default' ) {
@@ -756,6 +835,37 @@ function generateAllThemes($injector, $mdTheming) {
756
835
delete palette . contrastStrongLightColors ;
757
836
delete palette . contrastDarkColors ;
758
837
838
+ function getContrastType ( hueName ) {
839
+ if ( defaultContrast === 'light' ? darkColors . indexOf ( hueName ) !== - 1 : lightColors . indexOf ( hueName ) === - 1 ) {
840
+ return 'dark' ;
841
+ }
842
+ if ( strongLightColors . indexOf ( hueName ) !== - 1 ) {
843
+ return 'strongLight' ;
844
+ }
845
+ return 'light' ;
846
+ }
847
+ function getContrastColor ( contrastType ) {
848
+ switch ( contrastType ) {
849
+ default :
850
+ case 'strongLight' :
851
+ return STRONG_LIGHT_CONTRAST_COLOR ;
852
+ case 'light' :
853
+ return LIGHT_CONTRAST_COLOR ;
854
+ case 'dark' :
855
+ return DARK_CONTRAST_COLOR ;
856
+ }
857
+ }
858
+ function getOpacityValues ( contrastType ) {
859
+ switch ( contrastType ) {
860
+ default :
861
+ case 'strongLight' :
862
+ return STRONG_LIGHT_CONTRAST_OPACITY ;
863
+ case 'light' :
864
+ return LIGHT_CONTRAST_OPACITY ;
865
+ case 'dark' :
866
+ return DARK_CONTRAST_OPACITY ;
867
+ }
868
+ }
759
869
// Change { 'A100': '#fffeee' } to { 'A100': { value: '#fffeee', contrast:DARK_CONTRAST_COLOR }
760
870
angular . forEach ( palette , function ( hueValue , hueName ) {
761
871
if ( angular . isObject ( hueValue ) ) return ; // Already converted
@@ -768,27 +878,13 @@ function generateAllThemes($injector, $mdTheming) {
768
878
. replace ( '%3' , hueName ) ) ;
769
879
}
770
880
881
+ var contrastType = getContrastType ( hueName ) ;
771
882
palette [ hueName ] = {
772
883
value : rgbValue ,
773
- contrast : getContrastColor ( )
884
+ contrastType : contrastType ,
885
+ contrast : getContrastColor ( contrastType ) ,
886
+ opacity : getOpacityValues ( contrastType )
774
887
} ;
775
- function getContrastColor ( ) {
776
- if ( defaultContrast === 'light' ) {
777
- if ( darkColors . indexOf ( hueName ) > - 1 ) {
778
- return DARK_CONTRAST_COLOR ;
779
- } else {
780
- return strongLightColors . indexOf ( hueName ) > - 1 ? STRONG_LIGHT_CONTRAST_COLOR
781
- : LIGHT_CONTRAST_COLOR ;
782
- }
783
- } else {
784
- if ( lightColors . indexOf ( hueName ) > - 1 ) {
785
- return strongLightColors . indexOf ( hueName ) > - 1 ? STRONG_LIGHT_CONTRAST_COLOR
786
- : LIGHT_CONTRAST_COLOR ;
787
- } else {
788
- return DARK_CONTRAST_COLOR ;
789
- }
790
- }
791
- }
792
888
} ) ;
793
889
}
794
890
}
0 commit comments