xt-element-ui 1.0.7 → 1.0.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. package/lib/index.common.js +628 -377
  2. package/lib/index.css +1 -1
  3. package/lib/index.umd.js +628 -377
  4. package/lib/index.umd.min.js +1 -1
  5. package/package.json +2 -2
  6. package/src/components/button/index.vue +48 -15
  7. package/src/components/button/style/index.scss +130 -0
  8. package/src/components/card/index.vue +20 -41
  9. package/src/components/card/style/index.scss +49 -0
  10. package/src/components/card-item/index.vue +85 -40
  11. package/src/components/card-item/style/index.scss +72 -0
  12. package/src/components/config-provider/index.js +2 -0
  13. package/src/components/config-provider/index.vue +176 -0
  14. package/src/components/config-provider/style/index.scss +12 -0
  15. package/src/components/flex-box/index.vue +21 -91
  16. package/src/components/flex-box/style/index.scss +91 -0
  17. package/src/components/index.scss +19 -0
  18. package/src/components/input/index.vue +28 -11
  19. package/src/components/input/style/index.scss +27 -0
  20. package/src/index.js +65 -122
  21. package/src/styles/export.scss +1 -1
  22. package/src/styles/theme/bg.scss +6 -0
  23. package/src/styles/theme/border.scss +4 -0
  24. package/src/styles/theme/color.scss +11 -0
  25. package/src/styles/theme/component.scss +70 -0
  26. package/src/styles/theme/dark.scss +29 -0
  27. package/src/styles/theme/font.scss +10 -0
  28. package/src/styles/theme/index.scss +11 -0
  29. package/src/styles/theme/radius.scss +4 -0
  30. package/src/styles/theme/shadow.scss +3 -0
  31. package/src/styles/theme/spacing.scss +5 -0
  32. package/src/styles/theme/text.scss +5 -0
  33. package/src/styles/theme/transition.scss +3 -0
  34. package/src/styles/theme-element.scss +0 -10
  35. package/src/styles/variables.scss +1 -119
  36. package/src/styles/vars.scss +168 -0
  37. package/src/utils/index.js +195 -124
  38. package/src/styles/theme.scss +0 -128
@@ -0,0 +1,176 @@
1
+ <template>
2
+ <!-- 根据 tag 属性选择渲染的标签 -->
3
+ <component
4
+ :is="tag"
5
+ :style="mergedStyle"
6
+ :class="computedClass"
7
+ v-bind="customAttrs"
8
+ >
9
+ <slot></slot>
10
+ </component>
11
+ </template>
12
+
13
+ <script>
14
+ export default {
15
+ name: 'XtConfigProvider',
16
+ inheritAttrs: false,
17
+ props: {
18
+ theme: {
19
+ type: String,
20
+ default: 'light'
21
+ },
22
+ size: {
23
+ type: String,
24
+ default: 'medium'
25
+ },
26
+ primaryColor: {
27
+ type: String,
28
+ default: '#409EFF'
29
+ },
30
+ vars: {
31
+ type: Object,
32
+ default: () => ({})
33
+ },
34
+ tag: {
35
+ type: String,
36
+ default: 'div',
37
+ validator: (value) => {
38
+ return ['div', 'span', 'section', 'main', 'template', 'article', 'aside'].includes(value)
39
+ }
40
+ },
41
+ injectBackground: {
42
+ type: Boolean,
43
+ default: false
44
+ },
45
+ injectColor: {
46
+ type: Boolean,
47
+ default: false
48
+ }
49
+ },
50
+ computed: {
51
+ mergedStyle() {
52
+ const result = { ...this.vars }
53
+
54
+ if (this.primaryColor) {
55
+ const color = this.normalizeColor(this.primaryColor)
56
+ result['--xt-color-primary'] = color
57
+ result['--xt-color-primary-light-3'] = this.lightenColor(color, 30)
58
+ result['--xt-color-primary-light-5'] = this.lightenColor(color, 50)
59
+ result['--xt-color-primary-light-7'] = this.lightenColor(color, 70)
60
+ result['--xt-color-primary-light-8'] = this.lightenColor(color, 80)
61
+ result['--xt-color-primary-light-9'] = this.lightenColor(color, 90)
62
+ }
63
+
64
+ const sizeMap = {
65
+ small: '12px',
66
+ medium: '14px',
67
+ large: '16px'
68
+ }
69
+ if (sizeMap[this.size]) {
70
+ result['--xt-font-size-base'] = sizeMap[this.size]
71
+ }
72
+
73
+ if (this.theme === 'dark') {
74
+ result['--xt-color-text-primary'] = 'rgba(255, 255, 255, 0.95)'
75
+ result['--xt-color-text-regular'] = 'rgba(255, 255, 255, 0.8)'
76
+ result['--xt-color-text-secondary'] = 'rgba(255, 255, 255, 0.6)'
77
+ result['--xt-color-bg-primary'] = '#1f1f1f'
78
+ result['--xt-color-bg-secondary'] = '#2d2d2d'
79
+ result['--xt-color-bg-container'] = '#1f1f1f'
80
+ result['--xt-color-border'] = '#434343'
81
+ result['--xt-color-border-light'] = '#3d3d3d'
82
+
83
+ if (this.injectBackground) {
84
+ result.backgroundColor = result['--xt-color-bg-primary']
85
+ }
86
+ if (this.injectColor) {
87
+ result.color = result['--xt-color-text-primary']
88
+ }
89
+ }
90
+
91
+ return result
92
+ },
93
+ computedClass() {
94
+ const classes = []
95
+
96
+ if (this.tag !== 'template') {
97
+ classes.push('xt-config-provider')
98
+
99
+ if (this.theme === 'dark') {
100
+ classes.push('xt-config-provider--dark')
101
+ }
102
+ }
103
+
104
+ return classes
105
+ },
106
+ customAttrs() {
107
+ const props = ['theme', 'size', 'primaryColor', 'vars', 'tag', 'injectBackground', 'injectColor']
108
+ const attrs = {}
109
+
110
+ for (const key in this.$attrs) {
111
+ if (!props.includes(key)) {
112
+ attrs[key] = this.$attrs[key]
113
+ }
114
+ }
115
+
116
+ return attrs
117
+ }
118
+ },
119
+ methods: {
120
+ normalizeColor(color) {
121
+ if (!color) return '#409EFF'
122
+
123
+ if (/^#[0-9A-Fa-f]{6}$/.test(color)) {
124
+ return color
125
+ }
126
+
127
+ if (/^#[0-9A-Fa-f]{3}$/.test(color)) {
128
+ return '#' + color[1] + color[1] + color[2] + color[2] + color[3] + color[3]
129
+ }
130
+
131
+ if (/^#[0-9A-Fa-f]{8}$/.test(color)) {
132
+ return color.substring(0, 7)
133
+ }
134
+
135
+ const rgbaMatch = color.match(/^rgba?\((\d+),\s*(\d+),\s*(\d+)/i)
136
+ if (rgbaMatch) {
137
+ const r = parseInt(rgbaMatch[1])
138
+ const g = parseInt(rgbaMatch[2])
139
+ const b = parseInt(rgbaMatch[3])
140
+ return this.rgbToHex(r, g, b)
141
+ }
142
+
143
+ console.warn('[XtConfigProvider] 无法识别的颜色格式:', color)
144
+ return '#409EFF'
145
+ },
146
+
147
+ hexToRgb(hex) {
148
+ const result = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex)
149
+ return result ? {
150
+ r: parseInt(result[1], 16),
151
+ g: parseInt(result[2], 16),
152
+ b: parseInt(result[3], 16)
153
+ } : null
154
+ },
155
+
156
+ rgbToHex(r, g, b) {
157
+ return '#' + [r, g, b].map(x => {
158
+ const hex = x.toString(16)
159
+ return hex.length === 1 ? '0' + hex : hex
160
+ }).join('')
161
+ },
162
+
163
+ lightenColor(hex, percent) {
164
+ const rgb = this.hexToRgb(hex)
165
+ if (!rgb) return hex
166
+
167
+ const amount = Math.round(2.55 * percent)
168
+ const r = Math.min(255, rgb.r + amount)
169
+ const g = Math.min(255, rgb.g + amount)
170
+ const b = Math.min(255, rgb.b + amount)
171
+
172
+ return this.rgbToHex(r, g, b)
173
+ }
174
+ }
175
+ }
176
+ </script>
@@ -0,0 +1,12 @@
1
+ @import '../../../styles/variables.scss';
2
+
3
+ .xt-config-provider {
4
+ }
5
+
6
+ .xt-config-provider--dark {
7
+ }
8
+
9
+ .xt-config-provider--dark.xt-config-provider--with-bg {
10
+ background-color: var(--xt-color-bg-primary, #1f1f1f);
11
+ color: var(--xt-color-text-primary, rgba(255, 255, 255, 0.95));
12
+ }
@@ -1,104 +1,34 @@
1
- <<template>
2
- <div class="xt-flex-box" :class="classAttrs" style="gap: gap">
3
-
1
+ <template>
2
+ <div class="xt-flex-box" :class="classAttrs" :style="flexStyle">
3
+ <slot></slot>
4
4
  </div>
5
5
  </template>
6
6
 
7
7
  <script>
8
8
  export default {
9
- name: "XtFlex",
9
+ name: "XtFlexBox",
10
10
  props: {
11
- type: "flex",
12
- align: "center",
13
- content: "start",
14
- direction: "row",
15
- wrap: "unset",
16
- gap: {}
11
+ type: { type: String, default: "flex" },
12
+ align: { type: String, default: "center" },
13
+ content: { type: String, default: "start" },
14
+ direction: { type: String, default: "row" },
15
+ wrap: { type: String, default: "unset" },
16
+ gap: { type: String, default: "" }
17
17
  },
18
18
  computed: {
19
19
  classAttrs(){
20
- const {inline, align, wrap, direction,content} = this;
21
- return [`${inline?'is-inline':'flex'}`, `align-${align} content-${content} direction-${direction} wrap-${wrap}`]
22
- }
23
- }
24
- }
25
- </script>
26
-
27
- <style scoped lang="scss">
28
- .xt-flex-box{
29
- &.flex{
30
- display: flex;
31
- &.direction{
32
- &-row,&-row-reverse{
33
- >.flex{
34
- width: 100%;
35
- }
20
+ const { type, align, wrap, direction, content } = this;
21
+ return [`${type}`, `align-${align}`, `content-${content}`, `direction-${direction}`, `wrap-${wrap}`]
22
+ },
23
+ flexStyle() {
24
+ const result = {}
25
+ if (this.gap) {
26
+ result.gap = this.gap
27
+ } else {
28
+ result.gap = 'var(--xt-flex-box-gap, 8px)'
36
29
  }
37
- &-column,&-column-reverse{
38
- >.flex{
39
- height: 100%;
40
- }
41
- }
42
- }
43
- }
44
- &.is-inline{
45
- display: inline-flex;
46
- }
47
-
48
- }
49
- .direction{
50
- &-row{
51
- flex-direction: row;
52
- &-reverse{
53
- flex-direction: row-reverse;
54
- }
55
- }
56
- &-column{
57
- flex-direction: column;
58
- &-reverse{
59
- flex-direction: column-reverse;
30
+ return result
60
31
  }
61
32
  }
62
33
  }
63
- .align{
64
- &-center{
65
- align-items: center;
66
- }
67
- &-start{
68
- align-items: flex-start;
69
- }
70
- &-end{
71
- align-items: flex-end;
72
- }
73
-
74
- }
75
-
76
- .content{
77
- &-center{
78
- justify-content: center;
79
- }
80
- &-around{
81
- justify-content: space-around;
82
- }
83
- &-between{
84
- justify-content: space-between;
85
- }
86
- &-start{
87
- justify-content: flex-start;
88
- }
89
- &-end{
90
- justify-content: flex-end;
91
- }
92
- }
93
- .wrap{
94
- &-wrap{
95
- flex-wrap: wrap;
96
- }
97
- &-nowrap{
98
- flex-wrap: nowrap;
99
- }
100
- &-unset{
101
- flex-wrap: wrap;
102
- }
103
- }
104
- </style>
34
+ </script>
@@ -0,0 +1,91 @@
1
+ @import '../../../styles/variables.scss';
2
+
3
+ .xt-flex-box.flex {
4
+ display: flex;
5
+ }
6
+
7
+ .xt-flex-box.flex.direction-row > .flex,
8
+ .xt-flex-box.flex.direction-row-reverse > .flex {
9
+ width: 100%;
10
+ }
11
+
12
+ .xt-flex-box.flex.direction-column > .flex,
13
+ .xt-flex-box.flex.direction-column-reverse > .flex {
14
+ height: 100%;
15
+ }
16
+
17
+ .xt-flex-box.is-inline {
18
+ display: inline-flex;
19
+ }
20
+
21
+ .direction-row {
22
+ flex-direction: row;
23
+ }
24
+
25
+ .direction-row-reverse {
26
+ flex-direction: row-reverse;
27
+ }
28
+
29
+ .direction-column {
30
+ flex-direction: column;
31
+ }
32
+
33
+ .direction-column-reverse {
34
+ flex-direction: column-reverse;
35
+ }
36
+
37
+ .align-center {
38
+ align-items: center;
39
+ }
40
+
41
+ .align-start {
42
+ align-items: flex-start;
43
+ }
44
+
45
+ .align-end {
46
+ align-items: flex-end;
47
+ }
48
+
49
+ .align-baseline {
50
+ align-items: baseline;
51
+ }
52
+
53
+ .align-stretch {
54
+ align-items: stretch;
55
+ }
56
+
57
+ .content-center {
58
+ justify-content: center;
59
+ }
60
+
61
+ .content-around {
62
+ justify-content: space-around;
63
+ }
64
+
65
+ .content-between {
66
+ justify-content: space-between;
67
+ }
68
+
69
+ .content-start {
70
+ justify-content: flex-start;
71
+ }
72
+
73
+ .content-end {
74
+ justify-content: flex-end;
75
+ }
76
+
77
+ .content-evenly {
78
+ justify-content: space-evenly;
79
+ }
80
+
81
+ .wrap-wrap {
82
+ flex-wrap: wrap;
83
+ }
84
+
85
+ .wrap-nowrap {
86
+ flex-wrap: nowrap;
87
+ }
88
+
89
+ .wrap-unset {
90
+ flex-wrap: wrap;
91
+ }
@@ -0,0 +1,19 @@
1
+ // 组件样式统一入口文件
2
+
3
+ // Button 组件样式
4
+ @import './button/style/index.scss';
5
+
6
+ // Card 组件样式
7
+ @import './card/style/index.scss';
8
+
9
+ // CardItem 组件样式
10
+ @import './card-item/style/index.scss';
11
+
12
+ // Input 组件样式
13
+ @import './input/style/index.scss';
14
+
15
+ // FlexBox 组件样式
16
+ @import './flex-box/style/index.scss';
17
+
18
+ // ConfigProvider 组件样式
19
+ @import './config-provider/style/index.scss';
@@ -1,20 +1,37 @@
1
1
  <template>
2
+ <div class="xt-input">
2
3
  <el-input
3
4
  :value="value"
4
5
  :placeholder="placeholder"
6
+ :style="inputStyle"
5
7
  @input="$emit('input', $event)"
6
8
  />
7
- </template>
8
-
9
- <script>
10
- export default {
11
- name: 'XtInput',
12
- props: {
13
- value: [String, Number],
14
- placeholder: {
15
- type: String,
16
- default: '请输入内容'
9
+ </div>
10
+ </template>
11
+
12
+ <script>
13
+ export default {
14
+ name: 'XtInput',
15
+ props: {
16
+ value: [String, Number],
17
+ placeholder: {
18
+ type: String,
19
+ default: '请输入内容'
20
+ },
21
+ color: {
22
+ type: String,
23
+ default: ''
24
+ }
25
+ },
26
+ computed: {
27
+ inputStyle() {
28
+ if (this.color) {
29
+ return {
30
+ '--xt-input-focus-color': this.color
31
+ }
17
32
  }
33
+ return {}
18
34
  }
19
35
  }
20
- </script>
36
+ }
37
+ </script>
@@ -0,0 +1,27 @@
1
+ @import '../../../styles/variables.scss';
2
+
3
+ .xt-input .el-input__inner {
4
+ --xt-input-focus-color: var(--xt-color-primary, #409EFF);
5
+
6
+ background-color: var(--xt-input-bg-color, #ffffff);
7
+ border-color: var(--xt-input-border-color, #DCDFE6);
8
+ color: var(--xt-input-text-color, #303133);
9
+ font-size: var(--xt-font-size-base, 14px);
10
+ }
11
+
12
+ .xt-input .el-input__inner::placeholder {
13
+ color: var(--xt-input-placeholder-color, #C0C4CC);
14
+ }
15
+
16
+ .xt-input .el-input__inner:focus {
17
+ border-color: var(--xt-input-focus-color);
18
+ box-shadow: 0 0 0 2px color-mix(in srgb, var(--xt-input-focus-color) 20%, transparent);
19
+ }
20
+
21
+ .xt-input .el-input {
22
+ height: var(--xt-input-height, 32px);
23
+ }
24
+
25
+ .xt-input .el-input .el-input__wrapper {
26
+ padding: 0 var(--xt-input-padding-x, 15px);
27
+ }