@sima-land/ui-nucleons 41.2.2 → 41.3.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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sima-land/ui-nucleons",
3
- "version": "41.2.2",
3
+ "version": "41.3.0",
4
4
  "repository": "ssh://git@github.com:sima-land/ui-nucleons.git",
5
5
  "author": "www.sima-land.ru team",
6
6
  "license": "Apache-2.0",
package/select/index.d.ts CHANGED
@@ -22,5 +22,5 @@ export interface SelectProps extends Omit<TextFieldProps, 'style'> {
22
22
  * @param props Свойства.
23
23
  * @return Элемент.
24
24
  */
25
- export declare const Select: React.FC<SelectProps>;
25
+ export declare const Select: ({ options, optionSize, onSelect, style, className, label, onClick, value, loading, onMenuToggle, renderOption, "data-testid": dataTestId, ...restProps }: SelectProps) => JSX.Element;
26
26
  export {};
package/select/index.js CHANGED
@@ -45,6 +45,7 @@ const up_1 = __importDefault(require("@sima-land/ui-quarks/icons/16x16/Stroked/A
45
45
  const select_module_scss_1 = __importDefault(require("./select.module.scss"));
46
46
  const colors_1 = require("../colors");
47
47
  const dropdown_loading_1 = require("../_internal/dropdown-loading");
48
+ const hooks_1 = require("../hooks");
48
49
  const cx = bind_1.default.bind(select_module_scss_1.default);
49
50
  /**
50
51
  * Поле выбора из списка.
@@ -53,30 +54,43 @@ const cx = bind_1.default.bind(select_module_scss_1.default);
53
54
  */
54
55
  const Select = (_a) => {
55
56
  var { options, optionSize, onSelect, style, className, label, onClick, value, loading, onMenuToggle, renderOption = String, 'data-testid': dataTestId } = _a, restProps = __rest(_a, ["options", "optionSize", "onSelect", "style", "className", "label", "onClick", "value", "loading", "onMenuToggle", "renderOption", 'data-testid']);
57
+ const rootRef = (0, react_1.useRef)(null);
56
58
  const fieldRef = (0, react_1.useRef)(null);
57
59
  const menuRef = (0, react_1.useRef)(null);
58
60
  const [opened, toggleMenu] = (0, react_1.useState)(false);
59
61
  const ArrowSVG = opened ? up_1.default : down_1.default;
60
62
  (0, react_1.useEffect)(() => {
61
- opened && menuRef.current.focus();
63
+ opened && menuRef.current && menuRef.current.focus();
62
64
  onMenuToggle && onMenuToggle(opened);
63
65
  }, [opened]);
64
- return (react_1.default.createElement("div", { style: style, className: cx('root', className), "data-testid": dataTestId },
65
- react_1.default.createElement(text_field_1.TextField, Object.assign({}, restProps, { readOnly: true, "data-testid": 'select:field', ref: fieldRef, variant: 'desktop', label: label, value: value, multiline: false, focused: opened, onClick: e => {
66
- toggleMenu(o => !o);
67
- onClick && onClick(e);
68
- }, onBlur: ({ relatedTarget }) => {
69
- relatedTarget !== menuRef.current && toggleMenu(false);
70
- }, onKeyDown: (e) => {
71
- e.key === 'Enter' && toggleMenu(true);
72
- }, className: cx('field'), endAdornment: react_1.default.createElement(ArrowSVG, { fill: colors_1.COLORS.get('gray38') }) })),
73
- opened && (loading || options.length > 0) && (react_1.default.createElement(dropdown_1.Dropdown, Object.assign({}, (0, dropdown_2.placeDropdown)(restProps.size), { ref: menuRef, "data-testid": 'select:menu', tabIndex: -1, className: cx('menu'), onBlur: () => {
74
- toggleMenu(false);
75
- }, role: 'menu', onKeyDown: (event) => {
66
+ (0, hooks_1.useOutsideClick)(rootRef, toggleMenu.bind(null, false));
67
+ return (react_1.default.createElement("div", { ref: rootRef, style: style, className: cx('root', className), "data-testid": dataTestId },
68
+ react_1.default.createElement(text_field_1.TextField, { blockProps: {
69
+ ref: fieldRef,
70
+ tabIndex: 0,
71
+ onMouseDown: () => {
72
+ toggleMenu(a => !a);
73
+ },
74
+ onKeyDown: e => {
75
+ e.key === 'Enter' && toggleMenu(true);
76
+ },
77
+ onClick: e => {
78
+ e.preventDefault();
79
+ onClick && onClick(e);
80
+ },
81
+ }, className: select_module_scss_1.default.field, "data-testid": 'select:field', label: label, focused: opened, baseInputProps: {
82
+ // чтобы не ловить фокус на поле
83
+ style: { pointerEvents: 'none' },
84
+ tabIndex: -1,
85
+ }, value: value, multiline: false, variant: 'desktop', readOnly: true, endAdornment: react_1.default.createElement(ArrowSVG, { fill: colors_1.COLORS.get('gray38') }) }),
86
+ opened && (loading || options.length > 0) && (react_1.default.createElement(dropdown_1.Dropdown, Object.assign({}, (0, dropdown_2.placeDropdown)(restProps.size), { ref: menuRef, "data-testid": 'select:menu', role: 'menu', tabIndex: -1, className: cx('menu'), onKeyDown: event => {
76
87
  if (event.key === 'Enter') {
77
88
  toggleMenu(false);
78
89
  fieldRef.current && fieldRef.current.focus();
79
90
  }
91
+ }, onBlur: () => {
92
+ toggleMenu(false);
93
+ fieldRef.current && fieldRef.current.focus();
80
94
  } }), loading ? (react_1.default.createElement(dropdown_loading_1.DropdownLoading, { "data-testid": 'select:loading-area' })) : (options.map((option, index) => (react_1.default.createElement(dropdown_item_1.DropdownItem, { size: optionSize, key: index, role: 'menuitem', onClick: () => {
81
95
  toggleMenu(false);
82
96
  onSelect && onSelect(option);
@@ -46,6 +46,8 @@ export interface TextFieldProps extends Omit<React.InputHTMLAttributes<HTMLInput
46
46
  startAdornment?: React.ReactNode;
47
47
  /** Вариант отображения. */
48
48
  variant?: Variant;
49
+ /** Свойства элемента-блока. */
50
+ blockProps?: React.HTMLProps<HTMLDivElement>;
49
51
  /** Идентификатор для систем автоматизированного тестирования. */
50
52
  'data-testid'?: string;
51
53
  }
@@ -51,7 +51,7 @@ const modifiersToClasses = ({ disabled, failed, focused, variant, }) => cx(disab
51
51
  * @param props Свойства.
52
52
  * @return Элемент.
53
53
  */
54
- exports.TextField = (0, react_1.forwardRef)(function TextField({ autoFocus, caption, classes = {}, defaultValue, disabled, endAdornment, failed, focused: asFocused, label, onClick, onBlur, onChange, onFocus, onInput, onKeyDown, onKeyUp, placeholder, readOnly, rounds = 'all', size = exports.DEFAULTS.size, startAdornment, value, variant = 'desktop', multiline, baseInputProps = {}, className, restPlaceholder, style, 'data-testid': dataTestId, }, ref) {
54
+ exports.TextField = (0, react_1.forwardRef)(function TextField({ autoFocus, caption, classes = {}, defaultValue, disabled, endAdornment, failed, focused: asFocused, label, onClick, onBlur, onChange, onFocus, onInput, onKeyDown, onKeyUp, placeholder, readOnly, rounds = 'all', size = exports.DEFAULTS.size, startAdornment, value, variant = 'desktop', multiline, baseInputProps = {}, className, restPlaceholder, style, blockProps, 'data-testid': dataTestId, }, ref) {
55
55
  const [hasValue, toggleHasValue] = (0, react_1.useState)(isVisible(value) || isVisible(defaultValue));
56
56
  const [reallyFocused, toggleFocused] = (0, react_1.useState)(autoFocus);
57
57
  const focused = reallyFocused || Boolean(asFocused);
@@ -70,21 +70,25 @@ exports.TextField = (0, react_1.forwardRef)(function TextField({ autoFocus, capt
70
70
  (0, react_1.useImperativeHandle)(ref, () => baseInputRef.current);
71
71
  (0, react_1.useEffect)(() => toggleHasValue(Boolean(baseInputRef.current.value)));
72
72
  return (react_1.default.createElement("div", { "data-testid": dataTestId, className: cx('root', className, classes.root), style: style },
73
- react_1.default.createElement("div", { "data-testid": 'text-field:block', className: cx('reset', 'input-block', commonModifyClasses, size && `size-${size}`, focused && classes.blockFocused, multiline && 'multiline', withLabel && 'with-label', variant === 'desktop' && rounds !== 'none' && shapes_1.SmallRounds[rounds]), onClick: event => {
73
+ react_1.default.createElement("div", Object.assign({ "data-testid": 'text-field:block', className: cx('reset', 'input-block', commonModifyClasses, size && `size-${size}`, focused && classes.blockFocused, multiline && 'multiline', withLabel && 'with-label', variant === 'desktop' && rounds !== 'none' && shapes_1.SmallRounds[rounds], blockProps === null || blockProps === void 0 ? void 0 : blockProps.className), onClick: event => {
74
74
  const input = baseInputRef.current;
75
75
  onClick === null || onClick === void 0 ? void 0 : onClick(event);
76
- input && !disabled && input !== document.activeElement && input.focus();
77
- } },
76
+ input &&
77
+ !disabled &&
78
+ !event.defaultPrevented &&
79
+ input !== document.activeElement &&
80
+ input.focus();
81
+ } }, blockProps),
78
82
  !multiline && Boolean(startAdornment) && (react_1.default.createElement(box_1.Box, { display: 'flex', alignItems: 'center', marginRight: 4 }, startAdornment)),
79
83
  react_1.default.createElement("div", { className: cx('main-column') },
80
84
  withLabel && (react_1.default.createElement("label", { className: cx('label', commonModifyClasses, hasValue && 'filled', labelAsPlaceholder && 'as-placeholder'), children: label, "data-testid": 'text-field:label' })),
81
85
  react_1.default.createElement("div", { className: cx('input-wrapper') },
82
86
  react_1.default.createElement(base_input_1.BaseInput, Object.assign({}, baseInputProps, { "data-testid": 'text-field:field', multiline: multiline, ref: baseInputRef, placeholder: withLabel && labelAsPlaceholder ? undefined : placeholder, restPlaceholder: withLabel && labelAsPlaceholder ? undefined : restPlaceholder, autoFocus: autoFocus, className: cx('base-input', commonModifyClasses, classes.baseInput, size && `size-${size}`), defaultValue: defaultValue, value: value, readOnly: readOnly, disabled: disabled, onFocus: (event) => {
83
- (0, lodash_1.isFunction)(onFocus) && onFocus(event);
87
+ onFocus && onFocus(event);
84
88
  toggleHasValue(Boolean(event.target.value));
85
89
  toggleFocused(true);
86
90
  }, onBlur: (event) => {
87
- (0, lodash_1.isFunction)(onBlur) && onBlur(event);
91
+ onBlur && onBlur(event);
88
92
  toggleHasValue(Boolean(event.target.value));
89
93
  toggleFocused(false);
90
94
  }, onInput: onInput, onChange: onChange, onKeyDown: onKeyDown, onKeyUp: onKeyUp })))),