@cloud-ru/ds-fields 1.0.2-preview-ece1f136.0 → 1.0.2-preview-c048fbb9.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": "@cloud-ru/ds-fields",
3
- "version": "1.0.2-preview-ece1f136.0",
3
+ "version": "1.0.2-preview-c048fbb9.0",
4
4
  "description": "Поля ввода с единой обёрткой label/caption/hint/error и общими осями size/validationState — текст, пароль, число, ползунок, дата, время, выбор, цвет.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -42,21 +42,21 @@
42
42
  "@cloud-ru/ds-adaptive": "1.0.0",
43
43
  "@cloud-ru/ds-bottom-sheet": "1.0.0",
44
44
  "@cloud-ru/ds-button": "1.0.0",
45
- "@cloud-ru/ds-calendar": "1.0.1",
45
+ "@cloud-ru/ds-calendar": "1.0.2-preview-c048fbb9.0",
46
46
  "@cloud-ru/ds-color-picker": "1.0.0",
47
- "@cloud-ru/ds-divider": "1.0.0",
48
47
  "@cloud-ru/ds-dropdown": "1.0.0",
49
48
  "@cloud-ru/ds-field-decorator": "1.0.0",
49
+ "@cloud-ru/ds-divider": "1.0.0",
50
50
  "@cloud-ru/ds-icons": "1.0.0",
51
+ "@cloud-ru/ds-list": "1.1.1-preview-c048fbb9.0",
51
52
  "@cloud-ru/ds-input-private": "1.0.0",
52
- "@cloud-ru/ds-list": "1.1.0",
53
53
  "@cloud-ru/ds-loader": "1.0.0",
54
- "@cloud-ru/ds-scroll": "1.0.0",
55
54
  "@cloud-ru/ds-materials": "1.0.0",
55
+ "@cloud-ru/ds-scroll": "1.0.0",
56
56
  "@cloud-ru/ds-skeleton": "1.0.0",
57
57
  "@cloud-ru/ds-slider": "1.0.0",
58
58
  "@cloud-ru/ds-tag": "1.0.0",
59
- "@cloud-ru/ds-tooltip": "1.0.0",
60
- "@cloud-ru/ds-utils": "1.0.0"
59
+ "@cloud-ru/ds-utils": "1.0.0",
60
+ "@cloud-ru/ds-tooltip": "1.0.0"
61
61
  }
62
62
  }
@@ -37,16 +37,7 @@ import {
37
37
  import fieldStyles from '../shared/styles.module.scss';
38
38
  import styles from './styles.module.scss';
39
39
  import { FieldSelectProps } from './types';
40
- import {
41
- extractAppearance,
42
- extractLabel,
43
- filterItems,
44
- findItem,
45
- flatten,
46
- isMultiple,
47
- TAG_SIZE_MAP,
48
- WithIdContent,
49
- } from './utils';
40
+ import { extractAppearance, extractLabel, filterItems, findItem, isMultiple, TAG_SIZE_MAP } from './utils';
50
41
 
51
42
  export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(function FieldSelect(props, ref) {
52
43
  const {
@@ -159,19 +150,6 @@ export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(functi
159
150
 
160
151
  const allItems = useMemo(() => [...(pinTop ?? []), ...items, ...(pinBottom ?? [])], [items, pinTop, pinBottom]);
161
152
 
162
- // Выбранное значение переживает смену `items` (серверный поиск, ленивая подгрузка).
163
- const seenItems = useRef(new Map<ItemId, WithIdContent>());
164
-
165
- const resolveItem = useMemo(() => {
166
- for (const item of flatten(allItems)) {
167
- if (item.id !== undefined) {
168
- seenItems.current.set(item.id, item);
169
- }
170
- }
171
-
172
- return (id: ItemId) => findItem(allItems, id) ?? seenItems.current.get(id);
173
- }, [allItems]);
174
-
175
153
  const selectedPairs = useMemo(() => {
176
154
  if (!multiple || multipleValue.length === 0) {
177
155
  return [];
@@ -179,7 +157,7 @@ export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(functi
179
157
 
180
158
  // Неизвестное значение (ещё не загружены опции) показываем по его id, не теряем (паритет с легаси).
181
159
  return multipleValue.map(id => {
182
- const item = resolveItem(id);
160
+ const item = findItem(allItems, id);
183
161
 
184
162
  return {
185
163
  id,
@@ -188,7 +166,7 @@ export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(functi
188
166
  appearance: extractAppearance(item),
189
167
  };
190
168
  });
191
- }, [multiple, multipleValue, resolveItem]);
169
+ }, [allItems, multiple, multipleValue]);
192
170
 
193
171
  const formatPair = useCallback(
194
172
  (pair: { id: ItemId; label: string }) => (selectedOptionFormatter ? selectedOptionFormatter(pair) : pair.label),
@@ -201,7 +179,7 @@ export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(functi
201
179
  return '';
202
180
  }
203
181
 
204
- const item = resolveItem(singleValue);
182
+ const item = findItem(allItems, singleValue);
205
183
  const label = item ? extractLabel(item) : String(singleValue);
206
184
 
207
185
  return formatPair({ id: singleValue, label });
@@ -216,7 +194,7 @@ export const FieldSelect = forwardRef<HTMLInputElement, FieldSelectProps>(functi
216
194
  }
217
195
 
218
196
  return selectedPairs.map(formatPair).join(', ');
219
- }, [multiple, singleValue, selectedPairs, chips, props, formatPair, resolveItem]);
197
+ }, [allItems, multiple, singleValue, selectedPairs, chips, props, formatPair]);
220
198
 
221
199
  // Строка поиска: controlled через `search.value`, иначе локальный state. Auto-sync к выбранному
222
200
  // значению делаем через СТАБИЛЬНЫЙ setLocalInput, а не через setInputValue в deps эффекта —
@@ -14,7 +14,9 @@ import {
14
14
  MouseEvent,
15
15
  ReactNode,
16
16
  useCallback,
17
+ useEffect,
17
18
  useMemo,
19
+ useReducer,
18
20
  useRef,
19
21
  useState,
20
22
  } from 'react';
@@ -170,6 +172,12 @@ export const FieldTextArea = forwardRef<HTMLTextAreaElement, FieldTextAreaProps>
170
172
  const [focusVisible, setFocusVisible] = useState(false);
171
173
  const [hover, setHover] = useState(false);
172
174
 
175
+ // autosize меряет высоту до того, как ThemeScope навесит классы темы — пересчитываем после mount.
176
+ const [, remeasure] = useReducer((tick: number) => tick + 1, 0);
177
+ useEffect(() => {
178
+ remeasure();
179
+ }, []);
180
+
173
181
  const resolvedAutoFocus = useAdaptiveAutoFocus(autoFocus, layoutPresets);
174
182
 
175
183
  // controlled/uncontrolled: useValueControl держит внутреннее состояние при отсутствии `value`,