Sass制定组件库全局变量

deep-merge定义主题色

packages/theme/src/common/var.scss

1/** map是sass内置的方法,使用前需要先引入 */
2@use "sass:map";
3
4/** 定义colors变量存储主题色,初始化默认值为空,并设置属性 !default */
5$colors: () !default;
6
7// 使用sass合并对象方法 map.deep-merge,将两个值合并再重新赋值给$colors
8$colors: map.deep-merge(
9    (
10        'white': #ffffff,                // 白色
11        'black': #000000,                // 黑色
12        'primary': ( 'base': #3069ff ),  // 主要
13        'success': ( 'base': #14cd70 ),  // 成功
14        'warning': ( 'base': #ffa81a ),  // 警告
15        'error': ( 'base': #ff4a5b ),   // 错误
16    ),
17    $colors
18);
19
20// 色调
21// 使用sass的map.get对象设置主题色
22$color-white: map.get($colors, 'white') !default;
23$color-black: map.get($colors, 'black') !default;
24$color-primary: map.get($colors, 'primary', 'base') !default;
25$color-success: map.get($colors, 'success', 'base') !default;
26$color-warning: map.get($colors, 'warning', 'base') !default;
27$color-error: map.get($colors, 'error', 'base') !default;

mix生成主题色层次

1 定义@mixin方法

packages/theme/src/common/var.scss

1// type
2$types: primary, success, warning, error;
3
4/** 
5*   mixin 设置颜色层次 
6*   $type 类型:primary, success, warning, error
7*   $number 百分比计算值
8*   $mode 标识
9*   $mix-color 混合种颜色
10*/
11@mixin set-color-level($type, $number, $mode: 'light', $mix-color) {
12    $colors: map.deep-merge(
13        (
14            $type: (
15                '#{$mode}-#{$number}': mix(
16                    $mix-color, 
17                    map.get($colors, $type, 'base'), 
18                    $number * 10
19                ),
20            ),
21        ),
22        $colors
23    ) !global;
24}

2 each、for:循环生成层次色调

packages/theme/src/common/var.scss

1// 生成层次颜色
2// 使用 @each 方法循环 types
3@each $type in $types {
4    // 在@each每一次循环中再使用@for循环9次
5    @for $i from 1 through 9 {
6      	// 自动生成不同主题色调的层次颜色
7        @include set-color-level($type, $i, 'light', $color-white);
8    }
9}

定义中性色及其它元素

packages/theme/src/common/var.scss

1/** 中性色 */
2$neutral-color: () !default;
3$neutral-color: map.deep-merge(
4    (
5        'light-1': #212226,
6        'light-2': #4d5059,
7        'light-3': #7c808c,
8        'light-4': #abb1bf,
9        'light-5': #c9cdd9,
10        'light-6': #e2e6f1,
11        'light-7': #ebeef5,
12        'light-8': #f5f6fa,
13        'light-9': #fafbff,
14    ),
15    $neutral-color
16);
17
18/** 文字颜色 */
19$text-color: () !default;
20$text-color: map.deep-merge(
21    (
22        'primary': #4d5059,      // 文字主色
23        'secondary': #7c808c,    // 文字辅色
24        'disabled': #abb1bf,     // 文字禁用
25        'placeholder': #c9cdd9,  // 文字占位
26        'light-8': #f5f6fa,      // 文字占位
27        'light-9': #fafbff,      // 文字占位
28    ),
29    $text-color
30);
31
32
33/** 文字尺寸 */
34$font-size: () !default;
35$font-size: map.deep-merge(
36    (
37        'small': 12px,      // 小的
38        'default': 14px,    // 默认的
39        'large': 16px,      // 大的
40    ),
41    $font-size
42);
43
44/** 边框颜色 */
45$border-color: () !default;
46$border-color: map.deep-merge(
47    (
48        'default': #e2e6f1,      // 边框主色
49        'disabled': #ebeef5,     // 边框禁用
50        'hover': #C9CDD9,        // 鼠标悬停
51        'light-8': #f5f6fa,      // 边框
52    ),
53    $border-color
54);
55
56/** 组件尺寸 */
57$component-size: () !default;
58$component-size: map.deep-merge(
59    (
60        'small': 24px,      // 小的
61        'default': 32px,    // 默认的
62        'large': 40px,      // 大的
63    ),
64    $component-size
65);

:root伪类选择器

packages/theme/src/index.scss

1@use "./initRoot.scss";

packages/theme/src/initRoot.scss

1@use "./common/var.scss" as *;
2@use "./common/mixins.scss" as *;
3:root {
4    --a-transition: .3s;
5    // 初始化
6    @include set-global-var();
7    // 主色、辅助色
8    @include set-color();
9    // 层次色
10    @include set-color-light();
11}
12@font-face {
13    font-family: 'Aileron';
14    src: url("./Aileron.otf");
15}
16body { font-family: 'Aileron'; }

packages/theme/src/button.scss

生成:root变量

定义前缀、块、修改器变量

packages/theme/src/common/config.scss

1$namespace: 'a' !default;               // 前缀
2$connect: '-' !default;                 // 块、子级
3$element-connect: '__' !default;        // 元素
4$modifier-connect: '--' !default;       // 修改器
5$modifier-value-connect: '_' !default;  // 修改器的值
6$state-prefix: 'is-' !default;          // 状态前缀,如禁用、圆角、加载等

:root变量名称的生成规则

packages/theme/src/common/function.scss

1@use "config.scss" as *;
2
3/** 组合变量名称 */
4@function createVarName($list) {
5    $name: '--' + $namespace;       // --拼接前缀
6    @each $item in $list {          // each循环
7      @if $item != '' {             // 判断不为空时执行
8        $name: $name + '-' + $item; // 开始拼接
9      }
10    }
11    @return $name;                  // 返回结果
12}

packages/theme/src/common/mixins.scss

1@use "sass:map";
2@forward "function";
3@forward "var";
4@use "function" as *;
5@use "var.scss" as *;
6@use "config.scss" as *;
7
8/** 主色、辅助色 **/
9@mixin set-color() {
10  @each $type in $types {
11    $color: map.get($colors, $type, "base"); // 获取颜色值
12    #{createVarName(('color', $type))}: #{$color}; // 产生新的变量名称
13  }
14}

生成层次色

packages/theme/src/common/mixins.scss

1@mixin set-color-light() {
2  @each $type in $types {
3    @for $i from 1 through 9 {
4        $color: map.get($colors, $type, "light-" + $i);
5        #{createVarName(('color', $type, 'light', $i))}: #{$color};
6    }
7  }
8}

获取:root变量名称

packages/theme/src/common/function.scss

1/** 获取变量名称 */
2@function getVarName($args...) {
3  @return createVarName(($args));
4}

UI组件库全局规范

packages/theme/src/common/var.scss

1/** 全局配置 */
2$global: (
3    'neutral-color': $neutral-color,           // 文字颜色
4    'text-color': $text-color,           // 文字颜色
5    'font-size': $font-size,             // 文字尺寸
6    'border-color': $border-color,       // 边框颜色
7    'component-size': $component-size,   // 组件尺寸
8    'color': $color,                     // 颜色
9    'component-round': $component-round, // 圆角
10    'padding': $padding,
11    'checkbox-size': $checkbox-size,
12    'checkbox-round': $checkbox-round,
13    'checkbox-icon-size': $checkbox-icon-size,
14    'checkbox-indeterminate-size': $checkbox-indeterminate-size,
15    'checkbox-indeterminate-round': $checkbox-indeterminate-round,
16    'radio-size': $radio-size,
17    'radio-icon-size': $radio-icon-size,
18    'gap': $gap
19);

packages/theme/src/common/mixins.scss

1@mixin set-global-var(){
2  @debug 11;
3  @each $key, $data in $global {
4    @if $data { // 判断是否存在数据
5      @each $type, $value in $data {
6        #{createVarName(($key, $type))}: #{$value};
7      }
8    }
9  }
10}

UI组件库应用规范

私有变量

packages/theme/src/common/componentVar.scss

1@use "function" as *;
2// 按钮组件配置
3@function buttonVar($type: ''){
4  $button: (
5    // 默认
6    'border-color': (
7      'default': getVarName('border-color', 'default'),
8      'type': getVarName('color', $type),
9    ),
10    'text-color': (
11      'default': getVarName('text-color', 'primary'),
12      'type': getVarName('color', 'white'),
13    ),
14    'bg-color': (
15      'default': getVarName('color', 'white'),
16      'type': getVarName('color', $type)
17    ),
18    'is-link-color': (
19      'default': getVarName('text-color', 'primary'),
20      'type': getVarName('color', $type),
21    ),
22    'is-text-color': (
23      'default': getVarName('text-color', 'primary'),
24      'type': getVarName('color', $type),
25    ),
26    'is-text-bg-color': (
27      'default': getVarName('color', 'white'),
28      'type': getVarName('color', 'white'),
29    ),
30    // 鼠标悬停
31    'hover-text-color': (
32      'default': getVarName('color', 'primary'),
33      'type': getVarName('color', 'white'),
34    ),
35    'hover-bg-color': (
36      'default': getVarName('color', 'primary', 'light-9'),
37      'type': getVarName('color', $type, 'light-3')
38    ),
39    'hover-border-color': (
40      'default': getVarName('color', 'primary', 'light-7'),
41      'type': getVarName('color', $type, 'light-3')
42    ),
43    'hover-is-link-color': (
44      'default': getVarName('text-color', 'secondary'),
45      'type': getVarName('color', $type, 'light-4')
46    ),
47    'hover-is-text-color': (
48      'default': getVarName('text-color', 'primary'),
49      'type': getVarName('color', $type),
50    ),
51    'hover-is-text-bg-color': (
52      'default': getVarName('text-color', 'light-8'),
53      'type': getVarName('color', $type, 'light-9')
54    ),
55    // 禁用
56    'disabled-text-color': (
57      'default': getVarName('text-color', 'disabled'),
58      'type': getVarName('color', 'white')
59    ),
60    'disabled-bg-color': (
61      'default': getVarName('color', 'disabled-bg'),
62      'type': getVarName('color', $type, 'light-5')
63    ),
64    'disabled-border-color': (
65      'default': getVarName('border-color', 'disabled'),
66      'type': getVarName('color', $type, 'light-5')
67    ),
68    'disabled-is-link-color': (
69      'default': getVarName('text-color', 'disabled'),
70      'type': getVarName('color', $type, 'light-5')
71    ),
72    'disabled-is-text-color': (
73      'default': getVarName('text-color', 'disabled'),
74      'type': getVarName('color', $type, 'light-5'),
75    ),
76    'disabled-is-text-bg-color': (
77      'default': getVarName('color', 'white'),
78      'type': getVarName('color', 'white')
79    ),
80    'size': (
81      'default': getVarName('component-size', 'default')
82    ),
83    'font-size': (
84      'default': getVarName('font-size', 'default')
85    ),
86    'radius': (
87      'default': getVarName('component-round', 'default')
88    ),
89    'padding': (
90      'default': getVarName('button-padding', 'default')
91    ),
92    'space': (
93      'default': getVarName('button-space', 'default')
94    )
95  );
96  @return $button;
97}

packages/theme/src/common/mixins.scss

1// 设置组件的变量
2@mixin set-component-var($name, $var, $varKey: 'default') {
3  @each $key, $value in $var {
4    $varName: getVarName($name, $key);
5    $val: map.get($var, $key, $varKey);
6    @if($val) { #{$varName}: var(#{$val}); }
7  }
8}

遵循BEM命名规则生成组件类名

生成块的类名

packages/theme/src/common/mixins.scss

1// 生成block
2@mixin b($block) {
3  $b: '.' + $namespace + $connect + $block !global;
4  #{$b} {
5    @content;
6  }
7}

生成元素的类名

packages/theme/src/common/mixins.scss

1// 生成elem
2@mixin e($elem, $root: true) {
3  $name: $b + $element-connect + $elem;
4  @if $root {
5    @at-root {
6      #{$name} { @content; }
7    }
8  } @else {
9    #{$name} { @content; }
10  }
11}

生成修改器的类名

packages/theme/src/common/mixins.scss

1// 生成修改器
2@mixin m($attr, $value: '') {
3  $modifier: $b + $modifier-connect + $attr + $modifier-value-connect + $value;
4  @at-root {
5    #{$modifier} {
6      @content;
7    }
8  }
9}

生成状态的类名

packages/theme/src/common/mixins.scss

1// 状态
2@mixin s($attrs, $and: true) {
3  $state: '';
4  @each $attr in $attrs {
5    $state: if($and, '&', '') + '.' + $state-prefix + $attr + ',' + $state;
6  }
7  #{$state} {
8    @content;
9  }
10}