@rescui/select 0.1.2 → 0.2.1

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.
@@ -16,6 +16,7 @@ import _Object$getOwnPropertyDescriptors from "@babel/runtime-corejs3/core-js-st
16
16
  import "core-js/modules/es.object.to-string.js";
17
17
  import "core-js/modules/es.array.join.js";
18
18
  import "core-js/modules/web.dom-collections.for-each.js";
19
+ import "core-js/modules/es.function.name.js";
19
20
  import React, { useState } from 'react';
20
21
  import PropTypes from 'prop-types';
21
22
  import cn from 'classnames';
@@ -157,11 +158,6 @@ var NativeSelect = function NativeSelect(_ref7) {
157
158
  _ref7$className = _ref7.className,
158
159
  className = _ref7$className === void 0 ? null : _ref7$className,
159
160
  style = _ref7.style,
160
- _ref7$defaultValue = _ref7.defaultValue,
161
- defaultValue = _ref7$defaultValue === void 0 ? {
162
- label: '',
163
- value: null
164
- } : _ref7$defaultValue,
165
161
  _ref7$value = _ref7.value,
166
162
  value = _ref7$value === void 0 ? undefined : _ref7$value,
167
163
  onChange = _ref7.onChange,
@@ -175,25 +171,18 @@ var NativeSelect = function NativeSelect(_ref7) {
175
171
  label = _ref7.label,
176
172
  note = _ref7.note,
177
173
  error = _ref7.error,
178
- noOptionsMessage = _ref7.noOptionsMessage;
174
+ noOptionsMessage = _ref7.noOptionsMessage,
175
+ name = _ref7.name;
179
176
  var theme = useTheme(themeFromProps);
180
177
 
181
- var _useState = useState(defaultValue),
178
+ var _useState = useState(false),
182
179
  _useState2 = _slicedToArray(_useState, 2),
183
- selected = _useState2[0],
184
- setSelected = _useState2[1];
185
-
186
- var displayed = value ? value : selected;
187
-
188
- var _useState3 = useState(false),
189
- _useState4 = _slicedToArray(_useState3, 2),
190
- hovered = _useState4[0],
191
- setHovered = _useState4[1];
180
+ hovered = _useState2[0],
181
+ setHovered = _useState2[1];
192
182
 
193
183
  var handleChange = function handleChange(event) {
194
184
  var newValue = event.target.value;
195
185
  var selectedOption = findSelectedOption(options, newValue);
196
- setSelected(selectedOption);
197
186
 
198
187
  if (onChange) {
199
188
  onChange(selectedOption);
@@ -212,8 +201,8 @@ var NativeSelect = function NativeSelect(_ref7) {
212
201
 
213
202
  if (trigger) {
214
203
  _trigger = trigger({
215
- selectedLabel: displayed.label,
216
- selectedValue: displayed.value,
204
+ selectedLabel: value === null || value === void 0 ? void 0 : value.label,
205
+ selectedValue: value === null || value === void 0 ? void 0 : value.value,
217
206
  placeholder: placeholder,
218
207
  hovered: hovered
219
208
  });
@@ -222,10 +211,7 @@ var NativeSelect = function NativeSelect(_ref7) {
222
211
  theme: theme,
223
212
  size: size,
224
213
  isOpen: false,
225
- onKeyDown: function onKeyDown() {
226
- return false;
227
- },
228
- selected: displayed,
214
+ selected: value,
229
215
  placeholder: placeholder,
230
216
  searchInput: "",
231
217
  isClearable: false,
@@ -241,7 +227,10 @@ var NativeSelect = function NativeSelect(_ref7) {
241
227
  size: size,
242
228
  error: error,
243
229
  label: label,
244
- note: note
230
+ note: note,
231
+ onKeyDown: function onKeyDown() {
232
+ return false;
233
+ }
245
234
  }, /*#__PURE__*/React.createElement("div", {
246
235
  className: styles.main,
247
236
  onMouseEnter: function onMouseEnter() {
@@ -257,14 +246,14 @@ var NativeSelect = function NativeSelect(_ref7) {
257
246
  className: cn(styles.select, SIZE_STYLES[size]),
258
247
  disabled: isDisabled ? true : undefined,
259
248
  onChange: handleChange,
260
- value: displayed.label !== '' ? displayed.value : PLACEHOLDER_VALUE
249
+ name: name,
250
+ value: (value === null || value === void 0 ? void 0 : value.label) !== '' ? value === null || value === void 0 ? void 0 : value.value : PLACEHOLDER_VALUE
261
251
  }, optionList)));
262
252
  };
263
253
 
264
254
  NativeSelect.propTypes = {
265
255
  className: PropTypes.string,
266
256
  options: PropTypes.arrayOf(PropTypes.oneOfType([optionType, optionsGroupType])),
267
- defaultValue: optionType,
268
257
  value: optionType,
269
258
  onChange: PropTypes.func,
270
259
  size: PropTypes.oneOf(['m', 's', 'l']),
@@ -277,6 +266,7 @@ NativeSelect.propTypes = {
277
266
  label: PropTypes.node,
278
267
  note: PropTypes.node,
279
268
  noOptionsMessage: noOptionsMessageType,
280
- style: PropTypes.object
269
+ style: PropTypes.object,
270
+ name: PropTypes.string
281
271
  };
282
272
  export default NativeSelect;
@@ -1,9 +1,9 @@
1
1
  var styles = {
2
- "main": "_main_1uu0zyo_3",
3
- "select": "_select_1uu0zyo_7",
4
- "sizeL": "_sizeL_1uu0zyo_19",
5
- "rs-reset-letter-spacing": "_rs-reset-letter-spacing_1uu0zyo_1",
6
- "sizeM": "_sizeM_1uu0zyo_23",
7
- "sizeS": "_sizeS_1uu0zyo_27"
2
+ "main": "_main_19ve46_3",
3
+ "select": "_select_19ve46_7",
4
+ "sizeL": "_sizeL_19ve46_19",
5
+ "rs-reset-letter-spacing": "_rs-reset-letter-spacing_19ve46_1",
6
+ "sizeM": "_sizeM_19ve46_23",
7
+ "sizeS": "_sizeS_19ve46_27"
8
8
  };
9
9
  export default styles;
@@ -49,7 +49,7 @@ var TAG_SIZE = {
49
49
  l: 'm'
50
50
  }; // eslint-disable-next-line complexity
51
51
 
52
- var SelectTrigger = function SelectTrigger(props) {
52
+ var SelectTrigger = /*#__PURE__*/React.memo(function (props) {
53
53
  var size = props.size,
54
54
  mode = props.mode,
55
55
  themeFromProps = props.theme,
@@ -156,7 +156,8 @@ var SelectTrigger = function SelectTrigger(props) {
156
156
  className: styles.toggle,
157
157
  "data-test": "down-icon"
158
158
  })));
159
- };
159
+ });
160
+ SelectTrigger.displayName = 'SelectTrigger';
160
161
 
161
162
  var MultiselectOptions = function MultiselectOptions(_ref) {
162
163
  var isSingleLine = _ref.isSingleLine,
@@ -1,30 +1,30 @@
1
1
  var styles = {
2
- "main": "_main_1vzhj39_24",
3
- "open": "_open_1vzhj39_36",
4
- "enabled": "_enabled_1vzhj39_41",
5
- "disabled": "_disabled_1vzhj39_45",
6
- "focused": "_focused_1vzhj39_49",
7
- "searchFocused": "_searchFocused_1vzhj39_50",
8
- "sizeL": "_sizeL_1vzhj39_56",
9
- "sizeM": "_sizeM_1vzhj39_59",
10
- "rs-reset-letter-spacing": "_rs-reset-letter-spacing_1vzhj39_1",
11
- "sizeS": "_sizeS_1vzhj39_62",
12
- "isMulti": "_isMulti_1vzhj39_136",
13
- "error": "_error_1vzhj39_69",
14
- "notSelected": "_notSelected_1vzhj39_144",
15
- "themeLight": "_themeLight_1vzhj39_148",
16
- "searchKeyFocused": "_searchKeyFocused_1vzhj39_154",
17
- "rock": "_rock_1vzhj39_168",
18
- "toggle": "_toggle_1vzhj39_173",
19
- "labelWrapper": "_labelWrapper_1vzhj39_177",
20
- "themeDark": "_themeDark_1vzhj39_199",
21
- "label": "_label_1vzhj39_177",
22
- "iconsWrapper": "_iconsWrapper_1vzhj39_285",
23
- "searchInput": "_searchInput_1vzhj39_340",
24
- "multi": "_multi_1vzhj39_366",
25
- "tagsContainer": "_tagsContainer_1vzhj39_375",
26
- "tag": "_tag_1vzhj39_375",
27
- "icon": "_icon_1vzhj39_285",
28
- "clearIcon": "_clearIcon_1vzhj39_490"
2
+ "main": "_main_1i1mczn_24",
3
+ "open": "_open_1i1mczn_36",
4
+ "enabled": "_enabled_1i1mczn_41",
5
+ "disabled": "_disabled_1i1mczn_45",
6
+ "focused": "_focused_1i1mczn_49",
7
+ "searchFocused": "_searchFocused_1i1mczn_50",
8
+ "sizeL": "_sizeL_1i1mczn_56",
9
+ "sizeM": "_sizeM_1i1mczn_59",
10
+ "rs-reset-letter-spacing": "_rs-reset-letter-spacing_1i1mczn_1",
11
+ "sizeS": "_sizeS_1i1mczn_62",
12
+ "isMulti": "_isMulti_1i1mczn_136",
13
+ "error": "_error_1i1mczn_69",
14
+ "notSelected": "_notSelected_1i1mczn_144",
15
+ "themeLight": "_themeLight_1i1mczn_148",
16
+ "searchKeyFocused": "_searchKeyFocused_1i1mczn_154",
17
+ "rock": "_rock_1i1mczn_168",
18
+ "toggle": "_toggle_1i1mczn_173",
19
+ "labelWrapper": "_labelWrapper_1i1mczn_177",
20
+ "themeDark": "_themeDark_1i1mczn_199",
21
+ "label": "_label_1i1mczn_177",
22
+ "iconsWrapper": "_iconsWrapper_1i1mczn_285",
23
+ "searchInput": "_searchInput_1i1mczn_340",
24
+ "multi": "_multi_1i1mczn_366",
25
+ "tagsContainer": "_tagsContainer_1i1mczn_375",
26
+ "tag": "_tag_1i1mczn_375",
27
+ "icon": "_icon_1i1mczn_285",
28
+ "clearIcon": "_clearIcon_1i1mczn_490"
29
29
  };
30
30
  export default styles;
package/lib/select.d.ts CHANGED
@@ -16,10 +16,6 @@ export interface SelectProps {
16
16
  * Array of options or option groups
17
17
  */
18
18
  options: SelectOptionOrGroup[];
19
- /**
20
- * Default value for select state
21
- */
22
- defaultValue?: SelectOption;
23
19
  /**
24
20
  * Is select supports clear the value
25
21
  */
@@ -55,7 +51,7 @@ export interface SelectProps {
55
51
  /**
56
52
  * Value of the select
57
53
  */
58
- value?: SelectOption;
54
+ value: SelectOption;
59
55
  /**
60
56
  * Change value callback. `value => ...`
61
57
  */
@@ -81,6 +77,7 @@ export interface SelectProps {
81
77
  * Text to display when there are no options
82
78
  */
83
79
  noOptionsMessage?: NoOptionsMessage;
80
+ name?: string;
84
81
  }
85
82
  declare const Select: React.FC<SelectProps>;
86
83
  export default Select;
package/lib/select.js CHANGED
@@ -1,14 +1,26 @@
1
+ import "core-js/modules/web.dom-collections.for-each.js";
2
+ import _defineProperty from "@babel/runtime-corejs3/helpers/esm/defineProperty";
1
3
  import _slicedToArray from "@babel/runtime-corejs3/helpers/esm/slicedToArray";
2
4
  import _objectWithoutProperties from "@babel/runtime-corejs3/helpers/esm/objectWithoutProperties";
3
- var _excluded = ["options", "size", "mode", "theme", "className", "defaultValue", "value", "onChange", "placeholder", "isClearable", "isLoading", "isDisabled", "isSearchable", "noOptionsMessage", "placement"];
5
+ var _excluded = ["options", "size", "mode", "theme", "className", "value", "onChange", "placeholder", "isClearable", "isLoading", "isDisabled", "isSearchable", "noOptionsMessage", "placement"];
6
+
7
+ function ownKeys(object, enumerableOnly) { var keys = _Object$keys(object); if (_Object$getOwnPropertySymbols) { var symbols = _Object$getOwnPropertySymbols(object); if (enumerableOnly) { symbols = _filterInstanceProperty(symbols).call(symbols, function (sym) { return _Object$getOwnPropertyDescriptor(object, sym).enumerable; }); } keys.push.apply(keys, symbols); } return keys; }
8
+
9
+ function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (_Object$getOwnPropertyDescriptors) { Object.defineProperties(target, _Object$getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, _Object$getOwnPropertyDescriptor(source, key)); }); } } return target; }
10
+
4
11
  import _filterInstanceProperty from "@babel/runtime-corejs3/core-js-stable/instance/filter";
5
12
  import _concatInstanceProperty from "@babel/runtime-corejs3/core-js-stable/instance/concat";
6
13
  import _mapInstanceProperty from "@babel/runtime-corejs3/core-js-stable/instance/map";
14
+ import _Object$keys from "@babel/runtime-corejs3/core-js-stable/object/keys";
15
+ import _Object$getOwnPropertySymbols from "@babel/runtime-corejs3/core-js-stable/object/get-own-property-symbols";
16
+ import _Object$getOwnPropertyDescriptor from "@babel/runtime-corejs3/core-js-stable/object/get-own-property-descriptor";
17
+ import _Object$getOwnPropertyDescriptors from "@babel/runtime-corejs3/core-js-stable/object/get-own-property-descriptors";
7
18
  import "core-js/modules/es.array.join.js";
8
19
  import "core-js/modules/es.regexp.constructor.js";
9
20
  import "core-js/modules/es.regexp.exec.js";
10
21
  import "core-js/modules/es.regexp.to-string.js";
11
- import React, { useRef, useState, useReducer, useEffect, useCallback } from 'react';
22
+ import "core-js/modules/es.function.name.js";
23
+ import React, { useRef, useState, useEffect, useMemo, useCallback } from 'react';
12
24
  import PropTypes from 'prop-types';
13
25
  import scrollIntoView from 'scroll-into-view-if-needed';
14
26
  import Dropdown from '@rescui/dropdown';
@@ -17,22 +29,21 @@ import { useTheme } from '@rescui/ui-contexts';
17
29
  import SelectTrigger from './parts/trigger.js';
18
30
  import FormTriggerWrapper from './parts/form-trigger-wrapper.js';
19
31
  import { optionType, optionsGroupType, noOptionsMessageConfigType } from './common-prop-types.js';
20
- import { selectReducer, getInitialState } from './state/select/reducer.js';
21
- import { setGroups, setSelectedValue, setSelectedIndex, closeMenu, setSearchString, clearSelectedAndCloseMenu, openMenu, setCursorIndex, cursorMovedDown, cursorMovedUp } from './state/select/actions.js';
22
- import { getSelected, isEmpty, getPlainOptions, withoutGroupsLabel, OptionGroupTypes, getOptionValue, getSelectedValue, isIndexMatchCursor, getGroups, getCursorIndex } from './state/select/selectors.js';
23
- import { convertToOptionGroupsIfNeeded, reverseTheme, getEmptyMessage, escapeRegex, shouldOpenSelect, calculateMaxHeight } from './utils.js';
24
- import { ESCAPE, BACKSPACE, ARROW_DOWN, ARROW_UP, ENTER, SPACE, TAB } from './key-codes.js';
32
+ import { useStrongMemo, getDefaultCursorIndex, isGroupsEmpty, getMovedCursorIndex, shouldOpenSelect, isIndexMatchCursor, reverseTheme, getPlainOptionsFromGroups, getEmptyMessage, withoutGroupsLabel, OptionGroupTypes, getOptionValue, convertToOptionGroupsIfNeeded, escapeRegex, calculateMaxHeight } from './utils.js';
33
+ import { ARROW_DOWN, ARROW_UP, ENTER, SPACE, TAB, ESCAPE, BACKSPACE } from './key-codes.js';
25
34
  import styles from './parts/common-select.module.pcss.js'; // eslint-disable-next-line complexity
26
35
 
27
36
  var Option = function Option(_ref) {
28
- var state = _ref.state,
37
+ var groups = _ref.groups,
38
+ selected = _ref.selected,
39
+ cursorIndex = _ref.cursorIndex,
29
40
  size = _ref.size,
30
41
  item = _ref.item,
31
42
  isLastItem = _ref.isLastItem,
32
43
  highlightedItemRef = _ref.highlightedItemRef,
33
44
  handleSelectIndex = _ref.handleSelectIndex,
34
45
  handleHighlightIndex = _ref.handleHighlightIndex;
35
- var marginInPx = withoutGroupsLabel(state) ? 0 : {
46
+ var marginInPx = withoutGroupsLabel(groups) ? 0 : {
36
47
  l: 12,
37
48
  m: 6,
38
49
  s: 0
@@ -44,8 +55,8 @@ var Option = function Option(_ref) {
44
55
  var index = item.index,
45
56
  label = item.label;
46
57
  var value = getOptionValue(item);
47
- var isSelected = value === getSelectedValue(state);
48
- var isHighlighted = isIndexMatchCursor(state, index);
58
+ var isSelected = selected && value === getOptionValue(selected);
59
+ var isHighlighted = isIndexMatchCursor(cursorIndex, index);
49
60
  return /*#__PURE__*/React.createElement(MenuItem, {
50
61
  selected: isSelected,
51
62
  highlighted: isHighlighted,
@@ -98,7 +109,7 @@ var getOptionKey = function getOptionKey(item, i) {
98
109
 
99
110
 
100
111
  var Select = function Select(_ref2) {
101
- var _context3;
112
+ var _context4;
102
113
 
103
114
  var options = _ref2.options,
104
115
  _ref2$size = _ref2.size,
@@ -108,8 +119,6 @@ var Select = function Select(_ref2) {
108
119
  themeFromProps = _ref2.theme,
109
120
  _ref2$className = _ref2.className,
110
121
  className = _ref2$className === void 0 ? null : _ref2$className,
111
- _ref2$defaultValue = _ref2.defaultValue,
112
- defaultValue = _ref2$defaultValue === void 0 ? null : _ref2$defaultValue,
113
122
  _ref2$value = _ref2.value,
114
123
  value = _ref2$value === void 0 ? undefined : _ref2$value,
115
124
  onChange = _ref2.onChange,
@@ -139,36 +148,73 @@ var Select = function Select(_ref2) {
139
148
 
140
149
  var skipScrollingRef = useRef(false);
141
150
 
142
- var _useReducer = useReducer(selectReducer, getInitialState(convertToOptionGroupsIfNeeded(options), defaultValue)),
143
- _useReducer2 = _slicedToArray(_useReducer, 2),
144
- state = _useReducer2[0],
145
- dispatch = _useReducer2[1];
151
+ var _useState3 = useState(''),
152
+ _useState4 = _slicedToArray(_useState3, 2),
153
+ searchString = _useState4[0],
154
+ setSearchString = _useState4[1];
146
155
 
147
- useEffect(function () {
148
- dispatch(setGroups(convertToOptionGroupsIfNeeded(options)));
156
+ var groups = useStrongMemo(function () {
157
+ return convertToOptionGroupsIfNeeded(options);
149
158
  }, [options]);
159
+ var filteredGroups = useStrongMemo(function () {
160
+ if (searchString === '') {
161
+ return groups;
162
+ }
163
+
164
+ var filter = new RegExp("(?:^|\\s)".concat(escapeRegex(searchString)), 'i');
165
+ return _mapInstanceProperty(groups).call(groups, function (g) {
166
+ var _context3;
167
+
168
+ return _objectSpread(_objectSpread({}, g), {}, {
169
+ options: _filterInstanceProperty(_context3 = g.options).call(_context3, function (_ref3) {
170
+ var label = _ref3.label;
171
+ return filter.test(label);
172
+ })
173
+ });
174
+ });
175
+ }, [searchString, groups]);
176
+
177
+ var _useState5 = useState(false),
178
+ _useState6 = _slicedToArray(_useState5, 2),
179
+ menuIsOpen = _useState6[0],
180
+ setMenuIsOpen = _useState6[1];
181
+
182
+ var _useState7 = useState(function () {
183
+ return getDefaultCursorIndex(filteredGroups);
184
+ }),
185
+ _useState8 = _slicedToArray(_useState7, 2),
186
+ cursorIndex = _useState8[0],
187
+ setCursorIndex = _useState8[1];
188
+
150
189
  useEffect(function () {
151
- dispatch(setSelectedValue(value));
152
- }, [value]);
153
- var selected = value ? value : getSelected(state);
154
- var isEmptyMenu = isEmpty(state);
155
- var menuIsOpen = state.menuIsOpen;
156
-
157
- var handleSelectIndex = function handleSelectIndex(index) {
158
- var selectedOption = getGroups(state)[index[0]].options[index[1]];
159
- dispatch(setSelectedIndex(index));
190
+ setCursorIndex(getDefaultCursorIndex(filteredGroups));
191
+
192
+ if (searchString !== '') {
193
+ setMenuIsOpen(true);
194
+ }
195
+ }, [searchString, filteredGroups]);
196
+ var isEmptyMenu = useMemo(function () {
197
+ return isGroupsEmpty(filteredGroups);
198
+ }, [filteredGroups]);
199
+ var handleSelectIndex = useCallback(function (index) {
200
+ var _index = _slicedToArray(index, 2),
201
+ grpIndex = _index[0],
202
+ optIndex = _index[1];
203
+
204
+ var selectedOption = filteredGroups[grpIndex].options[optIndex];
205
+ setMenuIsOpen(false);
206
+ setSearchString('');
160
207
  setIsKeyboardNavigating(false);
161
208
 
162
209
  if (onChange) {
163
210
  onChange(selectedOption);
164
211
  }
165
- };
166
-
212
+ }, [onChange, filteredGroups]);
167
213
  useEffect(function () {
168
214
  if (dropdownRef.current) {
169
215
  dropdownRef.current.scheduleUpdate();
170
216
  }
171
- }, [state.searchString]);
217
+ }, [searchString]);
172
218
  var handleMouseMove = useCallback(function () {
173
219
  return setIsKeyboardNavigating(false);
174
220
  }, []);
@@ -188,7 +234,7 @@ var Select = function Select(_ref2) {
188
234
  } else {
189
235
  var elementToScrollTo = highlightedItemRef.current;
190
236
 
191
- if (state.cursorIndex[0] === 0 && state.cursorIndex[1] === 0) {
237
+ if (cursorIndex[0] === 0 && cursorIndex[1] === 0) {
192
238
  var groupHeader = highlightedItemRef.current.previousSibling;
193
239
 
194
240
  if (groupHeader) {
@@ -204,25 +250,22 @@ var Select = function Select(_ref2) {
204
250
  });
205
251
  }
206
252
  }
207
- }, [highlightedItemRef, state.cursorIndex, isKeyboardNavigating]);
208
-
209
- var handleClose = function handleClose() {
210
- dispatch(closeMenu());
253
+ }, [highlightedItemRef, cursorIndex, isKeyboardNavigating]);
254
+ var handleClose = useCallback(function () {
255
+ setSearchString('');
256
+ setMenuIsOpen(false);
211
257
  setIsKeyboardNavigating(false);
212
- }; // eslint-disable-next-line complexity
213
-
214
-
215
- var handleKeyNavigation = function handleKeyNavigation(e) {
258
+ }, []);
259
+ var handleKeyNavigation = useCallback( // eslint-disable-next-line complexity
260
+ function (e) {
216
261
  if (e.key === ARROW_DOWN || e.key === ARROW_UP) {
217
262
  var isDownDirection = e.key === ARROW_DOWN;
218
- dispatch(isDownDirection ? cursorMovedDown() : cursorMovedUp());
263
+ setCursorIndex(getMovedCursorIndex(filteredGroups, cursorIndex, isDownDirection));
219
264
  setIsKeyboardNavigating(true);
220
265
  e.preventDefault();
221
266
  }
222
267
 
223
268
  if (e.key === ENTER || !isSearchable && e.key === SPACE) {
224
- var cursorIndex = getCursorIndex(state);
225
-
226
269
  if (cursorIndex !== null) {
227
270
  handleSelectIndex(cursorIndex);
228
271
  } else {
@@ -235,35 +278,29 @@ var Select = function Select(_ref2) {
235
278
  if (e.key === TAB) {
236
279
  handleClose();
237
280
  }
238
- };
239
-
240
- var handleClick = function handleClick() {
281
+ }, [filteredGroups, cursorIndex, handleClose, handleSelectIndex, isSearchable]);
282
+ var handleClick = useCallback(function () {
241
283
  if (isDisabled) {
242
284
  return;
243
285
  }
244
286
 
245
- var action = menuIsOpen ? closeMenu() : openMenu();
246
- dispatch(action);
247
- };
248
-
249
- var handleSearchInputChange = function handleSearchInputChange(searchValue) {
250
- var filter = new RegExp("(?:^|\\s)".concat(escapeRegex(searchValue)), 'i');
251
- dispatch(setSearchString(searchValue, function (_ref3) {
252
- var label = _ref3.label;
253
- return filter.test(label);
254
- }));
255
- };
256
-
257
- var handleClearClick = function handleClearClick() {
258
- dispatch(clearSelectedAndCloseMenu());
287
+ setMenuIsOpen(function (currentMenuIsOpen) {
288
+ return !currentMenuIsOpen;
289
+ });
290
+ setSearchString('');
291
+ }, [isDisabled]);
292
+ var handleSearchInputChange = useCallback(function (searchValue) {
293
+ return setSearchString(searchValue);
294
+ }, []);
295
+ var handleClearClick = useCallback(function () {
296
+ setCursorIndex(getDefaultCursorIndex(filteredGroups));
297
+ setMenuIsOpen(false);
259
298
 
260
299
  if (onChange) {
261
300
  onChange(null);
262
301
  }
263
- }; // eslint-disable-next-line complexity
264
-
265
-
266
- var handleTriggerKeyDown = function handleTriggerKeyDown(e) {
302
+ }, [filteredGroups, onChange]);
303
+ var handleTriggerKeyDown = useCallback(function (e) {
267
304
  if (e.key === ESCAPE) {
268
305
  handleClose();
269
306
  e.preventDefault();
@@ -281,7 +318,8 @@ var Select = function Select(_ref2) {
281
318
  var isTriggerTarget = trigger === target;
282
319
 
283
320
  if (shouldOpenSelect(e.key, isTriggerTarget)) {
284
- dispatch(openMenu());
321
+ setMenuIsOpen(true);
322
+ setSearchString('');
285
323
  setIsKeyboardNavigating(true);
286
324
  skipScrollingRef.current = true;
287
325
  trigger.focus();
@@ -294,14 +332,12 @@ var Select = function Select(_ref2) {
294
332
  e.preventDefault();
295
333
  }
296
334
  }
297
- };
298
-
299
- var handleHighlightIndex = function handleHighlightIndex(index) {
300
- if (!isIndexMatchCursor(state, index)) {
301
- dispatch(setCursorIndex(index));
335
+ }, [menuIsOpen, isDisabled, isClearable, handleClose, handleClearClick, handleKeyNavigation]);
336
+ var handleHighlightIndex = useCallback(function (index) {
337
+ if (!isIndexMatchCursor(cursorIndex, index)) {
338
+ setCursorIndex(index);
302
339
  }
303
- };
304
-
340
+ }, [cursorIndex]);
305
341
  var maxHeight = calculateMaxHeight(size);
306
342
  return /*#__PURE__*/React.createElement(Dropdown, {
307
343
  theme: theme,
@@ -322,20 +358,24 @@ var Select = function Select(_ref2) {
322
358
  size: size,
323
359
  error: restProps.error,
324
360
  label: restProps.label,
325
- note: restProps.note
326
- }, /*#__PURE__*/React.createElement(SelectTrigger, {
361
+ note: restProps.note,
362
+ onKeyDown: handleTriggerKeyDown
363
+ }, restProps.name && /*#__PURE__*/React.createElement("input", {
364
+ type: "hidden",
365
+ name: restProps.name,
366
+ value: value && value.value || ''
367
+ }), /*#__PURE__*/React.createElement(SelectTrigger, {
327
368
  theme: theme,
328
369
  mode: mode,
329
370
  size: size,
330
371
  isOpen: menuIsOpen,
331
372
  triggerRef: ref,
332
- onKeyDown: handleTriggerKeyDown,
333
- selected: selected,
373
+ selected: value,
334
374
  placeholder: placeholder,
335
375
  isClearable: isClearable,
336
376
  isLoading: isLoading,
337
377
  isDisabled: isDisabled,
338
- searchInput: state.searchString,
378
+ searchInput: searchString,
339
379
  isSearchable: isSearchable,
340
380
  onSearchChange: handleSearchInputChange,
341
381
  onClick: handleClick,
@@ -351,12 +391,14 @@ var Select = function Select(_ref2) {
351
391
  theme: mode === 'rock' ? reverseTheme(theme) : theme,
352
392
  disableCursor: isKeyboardNavigating,
353
393
  className: styles.menu
354
- }, !isEmptyMenu ? _mapInstanceProperty(_context3 = getPlainOptions(state)).call(_context3, function (item, i, collection) {
394
+ }, !isEmptyMenu ? _mapInstanceProperty(_context4 = getPlainOptionsFromGroups(filteredGroups)).call(_context4, function (item, i, collection) {
355
395
  return /*#__PURE__*/React.createElement(Option, {
356
396
  item: item,
357
397
  isLastItem: i === collection.length - 1,
358
398
  key: getOptionKey(item, i),
359
- state: state,
399
+ groups: filteredGroups,
400
+ selected: value,
401
+ cursorIndex: cursorIndex,
360
402
  size: size,
361
403
  highlightedItemRef: highlightedItemRef,
362
404
  handleSelectIndex: handleSelectIndex,
@@ -364,13 +406,12 @@ var Select = function Select(_ref2) {
364
406
  });
365
407
  }) : /*#__PURE__*/React.createElement(MenuItem, {
366
408
  disabled: true
367
- }, getEmptyMessage(isLoading, isSearchable && state.searchString.length > 0, noOptionsMessage))));
409
+ }, getEmptyMessage(isLoading, isSearchable && searchString.length > 0, noOptionsMessage))));
368
410
  };
369
411
 
370
412
  Select.propTypes = {
371
413
  className: PropTypes.string,
372
414
  options: PropTypes.oneOfType([PropTypes.arrayOf(optionType), PropTypes.arrayOf(optionsGroupType)]),
373
- defaultValue: optionType,
374
415
  value: optionType,
375
416
  onChange: PropTypes.func,
376
417
  size: PropTypes.oneOf(['l', 'm', 's']),
@@ -386,6 +427,7 @@ Select.propTypes = {
386
427
  id: PropTypes.string,
387
428
  note: PropTypes.node,
388
429
  noOptionsMessage: PropTypes.oneOfType([PropTypes.string, noOptionsMessageConfigType]),
389
- placement: PropTypes.oneOf(['auto-start', 'auto', 'auto-end', 'top-start', 'top', 'top-end', 'right-start', 'right', 'right-end', 'bottom-end', 'bottom', 'bottom-start', 'left-end', 'left', 'left-start'])
430
+ placement: PropTypes.oneOf(['auto-start', 'auto', 'auto-end', 'top-start', 'top', 'top-end', 'right-start', 'right', 'right-end', 'bottom-end', 'bottom', 'bottom-start', 'left-end', 'left', 'left-start']),
431
+ name: PropTypes.string
390
432
  };
391
433
  export default Select;
package/lib/types.d.ts CHANGED
@@ -14,34 +14,6 @@ export declare type SelectOptionOrGroup = SelectOption | SelectOptionsGroup;
14
14
  export declare type SelectOptions = SelectOptionOrGroup[];
15
15
  export declare type Groups = SelectOptionsGroup[];
16
16
  export declare type Index = [number, number];
17
- export declare type State = {
18
- groups: Groups;
19
- menuIsOpen: boolean;
20
- selected: SelectOption | SelectOption[];
21
- searchString: string;
22
- filteredGroups: Groups;
23
- cursorIndex: Index;
24
- hideSelected?: boolean;
25
- groupsWithoutSelected?: Groups;
26
- };
27
- export declare type PartialState = Partial<State>;
28
- export interface GetGroups {
29
- (state: State): Groups;
30
- }
31
- export interface IsEmpty {
32
- (state: State): boolean;
33
- }
34
- export declare type Overrides = {
35
- getGroups?: GetGroups;
36
- isEmpty?: IsEmpty;
37
- };
38
- export declare type Action = {
39
- type: string;
40
- [key: string]: any;
41
- };
42
- export interface SelectReducer {
43
- (state: State, action: Action): State;
44
- }
45
17
  export declare type FilterFn = (option: SelectOption) => boolean;
46
18
  export declare type NoOptionsMessageConfig = {
47
19
  noOptions: string;
package/lib/utils.d.ts CHANGED
@@ -1,8 +1,22 @@
1
1
  import { Theme } from '@rescui/ui-contexts';
2
2
  import type { SelectOptionOrGroup, SelectOptionsGroup, NoOptionsMessage, SelectSize } from './types';
3
+ import { Groups, Index, SelectOption } from './types';
3
4
  export declare function shouldOpenSelect(key: string, isTriggerTarget?: boolean): boolean;
4
5
  export declare function getEmptyMessage(isLoading: boolean, isNothingFound: boolean, noOptionsMessage: NoOptionsMessage): string;
5
6
  export declare function escapeRegex(str: string): string;
6
7
  export declare function convertToOptionGroupsIfNeeded(optionsOrGroups?: SelectOptionOrGroup[]): SelectOptionsGroup[];
7
8
  export declare const calculateMaxHeight: (size: SelectSize) => number;
8
9
  export declare const reverseTheme: (theme: Theme) => "light" | "dark";
10
+ export declare function getOptionValue(option: SelectOption): string;
11
+ export declare const OptionGroupTypes: {
12
+ HEADER: string;
13
+ OPTION: string;
14
+ DIVIDER: string;
15
+ };
16
+ export declare const getDefaultCursorIndex: (groups: Groups) => Index;
17
+ export declare const getPlainOptionsFromGroups: (groups: Groups) => any[];
18
+ export declare function isGroupsEmpty(groups: Groups): boolean;
19
+ export declare function useStrongMemo<T>(callback: () => T, deps: unknown[]): T;
20
+ export declare function getMovedCursorIndex(groups: Groups, currentCursorIndex: Index, isDownDirection: boolean): Index;
21
+ export declare const isIndexMatchCursor: (cursorIndex: Index, index: Index) => boolean;
22
+ export declare const withoutGroupsLabel: (groups: Groups) => boolean;