@douyinfe/semi-foundation 2.12.1-alpha.1 → 2.13.0

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 (74) hide show
  1. package/autoComplete/foundation.ts +50 -11
  2. package/button/button.scss +4 -4
  3. package/button/variables.scss +12 -4
  4. package/checkbox/checkbox.scss +14 -1
  5. package/checkbox/checkboxFoundation.ts +30 -0
  6. package/checkbox/variables.scss +2 -0
  7. package/inputNumber/constants.ts +1 -1
  8. package/inputNumber/foundation.ts +2 -2
  9. package/lib/cjs/autoComplete/foundation.d.ts +3 -0
  10. package/lib/cjs/autoComplete/foundation.js +62 -12
  11. package/lib/cjs/button/button.scss +4 -4
  12. package/lib/cjs/button/variables.scss +12 -4
  13. package/lib/cjs/checkbox/checkbox.css +9 -1
  14. package/lib/cjs/checkbox/checkbox.scss +14 -1
  15. package/lib/cjs/checkbox/checkboxFoundation.d.ts +5 -0
  16. package/lib/cjs/checkbox/checkboxFoundation.js +32 -0
  17. package/lib/cjs/checkbox/variables.scss +2 -0
  18. package/lib/cjs/inputNumber/constants.js +1 -1
  19. package/lib/cjs/inputNumber/foundation.js +2 -2
  20. package/lib/cjs/modal/modal.css +1 -0
  21. package/lib/cjs/modal/modal.scss +1 -0
  22. package/lib/cjs/navigation/foundation.js +4 -0
  23. package/lib/cjs/select/foundation.js +25 -1
  24. package/lib/cjs/tabs/foundation.js +1 -1
  25. package/lib/cjs/tabs/tabs.css +1 -0
  26. package/lib/cjs/tabs/tabs.scss +1 -1
  27. package/lib/cjs/tabs/variables.scss +1 -0
  28. package/lib/cjs/tagInput/foundation.d.ts +3 -0
  29. package/lib/cjs/tagInput/foundation.js +20 -0
  30. package/lib/cjs/timePicker/timePicker.css +6 -0
  31. package/lib/cjs/timePicker/timePicker.scss +9 -1
  32. package/lib/cjs/upload/foundation.js +4 -0
  33. package/lib/cjs/upload/upload.css +14 -0
  34. package/lib/cjs/upload/upload.scss +14 -0
  35. package/lib/cjs/upload/variables.scss +8 -0
  36. package/lib/es/autoComplete/foundation.d.ts +3 -0
  37. package/lib/es/autoComplete/foundation.js +62 -12
  38. package/lib/es/button/button.scss +4 -4
  39. package/lib/es/button/variables.scss +12 -4
  40. package/lib/es/checkbox/checkbox.css +9 -1
  41. package/lib/es/checkbox/checkbox.scss +14 -1
  42. package/lib/es/checkbox/checkboxFoundation.d.ts +5 -0
  43. package/lib/es/checkbox/checkboxFoundation.js +32 -0
  44. package/lib/es/checkbox/variables.scss +2 -0
  45. package/lib/es/inputNumber/constants.js +1 -1
  46. package/lib/es/inputNumber/foundation.js +2 -2
  47. package/lib/es/modal/modal.css +1 -0
  48. package/lib/es/modal/modal.scss +1 -0
  49. package/lib/es/navigation/foundation.js +4 -0
  50. package/lib/es/select/foundation.js +25 -1
  51. package/lib/es/tabs/foundation.js +1 -1
  52. package/lib/es/tabs/tabs.css +1 -0
  53. package/lib/es/tabs/tabs.scss +1 -1
  54. package/lib/es/tabs/variables.scss +1 -0
  55. package/lib/es/tagInput/foundation.d.ts +3 -0
  56. package/lib/es/tagInput/foundation.js +20 -0
  57. package/lib/es/timePicker/timePicker.css +6 -0
  58. package/lib/es/timePicker/timePicker.scss +9 -1
  59. package/lib/es/upload/foundation.js +4 -0
  60. package/lib/es/upload/upload.css +14 -0
  61. package/lib/es/upload/upload.scss +14 -0
  62. package/lib/es/upload/variables.scss +8 -0
  63. package/modal/modal.scss +1 -0
  64. package/navigation/foundation.ts +2 -0
  65. package/package.json +3 -3
  66. package/select/foundation.ts +14 -2
  67. package/tabs/foundation.ts +1 -1
  68. package/tabs/tabs.scss +1 -1
  69. package/tabs/variables.scss +1 -0
  70. package/tagInput/foundation.ts +14 -0
  71. package/timePicker/timePicker.scss +9 -1
  72. package/upload/foundation.ts +2 -0
  73. package/upload/upload.scss +14 -0
  74. package/upload/variables.scss +8 -0
@@ -47,6 +47,8 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
47
47
  super({ ...adapter });
48
48
  }
49
49
 
50
+ isPanelOpen = false;
51
+
50
52
  init(): void {
51
53
  this._setDropdownWidth();
52
54
 
@@ -62,7 +64,7 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
62
64
  }
63
65
 
64
66
  // When both defaultValue and value exist, finally the value of value will be taken as initValue
65
- let initValue = '';
67
+ let initValue: string;
66
68
  if (typeof defaultValue !== 'undefined') {
67
69
  initValue = defaultValue;
68
70
  }
@@ -97,20 +99,27 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
97
99
  handleInputClick(e?: MouseEvent): void {
98
100
  const { options } = this.getStates();
99
101
  const { disabled } = this.getProps();
100
- if (options.length && !disabled) {
101
- this.openDropdown();
102
+ if (!disabled) {
103
+ if (this.isPanelOpen) {
104
+ this.closeDropdown();
105
+ } else {
106
+ this.openDropdown();
107
+ }
102
108
  }
103
109
  }
104
110
 
105
111
  openDropdown(): void {
112
+ this.isPanelOpen = true;
106
113
  this._adapter.toggleListVisible(true);
107
114
  this._setDropdownWidth();
108
115
  // this._adapter.registerClickOutsideHandler(e => this.closeDropdown(e));
109
116
  this._adapter.notifyDropdownVisibleChange(true);
110
117
  this.bindKeyBoardEvent();
118
+ this._modifyFocusIndexOnPanelOpen();
111
119
  }
112
120
 
113
121
  closeDropdown(e?: any): void {
122
+ this.isPanelOpen = false;
114
123
  this._adapter.toggleListVisible(false);
115
124
  // this._adapter.unregisterClickOutsideHandler();
116
125
  this._adapter.notifyDropdownVisibleChange(false);
@@ -143,6 +152,7 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
143
152
  this._adapter.updateInputValue(inputValue);
144
153
  this._adapter.notifySearch(inputValue);
145
154
  this._adapter.notifyChange(inputValue);
155
+ this._modifyFocusIndex(inputValue);
146
156
  }
147
157
 
148
158
  handleSelect(option: StateOptionItem, optionIndex?: number): void {
@@ -156,7 +166,7 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
156
166
  'Warning: [Semi AutoComplete] renderSelectedItem must return string, please check your function return'
157
167
  );
158
168
  } else {
159
- newInputValue = option.label;
169
+ newInputValue = option.value;
160
170
  }
161
171
 
162
172
  // 1. trigger onSelect
@@ -207,7 +217,7 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
207
217
  }
208
218
 
209
219
  handleValueChange(propValue: any) {
210
- let { data } = this.getProps();
220
+ let { data, defaultActiveFirstOption } = this.getProps();
211
221
  let selectedValue = '';
212
222
  if (this._backwardLabelInValue() && Object.prototype.toString.call(propValue) === '[object Object]') {
213
223
  selectedValue = propValue.value;
@@ -219,10 +229,10 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
219
229
 
220
230
  const options = this._generateList(data);
221
231
  // Get the option whose value match from options
222
- let selectedOption: StateOptionItem | Array<StateOptionItem> = options.filter(option => option.value === selectedValue);
232
+ let selectedOption: StateOptionItem | Array<StateOptionItem> = options.filter(option => renderSelectedItem(option) === selectedValue);
223
233
  const canMatchInData = selectedOption.length;
224
234
 
225
- const selectedOptionIndex = options.findIndex(option => option.value === selectedValue);
235
+ const selectedOptionIndex = options.findIndex(option => renderSelectedItem(option) === selectedValue);
226
236
 
227
237
  let inputValue = '';
228
238
  if (canMatchInData) {
@@ -234,15 +244,45 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
234
244
  }
235
245
  this._adapter.updateInputValue(inputValue);
236
246
  this.updateSelection(canMatchInData ? selectedOption : null);
237
- this._adapter.updateFocusIndex(selectedOptionIndex);
247
+ if (selectedOptionIndex === -1 && defaultActiveFirstOption) {
248
+ this._adapter.updateFocusIndex(0);
249
+ } else {
250
+ this._adapter.updateFocusIndex(selectedOptionIndex);
251
+ }
238
252
  }
239
253
 
254
+ _modifyFocusIndex(searchValue) {
255
+ let { focusIndex } = this.getStates();
256
+
257
+ let { data, defaultActiveFirstOption } = this.getProps();
258
+
259
+ let renderSelectedItem = this._getRenderSelectedItem();
260
+
261
+ const options = this._generateList(data);
262
+
263
+ const selectedOptionIndex = options.findIndex(option => renderSelectedItem(option) === searchValue);
264
+
265
+ if (selectedOptionIndex === -1 && defaultActiveFirstOption) {
266
+ if (focusIndex !== 0) {
267
+ this._adapter.updateFocusIndex(0);
268
+ }
269
+ } else {
270
+ if (selectedOptionIndex !== focusIndex) {
271
+ this._adapter.updateFocusIndex(selectedOptionIndex);
272
+ }
273
+ }
274
+ }
275
+
276
+ _modifyFocusIndexOnPanelOpen() {
277
+ let { inputValue } = this.getStates();
278
+ this._modifyFocusIndex(inputValue);
279
+ }
240
280
 
241
281
  _getRenderSelectedItem() {
242
282
  let { renderSelectedItem } = this.getProps();
243
283
 
244
284
  if (typeof renderSelectedItem === 'undefined') {
245
- renderSelectedItem = (option: any) => option.label;
285
+ renderSelectedItem = (option: any) => option.value;
246
286
  } else if (renderSelectedItem && typeof renderSelectedItem === 'function') {
247
287
  // do nothing
248
288
  }
@@ -345,7 +385,7 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
345
385
  if (focusIndex !== -1 && options.length !== 0) {
346
386
  const visibleOptions = options.filter((item: StateOptionItem) => item.show);
347
387
  const selectedOption = visibleOptions[focusIndex];
348
- this.handleSelect(selectedOption);
388
+ this.handleSelect(selectedOption, focusIndex);
349
389
  } else if (visible) {
350
390
  // this.close();
351
391
  }
@@ -357,7 +397,6 @@ class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> e
357
397
 
358
398
  handleFocus(e: FocusEvent) {
359
399
  this._adapter.notifyFocus(e);
360
- this.openDropdown();
361
400
  }
362
401
 
363
402
  handleBlur(e: FocusEvent) {
@@ -47,7 +47,7 @@ $module: #{$prefix}-button;
47
47
  }
48
48
  &.#{$module}-light,
49
49
  &.#{$module}-borderless {
50
- color: $color-button_danger-bg-default;
50
+ color: $color-button_danger_borderless-text-default;
51
51
  }
52
52
  &:not(.#{$module}-borderless):not(.#{$module}-light):focus-visible {
53
53
  outline: $width-button-outline solid $color-button_danger-outline-focus;
@@ -64,7 +64,7 @@ $module: #{$prefix}-button;
64
64
  }
65
65
  &.#{$module}-light,
66
66
  &.#{$module}-borderless {
67
- color: $color-button_warning-bg-default;
67
+ color: $color-button_warning_borderless-text-default;
68
68
  }
69
69
  &:not(.#{$module}-borderless):not(.#{$module}-light):focus-visible {
70
70
  outline: $width-button-outline solid $color-button_warning-outline-focus;
@@ -96,7 +96,7 @@ $module: #{$prefix}-button;
96
96
 
97
97
  &.#{$module}-light,
98
98
  &.#{$module}-borderless {
99
- color: $color-button_primary-bg-default;
99
+ color: $color-button_primary_borderless-text-default;
100
100
  }
101
101
  }
102
102
  &-secondary {
@@ -112,7 +112,7 @@ $module: #{$prefix}-button;
112
112
 
113
113
  &.#{$module}-light,
114
114
  &.#{$module}-borderless {
115
- color: $color-button_secondary-bg-default;
115
+ color: $color-button_secondary_borderless-text-default;
116
116
  }
117
117
  }
118
118
  &-disabled {
@@ -12,6 +12,8 @@ $color-button_primary-border-active: var(--semi-color-primary-active); // 主要
12
12
  $color-button_primary-text-active: rgba(var(--semi-white), 1); // 主要按钮文字颜色 - 按下
13
13
  $color-button_primary-outline-focus: var(--semi-color-primary-light-active); // 主要按钮轮廓 - 聚焦
14
14
 
15
+ $color-button_primary_borderless-text-default: var(--semi-color-primary); // 主要按钮无边框文字颜色
16
+
15
17
  // secondary
16
18
  $color-button_secondary-bg-default: var(--semi-color-secondary); // 次要按钮背景颜色
17
19
  $color-button_secondary-border-default: var(--semi-color-secondary); // 次要按钮描边颜色
@@ -25,6 +27,8 @@ $color-button_secondary-bg-active: var(--semi-color-secondary-active); // 次要
25
27
  $color-button_secondary-border-active: var(--semi-color-secondary-active); // 次要按钮描边颜色 - 按下
26
28
  $color-button_secondary-text-active: rgba(var(--semi-white), 1); // 次要按钮文字颜色 - 按下
27
29
 
30
+ $color-button_secondary_borderless-text-default: var(--semi-color-secondary); // 次要按钮无边框文字颜色
31
+
28
32
  // danger
29
33
  $color-button_danger-bg-default: var(--semi-color-danger); // 危险按钮背景颜色
30
34
  $color-button_danger-border-default: var(--semi-color-danger); // 危险按钮描边颜色
@@ -39,6 +43,8 @@ $color-button_danger-border-active: var(--semi-color-danger-active); // 危险
39
43
  $color-button_danger-text-active: rgba(var(--semi-white), 1); // 危险按钮文字颜色 - 按下
40
44
  $color-button_danger-outline-focus: var(--semi-color-danger-light-active); // 危险按钮轮廓 - 聚焦
41
45
 
46
+ $color-button_danger_borderless-text-default: var(--semi-color-danger); // 危险按钮无边框文字颜色
47
+
42
48
  // warning
43
49
  $color-button_warning-bg-default: var(--semi-color-warning); // 警告按钮背景颜色
44
50
  $color-button_warning-border-default: var(--semi-color-warning); // 警告按钮描边颜色
@@ -53,6 +59,8 @@ $color-button_warning-border-active: var(--semi-color-warning-active); // 警告
53
59
  $color-button_warning-text-active: rgba(var(--semi-white), 1); // 警告按钮文字颜色 - 按下
54
60
  $color-button_warning-outline-focus: var(--semi-color-warning-light-active); // 警告按钮轮廓 - 聚焦
55
61
 
62
+ $color-button_warning_borderless-text-default: var(--semi-color-warning); // 警告按钮无边框文字颜色
63
+
56
64
  // tertiary
57
65
  $color-button_tertiary-bg-default: var(--semi-color-tertiary); // 第三按钮背景颜色
58
66
  $color-button_tertiary-border-default: var(--semi-color-tertiary); // 第三按钮描边颜色
@@ -79,10 +87,10 @@ $color-button_disabled-bg-hover: var(--semi-color-disabled-bg); // 禁用按钮
79
87
  $color-button_light-bg-default: var(--semi-color-fill-0); // 浅色按钮背景颜色
80
88
  $color-button_light-bg-hover: var(--semi-color-fill-1); // 禁用按钮背景颜色 - 悬浮
81
89
  $color-button_light-bg-active: var(--semi-color-fill-2); // 禁用按钮背景颜色 - 按下
82
- $color-button_light-border-default: transparent; // 浅色按钮描边颜色
90
+ $color-button_light-border-default: transparent; // 浅色按钮描边颜色
83
91
  $color-button_light-border-hover: $color-button_light-border-default; // 浅色按钮描边颜色 - 悬浮
84
92
  $color-button_light-border-active: $color-button_light-border-hover; // 浅色按钮描边颜色 - 按下
85
- $width-button_light-border: 0; // 浅色按钮描边宽度
93
+ $width-button_light-border: 0; // 浅色按钮描边宽度
86
94
 
87
95
  // borderless
88
96
  $color-button_borderless-text-default: var(--semi-color-primary); // 无背景按钮背景颜色
@@ -126,7 +134,7 @@ $spacing-button_iconOnly_small-paddingTop: $spacing-extra-tight; // 图标按钮
126
134
  $spacing-button_iconOnly_small-paddingBottom: $spacing-extra-tight; // 图标按钮底部内边距 - 小尺寸
127
135
 
128
136
  // margin
129
- $spacing-button_iconOnly_content-marginLeft: $spacing-tight; // 按钮左侧图标距离文字间距
137
+ $spacing-button_iconOnly_content-marginLeft: $spacing-tight; // 按钮左侧图标距离文字间距
130
138
  $spacing-button_iconOnly_content-marginRight: $spacing-tight; // 按钮右侧图标距离文字间距
131
139
 
132
140
  $font-button-fontWeight: $font-weight-bold; // 按钮文字字重
@@ -134,7 +142,7 @@ $height-button_large: $height-control-large; // 按钮高度 - 大尺寸
134
142
  $height-button_small: $height-control-small; // 按钮高度 - 小尺寸
135
143
  $height-button_default: $height-control-default; // 按钮高度 - 默认
136
144
 
137
- $width-button-border: $border-thickness; // 按钮描边宽度
145
+ $width-button-border: $border-thickness; // 按钮描边宽度
138
146
  $radius-button: var(--semi-border-radius-small); // 按钮圆角大小
139
147
  $radius-button_group: $radius-button; // 按钮组圆角大小
140
148
  $width-button-outline: 2px; // 按钮轮廓宽度
@@ -103,7 +103,12 @@ $module: #{$prefix}-checkbox;
103
103
  }
104
104
 
105
105
  &-pureCardType {
106
- display: none;
106
+ // Reasons to use opacity:0 & width: 0 instead of display: none
107
+ // The a11y keyboard focus event of the checkbox depends on the implementation of the input focus/blur event
108
+ // input focus/blur cannot take effect when display: none
109
+ opacity: 0;
110
+ width: 0;
111
+ margin-right: 0 !important;
107
112
  }
108
113
  }
109
114
 
@@ -347,6 +352,14 @@ $module: #{$prefix}-checkbox;
347
352
  color: $color-checkbox_extra-text-default;
348
353
  margin-top: $spacing-checkbox_extra-marginTop;
349
354
  }
355
+
356
+ &-focus {
357
+ outline: $width-checkbox-outline solid $color-checkbox_primary-outline-focus;
358
+
359
+ &-border {
360
+ box-shadow: inset 0 0 0 $size-checkbox_inner-shadow $color-checkbox_default-border-hover;
361
+ }
362
+ }
350
363
  }
351
364
 
352
365
  .#{$module}Group {
@@ -23,6 +23,8 @@ export interface CheckboxAdapter<P = Record<string, any>, S = Record<string, any
23
23
  notifyChange: (event: BasicCheckboxEvent) => void;
24
24
  setAddonId: () => void;
25
25
  setExtraId: () => void;
26
+ setFocusVisible: (focusVisible: boolean) => void;
27
+ focusCheckboxEntity: () => void;
26
28
  }
27
29
 
28
30
  class CheckboxFoundation<P = Record<string, any>, S = Record<string, any>> extends BaseFoundation<CheckboxAdapter<P, S>, P, S> {
@@ -31,6 +33,8 @@ class CheckboxFoundation<P = Record<string, any>, S = Record<string, any>> exten
31
33
  super({ ...adapter });
32
34
  }
33
35
 
36
+ clickState = false;
37
+
34
38
  init() {
35
39
  const { children, extra, extraId, addonId } = this.getProps();
36
40
  if (children && !addonId) {
@@ -77,6 +81,12 @@ class CheckboxFoundation<P = Record<string, any>, S = Record<string, any>> exten
77
81
  return;
78
82
  }
79
83
 
84
+ if (e?.type === 'click') {
85
+ this.clickState = true;
86
+ }
87
+
88
+ this._adapter.focusCheckboxEntity();
89
+
80
90
  const isInGroup = this._adapter.getIsInGroup();
81
91
 
82
92
  if (isInGroup) {
@@ -118,6 +128,26 @@ class CheckboxFoundation<P = Record<string, any>, S = Record<string, any>> exten
118
128
  this._adapter.setNativeControlChecked(checked);
119
129
  }
120
130
 
131
+ handleFocusVisible = (event: any) => {
132
+ const { target } = event;
133
+ try {
134
+ if (this.clickState) {
135
+ this.clickState = false;
136
+ return;
137
+ }
138
+ if (target.matches(':focus-visible')) {
139
+ this._adapter.setFocusVisible(true);
140
+ }
141
+ } catch (error){
142
+ console.warn('The current browser does not support the focus-visible');
143
+ }
144
+ }
145
+
146
+ handleBlur = () => {
147
+ this.clickState = false;
148
+ this._adapter.setFocusVisible(false);
149
+ }
150
+
121
151
  // eslint-disable-next-line @typescript-eslint/no-empty-function
122
152
  destroy() {}
123
153
  }
@@ -36,12 +36,14 @@ $color-checkbox_disabled-bg-default: var(--semi-color-disabled-fill); // 选框
36
36
  $color-checkbox_disabled-border-default: var(--semi-color-border); // 选框禁用态描边颜色 - 默认
37
37
  $color-checkbox_checked-bg-disabled: var(--semi-color-primary-disabled); // 选框选中 + 禁用态背景颜色
38
38
  $color-checkbox_checked-icon-disabled: var(--semi-color-white); // 选框禁用态对勾颜色
39
+ $color-checkbox_primary-outline-focus: var(--semi-color-primary-light-active); // 复选框轮廓-聚焦颜色
39
40
 
40
41
  $size-checkbox_inner-shadow: $border-thickness-control; // 选框内描边宽度
41
42
  $width-checkbox_inner: $width-icon-medium; // 选框对勾 icon 宽度
42
43
  $height-checkbox_inner: 20px; // 选框对勾 icon 高度
43
44
  $width-checkbox_cardType_checked-border: 1px; // 卡片类型复选框的边框宽度
44
45
  $width-checkbox_cardType_checked_disabled-border: 1px; // 卡片类型复选框选中且禁用的边框宽度
46
+ $width-checkbox-outline: 2px; // 复选框轮廓宽度
45
47
 
46
48
  $radius-checkbox_cardType: 3px; // 卡片类型复选框的圆角大小
47
49
  $radius-checkbox_inner: var(--semi-border-radius-extra-small); // 选框圆角
@@ -7,7 +7,7 @@ const cssClasses = {
7
7
  const numbers = {
8
8
  ...inputNumbers,
9
9
  DEFAULT_STEP: 1,
10
- DEFAULT_SHIFT_STEP: 1,
10
+ DEFAULT_SHIFT_STEP: 10,
11
11
  DEFAULT_PRESS_TIMEOUT: 250,
12
12
  DEFAULT_PRESS_INTERVAL: 0,
13
13
  MOUSE_BUTTON_LEFT: 0, // left mouse button
@@ -215,7 +215,7 @@ class InputNumberFoundation extends BaseFoundation<InputNumberAdapter> {
215
215
  if (code === keyCode.UP || code === keyCode.DOWN) {
216
216
  this._adapter.setClickUpOrDown(true);
217
217
  this._adapter.recordCursorPosition();
218
- const formattedVal = code === keyCode.UP ? this.add() : this.minus();
218
+ const formattedVal = code === keyCode.UP ? this.add(null, event) : this.minus(null, event);
219
219
 
220
220
  this._doInput(formattedVal, event, () => {
221
221
  this._adapter.restoreCursor();
@@ -382,7 +382,7 @@ class InputNumberFoundation extends BaseFoundation<InputNumberAdapter> {
382
382
  this._adapter.setNumber(number);
383
383
  this._adapter.setValue(formattedValue);
384
384
 
385
- if (isString(formattedValue) && formattedValue !== String(propsValue)) {
385
+ if (isString(formattedValue) && formattedValue !== String(propsValue ?? '')) {
386
386
  this.notifyChange(formattedValue, null);
387
387
  }
388
388
  }
@@ -33,6 +33,7 @@ export interface AutoCompleteAdapter<P = Record<string, any>, S = Record<string,
33
33
  declare class AutoCompleteFoundation<P = Record<string, any>, S = Record<string, any>> extends BaseFoundation<AutoCompleteAdapter<P, S>, P, S> {
34
34
  private _keydownHandler;
35
35
  constructor(adapter: AutoCompleteAdapter<P, S>);
36
+ isPanelOpen: boolean;
36
37
  init(): void;
37
38
  destroy(): void;
38
39
  _setDropdownWidth(): void;
@@ -47,6 +48,8 @@ declare class AutoCompleteFoundation<P = Record<string, any>, S = Record<string,
47
48
  _backwardLabelInValue(): any;
48
49
  handleDataChange(newData: any[]): void;
49
50
  handleValueChange(propValue: any): void;
51
+ _modifyFocusIndex(searchValue: any): void;
52
+ _modifyFocusIndexOnPanelOpen(): void;
50
53
  _getRenderSelectedItem(): any;
51
54
  handleClear(): void;
52
55
  bindKeyBoardEvent(): void;
@@ -42,6 +42,7 @@ var _keyCode = _interopRequireDefault(require("../utils/keyCode"));
42
42
  class AutoCompleteFoundation extends _foundation.default {
43
43
  constructor(adapter) {
44
44
  super((0, _assign.default)({}, adapter));
45
+ this.isPanelOpen = false;
45
46
  }
46
47
 
47
48
  init() {
@@ -65,7 +66,7 @@ class AutoCompleteFoundation extends _foundation.default {
65
66
  } // When both defaultValue and value exist, finally the value of value will be taken as initValue
66
67
 
67
68
 
68
- let initValue = '';
69
+ let initValue;
69
70
 
70
71
  if (typeof defaultValue !== 'undefined') {
71
72
  initValue = defaultValue;
@@ -115,12 +116,18 @@ class AutoCompleteFoundation extends _foundation.default {
115
116
  disabled
116
117
  } = this.getProps();
117
118
 
118
- if (options.length && !disabled) {
119
- this.openDropdown();
119
+ if (!disabled) {
120
+ if (this.isPanelOpen) {
121
+ this.closeDropdown();
122
+ } else {
123
+ this.openDropdown();
124
+ }
120
125
  }
121
126
  }
122
127
 
123
128
  openDropdown() {
129
+ this.isPanelOpen = true;
130
+
124
131
  this._adapter.toggleListVisible(true);
125
132
 
126
133
  this._setDropdownWidth(); // this._adapter.registerClickOutsideHandler(e => this.closeDropdown(e));
@@ -129,9 +136,13 @@ class AutoCompleteFoundation extends _foundation.default {
129
136
  this._adapter.notifyDropdownVisibleChange(true);
130
137
 
131
138
  this.bindKeyBoardEvent();
139
+
140
+ this._modifyFocusIndexOnPanelOpen();
132
141
  }
133
142
 
134
143
  closeDropdown(e) {
144
+ this.isPanelOpen = false;
145
+
135
146
  this._adapter.toggleListVisible(false); // this._adapter.unregisterClickOutsideHandler();
136
147
 
137
148
 
@@ -182,6 +193,8 @@ class AutoCompleteFoundation extends _foundation.default {
182
193
  this._adapter.notifySearch(inputValue);
183
194
 
184
195
  this._adapter.notifyChange(inputValue);
196
+
197
+ this._modifyFocusIndex(inputValue);
185
198
  }
186
199
 
187
200
  handleSelect(option, optionIndex) {
@@ -194,7 +207,7 @@ class AutoCompleteFoundation extends _foundation.default {
194
207
  newInputValue = renderSelectedItem(option);
195
208
  (0, _warning.default)(typeof newInputValue !== 'string', 'Warning: [Semi AutoComplete] renderSelectedItem must return string, please check your function return');
196
209
  } else {
197
- newInputValue = option.label;
210
+ newInputValue = option.value;
198
211
  } // 1. trigger onSelect
199
212
  // 2. close Dropdown
200
213
 
@@ -255,7 +268,8 @@ class AutoCompleteFoundation extends _foundation.default {
255
268
 
256
269
  handleValueChange(propValue) {
257
270
  let {
258
- data
271
+ data,
272
+ defaultActiveFirstOption
259
273
  } = this.getProps();
260
274
  let selectedValue = '';
261
275
 
@@ -270,9 +284,9 @@ class AutoCompleteFoundation extends _foundation.default {
270
284
  const options = this._generateList(data); // Get the option whose value match from options
271
285
 
272
286
 
273
- let selectedOption = (0, _filter.default)(options).call(options, option => option.value === selectedValue);
287
+ let selectedOption = (0, _filter.default)(options).call(options, option => renderSelectedItem(option) === selectedValue);
274
288
  const canMatchInData = selectedOption.length;
275
- const selectedOptionIndex = (0, _findIndex.default)(options).call(options, option => option.value === selectedValue);
289
+ const selectedOptionIndex = (0, _findIndex.default)(options).call(options, option => renderSelectedItem(option) === selectedValue);
276
290
  let inputValue = '';
277
291
 
278
292
  if (canMatchInData) {
@@ -290,7 +304,45 @@ class AutoCompleteFoundation extends _foundation.default {
290
304
 
291
305
  this.updateSelection(canMatchInData ? selectedOption : null);
292
306
 
293
- this._adapter.updateFocusIndex(selectedOptionIndex);
307
+ if (selectedOptionIndex === -1 && defaultActiveFirstOption) {
308
+ this._adapter.updateFocusIndex(0);
309
+ } else {
310
+ this._adapter.updateFocusIndex(selectedOptionIndex);
311
+ }
312
+ }
313
+
314
+ _modifyFocusIndex(searchValue) {
315
+ let {
316
+ focusIndex
317
+ } = this.getStates();
318
+ let {
319
+ data,
320
+ defaultActiveFirstOption
321
+ } = this.getProps();
322
+
323
+ let renderSelectedItem = this._getRenderSelectedItem();
324
+
325
+ const options = this._generateList(data);
326
+
327
+ const selectedOptionIndex = (0, _findIndex.default)(options).call(options, option => renderSelectedItem(option) === searchValue);
328
+
329
+ if (selectedOptionIndex === -1 && defaultActiveFirstOption) {
330
+ if (focusIndex !== 0) {
331
+ this._adapter.updateFocusIndex(0);
332
+ }
333
+ } else {
334
+ if (selectedOptionIndex !== focusIndex) {
335
+ this._adapter.updateFocusIndex(selectedOptionIndex);
336
+ }
337
+ }
338
+ }
339
+
340
+ _modifyFocusIndexOnPanelOpen() {
341
+ let {
342
+ inputValue
343
+ } = this.getStates();
344
+
345
+ this._modifyFocusIndex(inputValue);
294
346
  }
295
347
 
296
348
  _getRenderSelectedItem() {
@@ -299,7 +351,7 @@ class AutoCompleteFoundation extends _foundation.default {
299
351
  } = this.getProps();
300
352
 
301
353
  if (typeof renderSelectedItem === 'undefined') {
302
- renderSelectedItem = option => option.label;
354
+ renderSelectedItem = option => option.value;
303
355
  } else if (renderSelectedItem && typeof renderSelectedItem === 'function') {// do nothing
304
356
  }
305
357
 
@@ -434,7 +486,7 @@ class AutoCompleteFoundation extends _foundation.default {
434
486
  if (focusIndex !== -1 && options.length !== 0) {
435
487
  const visibleOptions = (0, _filter.default)(options).call(options, item => item.show);
436
488
  const selectedOption = visibleOptions[focusIndex];
437
- this.handleSelect(selectedOption);
489
+ this.handleSelect(selectedOption, focusIndex);
438
490
  } else if (visible) {// this.close();
439
491
  }
440
492
  }
@@ -445,8 +497,6 @@ class AutoCompleteFoundation extends _foundation.default {
445
497
 
446
498
  handleFocus(e) {
447
499
  this._adapter.notifyFocus(e);
448
-
449
- this.openDropdown();
450
500
  }
451
501
 
452
502
  handleBlur(e) {
@@ -47,7 +47,7 @@ $module: #{$prefix}-button;
47
47
  }
48
48
  &.#{$module}-light,
49
49
  &.#{$module}-borderless {
50
- color: $color-button_danger-bg-default;
50
+ color: $color-button_danger_borderless-text-default;
51
51
  }
52
52
  &:not(.#{$module}-borderless):not(.#{$module}-light):focus-visible {
53
53
  outline: $width-button-outline solid $color-button_danger-outline-focus;
@@ -64,7 +64,7 @@ $module: #{$prefix}-button;
64
64
  }
65
65
  &.#{$module}-light,
66
66
  &.#{$module}-borderless {
67
- color: $color-button_warning-bg-default;
67
+ color: $color-button_warning_borderless-text-default;
68
68
  }
69
69
  &:not(.#{$module}-borderless):not(.#{$module}-light):focus-visible {
70
70
  outline: $width-button-outline solid $color-button_warning-outline-focus;
@@ -96,7 +96,7 @@ $module: #{$prefix}-button;
96
96
 
97
97
  &.#{$module}-light,
98
98
  &.#{$module}-borderless {
99
- color: $color-button_primary-bg-default;
99
+ color: $color-button_primary_borderless-text-default;
100
100
  }
101
101
  }
102
102
  &-secondary {
@@ -112,7 +112,7 @@ $module: #{$prefix}-button;
112
112
 
113
113
  &.#{$module}-light,
114
114
  &.#{$module}-borderless {
115
- color: $color-button_secondary-bg-default;
115
+ color: $color-button_secondary_borderless-text-default;
116
116
  }
117
117
  }
118
118
  &-disabled {
@@ -12,6 +12,8 @@ $color-button_primary-border-active: var(--semi-color-primary-active); // 主要
12
12
  $color-button_primary-text-active: rgba(var(--semi-white), 1); // 主要按钮文字颜色 - 按下
13
13
  $color-button_primary-outline-focus: var(--semi-color-primary-light-active); // 主要按钮轮廓 - 聚焦
14
14
 
15
+ $color-button_primary_borderless-text-default: var(--semi-color-primary); // 主要按钮无边框文字颜色
16
+
15
17
  // secondary
16
18
  $color-button_secondary-bg-default: var(--semi-color-secondary); // 次要按钮背景颜色
17
19
  $color-button_secondary-border-default: var(--semi-color-secondary); // 次要按钮描边颜色
@@ -25,6 +27,8 @@ $color-button_secondary-bg-active: var(--semi-color-secondary-active); // 次要
25
27
  $color-button_secondary-border-active: var(--semi-color-secondary-active); // 次要按钮描边颜色 - 按下
26
28
  $color-button_secondary-text-active: rgba(var(--semi-white), 1); // 次要按钮文字颜色 - 按下
27
29
 
30
+ $color-button_secondary_borderless-text-default: var(--semi-color-secondary); // 次要按钮无边框文字颜色
31
+
28
32
  // danger
29
33
  $color-button_danger-bg-default: var(--semi-color-danger); // 危险按钮背景颜色
30
34
  $color-button_danger-border-default: var(--semi-color-danger); // 危险按钮描边颜色
@@ -39,6 +43,8 @@ $color-button_danger-border-active: var(--semi-color-danger-active); // 危险
39
43
  $color-button_danger-text-active: rgba(var(--semi-white), 1); // 危险按钮文字颜色 - 按下
40
44
  $color-button_danger-outline-focus: var(--semi-color-danger-light-active); // 危险按钮轮廓 - 聚焦
41
45
 
46
+ $color-button_danger_borderless-text-default: var(--semi-color-danger); // 危险按钮无边框文字颜色
47
+
42
48
  // warning
43
49
  $color-button_warning-bg-default: var(--semi-color-warning); // 警告按钮背景颜色
44
50
  $color-button_warning-border-default: var(--semi-color-warning); // 警告按钮描边颜色
@@ -53,6 +59,8 @@ $color-button_warning-border-active: var(--semi-color-warning-active); // 警告
53
59
  $color-button_warning-text-active: rgba(var(--semi-white), 1); // 警告按钮文字颜色 - 按下
54
60
  $color-button_warning-outline-focus: var(--semi-color-warning-light-active); // 警告按钮轮廓 - 聚焦
55
61
 
62
+ $color-button_warning_borderless-text-default: var(--semi-color-warning); // 警告按钮无边框文字颜色
63
+
56
64
  // tertiary
57
65
  $color-button_tertiary-bg-default: var(--semi-color-tertiary); // 第三按钮背景颜色
58
66
  $color-button_tertiary-border-default: var(--semi-color-tertiary); // 第三按钮描边颜色
@@ -79,10 +87,10 @@ $color-button_disabled-bg-hover: var(--semi-color-disabled-bg); // 禁用按钮
79
87
  $color-button_light-bg-default: var(--semi-color-fill-0); // 浅色按钮背景颜色
80
88
  $color-button_light-bg-hover: var(--semi-color-fill-1); // 禁用按钮背景颜色 - 悬浮
81
89
  $color-button_light-bg-active: var(--semi-color-fill-2); // 禁用按钮背景颜色 - 按下
82
- $color-button_light-border-default: transparent; // 浅色按钮描边颜色
90
+ $color-button_light-border-default: transparent; // 浅色按钮描边颜色
83
91
  $color-button_light-border-hover: $color-button_light-border-default; // 浅色按钮描边颜色 - 悬浮
84
92
  $color-button_light-border-active: $color-button_light-border-hover; // 浅色按钮描边颜色 - 按下
85
- $width-button_light-border: 0; // 浅色按钮描边宽度
93
+ $width-button_light-border: 0; // 浅色按钮描边宽度
86
94
 
87
95
  // borderless
88
96
  $color-button_borderless-text-default: var(--semi-color-primary); // 无背景按钮背景颜色
@@ -126,7 +134,7 @@ $spacing-button_iconOnly_small-paddingTop: $spacing-extra-tight; // 图标按钮
126
134
  $spacing-button_iconOnly_small-paddingBottom: $spacing-extra-tight; // 图标按钮底部内边距 - 小尺寸
127
135
 
128
136
  // margin
129
- $spacing-button_iconOnly_content-marginLeft: $spacing-tight; // 按钮左侧图标距离文字间距
137
+ $spacing-button_iconOnly_content-marginLeft: $spacing-tight; // 按钮左侧图标距离文字间距
130
138
  $spacing-button_iconOnly_content-marginRight: $spacing-tight; // 按钮右侧图标距离文字间距
131
139
 
132
140
  $font-button-fontWeight: $font-weight-bold; // 按钮文字字重
@@ -134,7 +142,7 @@ $height-button_large: $height-control-large; // 按钮高度 - 大尺寸
134
142
  $height-button_small: $height-control-small; // 按钮高度 - 小尺寸
135
143
  $height-button_default: $height-control-default; // 按钮高度 - 默认
136
144
 
137
- $width-button-border: $border-thickness; // 按钮描边宽度
145
+ $width-button-border: $border-thickness; // 按钮描边宽度
138
146
  $radius-button: var(--semi-border-radius-small); // 按钮圆角大小
139
147
  $radius-button_group: $radius-button; // 按钮组圆角大小
140
148
  $width-button-outline: 2px; // 按钮轮廓宽度