@sytechui/input 2.4.33

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.
@@ -0,0 +1,11 @@
1
+ import * as _sytechui_system from '@sytechui/system';
2
+ import { UseInputProps } from './use-input.mjs';
3
+ import 'react';
4
+ import '@sytechui/theme';
5
+ import '@react-types/textfield';
6
+
7
+ interface InputProps extends Omit<UseInputProps, "isMultiline"> {
8
+ }
9
+ declare const Input: _sytechui_system.InternalForwardRefRenderFunction<"input", InputProps, never>;
10
+
11
+ export { type InputProps, Input as default };
@@ -0,0 +1,11 @@
1
+ import * as _sytechui_system from '@sytechui/system';
2
+ import { UseInputProps } from './use-input.js';
3
+ import 'react';
4
+ import '@sytechui/theme';
5
+ import '@react-types/textfield';
6
+
7
+ interface InputProps extends Omit<UseInputProps, "isMultiline"> {
8
+ }
9
+ declare const Input: _sytechui_system.InternalForwardRefRenderFunction<"input", InputProps, never>;
10
+
11
+ export { type InputProps, Input as default };
package/dist/input.js ADDED
@@ -0,0 +1,553 @@
1
+ "use client";
2
+ "use strict";
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
7
+ var __export = (target, all) => {
8
+ for (var name in all)
9
+ __defProp(target, name, { get: all[name], enumerable: true });
10
+ };
11
+ var __copyProps = (to, from, except, desc) => {
12
+ if (from && typeof from === "object" || typeof from === "function") {
13
+ for (let key of __getOwnPropNames(from))
14
+ if (!__hasOwnProp.call(to, key) && key !== except)
15
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
16
+ }
17
+ return to;
18
+ };
19
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
20
+
21
+ // src/input.tsx
22
+ var input_exports = {};
23
+ __export(input_exports, {
24
+ default: () => input_default
25
+ });
26
+ module.exports = __toCommonJS(input_exports);
27
+ var import_shared_icons = require("@sytechui/shared-icons");
28
+ var import_react2 = require("react");
29
+ var import_system2 = require("@sytechui/system");
30
+
31
+ // src/use-input.ts
32
+ var import_system = require("@sytechui/system");
33
+ var import_use_safe_layout_effect = require("@sytechui/use-safe-layout-effect");
34
+ var import_focus = require("@react-aria/focus");
35
+ var import_theme = require("@sytechui/theme");
36
+ var import_react_utils = require("@sytechui/react-utils");
37
+ var import_interactions = require("@react-aria/interactions");
38
+ var import_shared_utils = require("@sytechui/shared-utils");
39
+ var import_utils = require("@react-stately/utils");
40
+ var import_react = require("react");
41
+ var import_textfield = require("@react-aria/textfield");
42
+ var import_form = require("@sytechui/form");
43
+ function useInput(originalProps) {
44
+ var _a, _b, _c, _d, _e, _f, _g;
45
+ const globalContext = (0, import_system.useProviderContext)();
46
+ const { validationBehavior: formValidationBehavior } = (0, import_form.useSlottedContext)(import_form.FormContext) || {};
47
+ const [props, variantProps] = (0, import_system.mapPropsVariants)(originalProps, import_theme.input.variantKeys);
48
+ const {
49
+ ref,
50
+ as,
51
+ type,
52
+ label,
53
+ baseRef,
54
+ wrapperRef,
55
+ description,
56
+ className,
57
+ classNames,
58
+ autoFocus,
59
+ startContent,
60
+ endContent,
61
+ onClear,
62
+ onChange,
63
+ validationState,
64
+ validationBehavior = (_a = formValidationBehavior != null ? formValidationBehavior : globalContext == null ? void 0 : globalContext.validationBehavior) != null ? _a : "native",
65
+ innerWrapperRef: innerWrapperRefProp,
66
+ onValueChange = () => {
67
+ },
68
+ ...otherProps
69
+ } = props;
70
+ const handleValueChange = (0, import_react.useCallback)(
71
+ (value) => {
72
+ onValueChange(value != null ? value : "");
73
+ },
74
+ [onValueChange]
75
+ );
76
+ const [isFocusWithin, setFocusWithin] = (0, import_react.useState)(false);
77
+ const Component = as || "div";
78
+ const disableAnimation = (_c = (_b = originalProps.disableAnimation) != null ? _b : globalContext == null ? void 0 : globalContext.disableAnimation) != null ? _c : false;
79
+ const domRef = (0, import_react_utils.useDOMRef)(ref);
80
+ const baseDomRef = (0, import_react_utils.useDOMRef)(baseRef);
81
+ const inputWrapperRef = (0, import_react_utils.useDOMRef)(wrapperRef);
82
+ const innerWrapperRef = (0, import_react_utils.useDOMRef)(innerWrapperRefProp);
83
+ const [inputValue, setInputValue] = (0, import_utils.useControlledState)(
84
+ props.value,
85
+ (_d = props.defaultValue) != null ? _d : "",
86
+ handleValueChange
87
+ );
88
+ const isFileTypeInput = type === "file";
89
+ const hasUploadedFiles = ((_g = (_f = (_e = domRef == null ? void 0 : domRef.current) == null ? void 0 : _e.files) == null ? void 0 : _f.length) != null ? _g : 0) > 0;
90
+ const isFilledByDefault = ["date", "time", "month", "week", "range"].includes(type);
91
+ const isFilled = !(0, import_shared_utils.isEmpty)(inputValue) || isFilledByDefault || hasUploadedFiles;
92
+ const isFilledWithin = isFilled || isFocusWithin;
93
+ const isHiddenType = type === "hidden";
94
+ const isMultiline = originalProps.isMultiline;
95
+ const baseStyles = (0, import_theme.cn)(classNames == null ? void 0 : classNames.base, className, isFilled ? "is-filled" : "");
96
+ const handleClear = (0, import_react.useCallback)(() => {
97
+ var _a2;
98
+ if (isFileTypeInput) {
99
+ domRef.current.value = "";
100
+ } else {
101
+ setInputValue("");
102
+ }
103
+ onClear == null ? void 0 : onClear();
104
+ (_a2 = domRef.current) == null ? void 0 : _a2.focus();
105
+ }, [setInputValue, onClear, isFileTypeInput]);
106
+ (0, import_use_safe_layout_effect.useSafeLayoutEffect)(() => {
107
+ if (!domRef.current) return;
108
+ setInputValue(domRef.current.value);
109
+ }, [domRef.current]);
110
+ const {
111
+ labelProps,
112
+ inputProps,
113
+ isInvalid: isAriaInvalid,
114
+ validationErrors,
115
+ validationDetails,
116
+ descriptionProps,
117
+ errorMessageProps
118
+ } = (0, import_textfield.useTextField)(
119
+ {
120
+ ...originalProps,
121
+ validationBehavior,
122
+ autoCapitalize: originalProps.autoCapitalize,
123
+ value: inputValue,
124
+ "aria-label": originalProps.label ? originalProps["aria-label"] : (0, import_shared_utils.safeAriaLabel)(originalProps["aria-label"], originalProps.placeholder),
125
+ inputElementType: isMultiline ? "textarea" : "input",
126
+ onChange: setInputValue
127
+ },
128
+ domRef
129
+ );
130
+ if (isFileTypeInput) {
131
+ delete inputProps.value;
132
+ delete inputProps.onChange;
133
+ }
134
+ const { isFocusVisible, isFocused, focusProps } = (0, import_focus.useFocusRing)({
135
+ autoFocus,
136
+ isTextInput: true
137
+ });
138
+ const { isHovered, hoverProps } = (0, import_interactions.useHover)({ isDisabled: !!(originalProps == null ? void 0 : originalProps.isDisabled) });
139
+ const { isHovered: isLabelHovered, hoverProps: labelHoverProps } = (0, import_interactions.useHover)({
140
+ isDisabled: !!(originalProps == null ? void 0 : originalProps.isDisabled)
141
+ });
142
+ const { focusProps: clearFocusProps, isFocusVisible: isClearButtonFocusVisible } = (0, import_focus.useFocusRing)();
143
+ const { focusWithinProps } = (0, import_interactions.useFocusWithin)({
144
+ onFocusWithinChange: setFocusWithin
145
+ });
146
+ const { pressProps: clearPressProps } = (0, import_interactions.usePress)({
147
+ isDisabled: !!(originalProps == null ? void 0 : originalProps.isDisabled) || !!(originalProps == null ? void 0 : originalProps.isReadOnly),
148
+ onPress: handleClear
149
+ });
150
+ const isInvalid = validationState === "invalid" || isAriaInvalid;
151
+ const labelPlacement = (0, import_system.useLabelPlacement)({
152
+ labelPlacement: originalProps.labelPlacement,
153
+ label
154
+ });
155
+ const errorMessage = typeof props.errorMessage === "function" ? props.errorMessage({ isInvalid, validationErrors, validationDetails }) : props.errorMessage || (validationErrors == null ? void 0 : validationErrors.join(" "));
156
+ const isClearable = !!onClear || originalProps.isClearable;
157
+ const hasElements = !!label || !!description || !!errorMessage;
158
+ const hasPlaceholder = !!props.placeholder;
159
+ const hasLabel = !!label;
160
+ const hasHelper = !!description || !!errorMessage;
161
+ const isOutsideLeft = labelPlacement === "outside-left";
162
+ const isOutsideTop = labelPlacement === "outside-top";
163
+ const shouldLabelBeOutside = (
164
+ // label is outside only when some placeholder is there
165
+ labelPlacement === "outside" || // label is outside regardless of placeholder
166
+ isOutsideLeft || isOutsideTop
167
+ );
168
+ const shouldLabelBeInside = labelPlacement === "inside";
169
+ const isPlaceholderShown = domRef.current ? (!domRef.current.value || domRef.current.value === "" || !inputValue || inputValue === "") && hasPlaceholder : false;
170
+ const hasStartContent = !!startContent;
171
+ const isLabelOutside = shouldLabelBeOutside ? isOutsideLeft || isOutsideTop || hasPlaceholder || labelPlacement === "outside" && hasStartContent : false;
172
+ const isLabelOutsideAsPlaceholder = labelPlacement === "outside" && !hasPlaceholder && !hasStartContent;
173
+ const slots = (0, import_react.useMemo)(
174
+ () => (0, import_theme.input)({
175
+ ...variantProps,
176
+ isInvalid,
177
+ labelPlacement,
178
+ isClearable,
179
+ disableAnimation
180
+ }),
181
+ [
182
+ (0, import_shared_utils.objectToDeps)(variantProps),
183
+ isInvalid,
184
+ labelPlacement,
185
+ isClearable,
186
+ hasStartContent,
187
+ disableAnimation
188
+ ]
189
+ );
190
+ const getBaseProps = (0, import_react.useCallback)(
191
+ (props2 = {}) => {
192
+ return {
193
+ ref: baseDomRef,
194
+ className: slots.base({ class: baseStyles }),
195
+ "data-slot": "base",
196
+ "data-filled": (0, import_shared_utils.dataAttr)(
197
+ isFilled || hasPlaceholder || hasStartContent || isPlaceholderShown || isFileTypeInput
198
+ ),
199
+ "data-filled-within": (0, import_shared_utils.dataAttr)(
200
+ isFilledWithin || hasPlaceholder || hasStartContent || isPlaceholderShown || isFileTypeInput
201
+ ),
202
+ "data-focus-within": (0, import_shared_utils.dataAttr)(isFocusWithin),
203
+ "data-focus-visible": (0, import_shared_utils.dataAttr)(isFocusVisible),
204
+ "data-readonly": (0, import_shared_utils.dataAttr)(originalProps.isReadOnly),
205
+ "data-focus": (0, import_shared_utils.dataAttr)(isFocused),
206
+ "data-hover": (0, import_shared_utils.dataAttr)(isHovered || isLabelHovered),
207
+ "data-required": (0, import_shared_utils.dataAttr)(originalProps.isRequired),
208
+ "data-invalid": (0, import_shared_utils.dataAttr)(isInvalid),
209
+ "data-disabled": (0, import_shared_utils.dataAttr)(originalProps.isDisabled),
210
+ "data-has-elements": (0, import_shared_utils.dataAttr)(hasElements),
211
+ "data-has-helper": (0, import_shared_utils.dataAttr)(hasHelper),
212
+ "data-has-label": (0, import_shared_utils.dataAttr)(hasLabel),
213
+ "data-has-value": (0, import_shared_utils.dataAttr)(!isPlaceholderShown),
214
+ "data-hidden": (0, import_shared_utils.dataAttr)(isHiddenType),
215
+ ...focusWithinProps,
216
+ ...props2
217
+ };
218
+ },
219
+ [
220
+ slots,
221
+ baseStyles,
222
+ isFilled,
223
+ isFocused,
224
+ isHovered,
225
+ isLabelHovered,
226
+ isInvalid,
227
+ hasHelper,
228
+ hasLabel,
229
+ hasElements,
230
+ isPlaceholderShown,
231
+ hasStartContent,
232
+ isFocusWithin,
233
+ isFocusVisible,
234
+ isFilledWithin,
235
+ hasPlaceholder,
236
+ focusWithinProps,
237
+ isHiddenType,
238
+ originalProps.isReadOnly,
239
+ originalProps.isRequired,
240
+ originalProps.isDisabled
241
+ ]
242
+ );
243
+ const getLabelProps = (0, import_react.useCallback)(
244
+ (props2 = {}) => {
245
+ return {
246
+ "data-slot": "label",
247
+ className: slots.label({ class: classNames == null ? void 0 : classNames.label }),
248
+ ...(0, import_shared_utils.mergeProps)(labelProps, labelHoverProps, props2)
249
+ };
250
+ },
251
+ [slots, isLabelHovered, labelProps, classNames == null ? void 0 : classNames.label]
252
+ );
253
+ const handleKeyDown = (0, import_react.useCallback)(
254
+ (e) => {
255
+ if (e.key === "Escape" && inputValue && (isClearable || onClear) && !originalProps.isReadOnly) {
256
+ setInputValue("");
257
+ onClear == null ? void 0 : onClear();
258
+ }
259
+ },
260
+ [inputValue, setInputValue, onClear, isClearable, originalProps.isReadOnly]
261
+ );
262
+ const getInputProps = (0, import_react.useCallback)(
263
+ (props2 = {}) => {
264
+ return {
265
+ "data-slot": "input",
266
+ "data-filled": (0, import_shared_utils.dataAttr)(isFilled),
267
+ "data-filled-within": (0, import_shared_utils.dataAttr)(isFilledWithin),
268
+ "data-has-start-content": (0, import_shared_utils.dataAttr)(hasStartContent),
269
+ "data-has-end-content": (0, import_shared_utils.dataAttr)(!!endContent),
270
+ "data-type": type,
271
+ className: slots.input({
272
+ class: (0, import_theme.cn)(
273
+ classNames == null ? void 0 : classNames.input,
274
+ isFilled ? "is-filled" : "",
275
+ isMultiline ? "pe-0" : "",
276
+ type === "password" ? "[&::-ms-reveal]:hidden" : ""
277
+ )
278
+ }),
279
+ ...(0, import_shared_utils.mergeProps)(
280
+ focusProps,
281
+ inputProps,
282
+ (0, import_react_utils.filterDOMProps)(otherProps, {
283
+ enabled: true,
284
+ labelable: true,
285
+ omitEventNames: new Set(Object.keys(inputProps))
286
+ }),
287
+ props2
288
+ ),
289
+ "aria-readonly": (0, import_shared_utils.dataAttr)(originalProps.isReadOnly),
290
+ onChange: (0, import_shared_utils.chain)(inputProps.onChange, onChange),
291
+ onKeyDown: (0, import_shared_utils.chain)(inputProps.onKeyDown, props2.onKeyDown, handleKeyDown),
292
+ ref: domRef
293
+ };
294
+ },
295
+ [
296
+ slots,
297
+ inputValue,
298
+ focusProps,
299
+ inputProps,
300
+ otherProps,
301
+ isFilled,
302
+ isFilledWithin,
303
+ hasStartContent,
304
+ endContent,
305
+ classNames == null ? void 0 : classNames.input,
306
+ originalProps.isReadOnly,
307
+ originalProps.isRequired,
308
+ onChange,
309
+ handleKeyDown
310
+ ]
311
+ );
312
+ const getInputWrapperProps = (0, import_react.useCallback)(
313
+ (props2 = {}) => {
314
+ return {
315
+ ref: inputWrapperRef,
316
+ "data-slot": "input-wrapper",
317
+ "data-hover": (0, import_shared_utils.dataAttr)(isHovered || isLabelHovered),
318
+ "data-focus-visible": (0, import_shared_utils.dataAttr)(isFocusVisible),
319
+ "data-focus": (0, import_shared_utils.dataAttr)(isFocused),
320
+ className: slots.inputWrapper({
321
+ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.inputWrapper, isFilled ? "is-filled" : "")
322
+ }),
323
+ ...(0, import_shared_utils.mergeProps)(props2, hoverProps),
324
+ onClick: (e) => {
325
+ if (domRef.current && e.currentTarget === e.target) {
326
+ domRef.current.focus();
327
+ }
328
+ },
329
+ style: {
330
+ cursor: "text",
331
+ ...props2.style
332
+ }
333
+ };
334
+ },
335
+ [
336
+ slots,
337
+ isHovered,
338
+ isLabelHovered,
339
+ isFocusVisible,
340
+ isFocused,
341
+ inputValue,
342
+ classNames == null ? void 0 : classNames.inputWrapper
343
+ ]
344
+ );
345
+ const getInnerWrapperProps = (0, import_react.useCallback)(
346
+ (props2 = {}) => {
347
+ return {
348
+ ...props2,
349
+ ref: innerWrapperRef,
350
+ "data-slot": "inner-wrapper",
351
+ onClick: (e) => {
352
+ if (domRef.current && e.currentTarget === e.target) {
353
+ domRef.current.focus();
354
+ }
355
+ },
356
+ className: slots.innerWrapper({
357
+ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.innerWrapper, props2 == null ? void 0 : props2.className)
358
+ })
359
+ };
360
+ },
361
+ [slots, classNames == null ? void 0 : classNames.innerWrapper]
362
+ );
363
+ const getMainWrapperProps = (0, import_react.useCallback)(
364
+ (props2 = {}) => {
365
+ return {
366
+ ...props2,
367
+ "data-slot": "main-wrapper",
368
+ className: slots.mainWrapper({
369
+ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.mainWrapper, props2 == null ? void 0 : props2.className)
370
+ })
371
+ };
372
+ },
373
+ [slots, classNames == null ? void 0 : classNames.mainWrapper]
374
+ );
375
+ const getHelperWrapperProps = (0, import_react.useCallback)(
376
+ (props2 = {}) => {
377
+ return {
378
+ ...props2,
379
+ "data-slot": "helper-wrapper",
380
+ className: slots.helperWrapper({
381
+ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.helperWrapper, props2 == null ? void 0 : props2.className)
382
+ })
383
+ };
384
+ },
385
+ [slots, classNames == null ? void 0 : classNames.helperWrapper]
386
+ );
387
+ const getDescriptionProps = (0, import_react.useCallback)(
388
+ (props2 = {}) => {
389
+ return {
390
+ ...props2,
391
+ ...descriptionProps,
392
+ "data-slot": "description",
393
+ className: slots.description({ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.description, props2 == null ? void 0 : props2.className) })
394
+ };
395
+ },
396
+ [slots, classNames == null ? void 0 : classNames.description]
397
+ );
398
+ const getErrorMessageProps = (0, import_react.useCallback)(
399
+ (props2 = {}) => {
400
+ return {
401
+ ...props2,
402
+ ...errorMessageProps,
403
+ "data-slot": "error-message",
404
+ className: slots.errorMessage({ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.errorMessage, props2 == null ? void 0 : props2.className) })
405
+ };
406
+ },
407
+ [slots, errorMessageProps, classNames == null ? void 0 : classNames.errorMessage]
408
+ );
409
+ const getClearButtonProps = (0, import_react.useCallback)(
410
+ (props2 = {}) => {
411
+ return {
412
+ ...props2,
413
+ type: "button",
414
+ tabIndex: -1,
415
+ disabled: originalProps.isDisabled,
416
+ "aria-label": "clear input",
417
+ "data-slot": "clear-button",
418
+ "data-focus-visible": (0, import_shared_utils.dataAttr)(isClearButtonFocusVisible),
419
+ className: slots.clearButton({
420
+ class: (0, import_theme.cn)(classNames == null ? void 0 : classNames.clearButton, props2 == null ? void 0 : props2.className)
421
+ }),
422
+ ...(0, import_shared_utils.mergeProps)(clearPressProps, clearFocusProps)
423
+ };
424
+ },
425
+ [slots, isClearButtonFocusVisible, clearPressProps, clearFocusProps, classNames == null ? void 0 : classNames.clearButton]
426
+ );
427
+ return {
428
+ Component,
429
+ classNames,
430
+ domRef,
431
+ label,
432
+ description,
433
+ startContent,
434
+ endContent,
435
+ labelPlacement,
436
+ isClearable,
437
+ hasHelper,
438
+ hasStartContent,
439
+ isLabelOutside,
440
+ isOutsideLeft,
441
+ isOutsideTop,
442
+ isLabelOutsideAsPlaceholder,
443
+ shouldLabelBeOutside,
444
+ shouldLabelBeInside,
445
+ hasPlaceholder,
446
+ isInvalid,
447
+ errorMessage,
448
+ getBaseProps,
449
+ getLabelProps,
450
+ getInputProps,
451
+ getMainWrapperProps,
452
+ getInputWrapperProps,
453
+ getInnerWrapperProps,
454
+ getHelperWrapperProps,
455
+ getDescriptionProps,
456
+ getErrorMessageProps,
457
+ getClearButtonProps
458
+ };
459
+ }
460
+
461
+ // src/input.tsx
462
+ var import_jsx_runtime = require("react/jsx-runtime");
463
+ var Input = (0, import_system2.forwardRef)((props, ref) => {
464
+ const {
465
+ Component,
466
+ label,
467
+ description,
468
+ isClearable,
469
+ startContent,
470
+ endContent,
471
+ labelPlacement,
472
+ hasHelper,
473
+ isOutsideLeft,
474
+ isOutsideTop,
475
+ shouldLabelBeOutside,
476
+ errorMessage,
477
+ isInvalid,
478
+ getBaseProps,
479
+ getLabelProps,
480
+ getInputProps,
481
+ getInnerWrapperProps,
482
+ getInputWrapperProps,
483
+ getMainWrapperProps,
484
+ getHelperWrapperProps,
485
+ getDescriptionProps,
486
+ getErrorMessageProps,
487
+ getClearButtonProps
488
+ } = useInput({ ...props, ref });
489
+ const labelContent = label ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)("label", { ...getLabelProps(), children: label }) : null;
490
+ const end = (0, import_react2.useMemo)(() => {
491
+ if (isClearable) {
492
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("button", { ...getClearButtonProps(), children: endContent || /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_shared_icons.CloseFilledIcon, {}) });
493
+ }
494
+ return endContent;
495
+ }, [isClearable, getClearButtonProps]);
496
+ const helperWrapper = (0, import_react2.useMemo)(() => {
497
+ const shouldShowError = isInvalid && errorMessage;
498
+ const hasContent = shouldShowError || description;
499
+ if (!hasHelper || !hasContent) return null;
500
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { ...getHelperWrapperProps(), children: shouldShowError ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { ...getErrorMessageProps(), children: errorMessage }) : /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { ...getDescriptionProps(), children: description }) });
501
+ }, [
502
+ hasHelper,
503
+ isInvalid,
504
+ errorMessage,
505
+ description,
506
+ getHelperWrapperProps,
507
+ getErrorMessageProps,
508
+ getDescriptionProps
509
+ ]);
510
+ const innerWrapper = (0, import_react2.useMemo)(() => {
511
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { ...getInnerWrapperProps(), children: [
512
+ startContent,
513
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)("input", { ...getInputProps() }),
514
+ end
515
+ ] });
516
+ }, [startContent, end, getInputProps, getInnerWrapperProps]);
517
+ const mainWrapper = (0, import_react2.useMemo)(() => {
518
+ if (shouldLabelBeOutside) {
519
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { ...getMainWrapperProps(), children: [
520
+ /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { ...getInputWrapperProps(), children: [
521
+ !isOutsideLeft && !isOutsideTop ? labelContent : null,
522
+ innerWrapper
523
+ ] }),
524
+ helperWrapper
525
+ ] });
526
+ }
527
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_jsx_runtime.Fragment, { children: [
528
+ /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { ...getInputWrapperProps(), children: [
529
+ labelContent,
530
+ innerWrapper
531
+ ] }),
532
+ helperWrapper
533
+ ] });
534
+ }, [
535
+ labelPlacement,
536
+ helperWrapper,
537
+ shouldLabelBeOutside,
538
+ labelContent,
539
+ innerWrapper,
540
+ errorMessage,
541
+ description,
542
+ getMainWrapperProps,
543
+ getInputWrapperProps,
544
+ getErrorMessageProps,
545
+ getDescriptionProps
546
+ ]);
547
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(Component, { ...getBaseProps(), children: [
548
+ isOutsideLeft || isOutsideTop ? labelContent : null,
549
+ mainWrapper
550
+ ] });
551
+ });
552
+ Input.displayName = "HeroUI.Input";
553
+ var input_default = Input;
package/dist/input.mjs ADDED
@@ -0,0 +1,8 @@
1
+ "use client";
2
+ import {
3
+ input_default
4
+ } from "./chunk-PPYXCOZH.mjs";
5
+ import "./chunk-6SGLJYRO.mjs";
6
+ export {
7
+ input_default as default
8
+ };
@@ -0,0 +1,44 @@
1
+ import * as _sytechui_system from '@sytechui/system';
2
+ import { UseInputProps } from './use-input.mjs';
3
+ import 'react';
4
+ import '@sytechui/theme';
5
+ import '@react-types/textfield';
6
+
7
+ type OmittedInputProps = "isClearButtonFocusVisible" | "isLabelPlaceholder" | "isTextarea";
8
+ type TextareaHeightChangeMeta = {
9
+ rowHeight: number;
10
+ };
11
+ interface TextAreaProps extends Omit<UseInputProps<HTMLTextAreaElement>, OmittedInputProps> {
12
+ /**
13
+ * Whether the textarea should automatically grow vertically to accommodate content.
14
+ * @default false
15
+ */
16
+ disableAutosize?: boolean;
17
+ /**
18
+ * Minimum number of rows to show for textarea
19
+ * @default 3
20
+ */
21
+ minRows?: number;
22
+ /**
23
+ * Maximum number of rows up to which the textarea can grow
24
+ * @default 8
25
+ */
26
+ maxRows?: number;
27
+ /**
28
+ * Reuse previously computed measurements when computing height of textarea.
29
+ * @default false
30
+ */
31
+ cacheMeasurements?: boolean;
32
+ /**
33
+ * Function invoked on textarea height change, with height as first argument.
34
+ * The second function argument is an object containing additional information that
35
+ * might be useful for custom behaviors. Current options include `{ rowHeight: number }`.
36
+ *
37
+ * @param height - The height of the textarea
38
+ * @param meta - Additional information about the height change
39
+ */
40
+ onHeightChange?: (height: number, meta: TextareaHeightChangeMeta) => void;
41
+ }
42
+ declare const Textarea: _sytechui_system.InternalForwardRefRenderFunction<"textarea", TextAreaProps, never>;
43
+
44
+ export { type TextAreaProps, type TextareaHeightChangeMeta, Textarea as default };
@@ -0,0 +1,44 @@
1
+ import * as _sytechui_system from '@sytechui/system';
2
+ import { UseInputProps } from './use-input.js';
3
+ import 'react';
4
+ import '@sytechui/theme';
5
+ import '@react-types/textfield';
6
+
7
+ type OmittedInputProps = "isClearButtonFocusVisible" | "isLabelPlaceholder" | "isTextarea";
8
+ type TextareaHeightChangeMeta = {
9
+ rowHeight: number;
10
+ };
11
+ interface TextAreaProps extends Omit<UseInputProps<HTMLTextAreaElement>, OmittedInputProps> {
12
+ /**
13
+ * Whether the textarea should automatically grow vertically to accommodate content.
14
+ * @default false
15
+ */
16
+ disableAutosize?: boolean;
17
+ /**
18
+ * Minimum number of rows to show for textarea
19
+ * @default 3
20
+ */
21
+ minRows?: number;
22
+ /**
23
+ * Maximum number of rows up to which the textarea can grow
24
+ * @default 8
25
+ */
26
+ maxRows?: number;
27
+ /**
28
+ * Reuse previously computed measurements when computing height of textarea.
29
+ * @default false
30
+ */
31
+ cacheMeasurements?: boolean;
32
+ /**
33
+ * Function invoked on textarea height change, with height as first argument.
34
+ * The second function argument is an object containing additional information that
35
+ * might be useful for custom behaviors. Current options include `{ rowHeight: number }`.
36
+ *
37
+ * @param height - The height of the textarea
38
+ * @param meta - Additional information about the height change
39
+ */
40
+ onHeightChange?: (height: number, meta: TextareaHeightChangeMeta) => void;
41
+ }
42
+ declare const Textarea: _sytechui_system.InternalForwardRefRenderFunction<"textarea", TextAreaProps, never>;
43
+
44
+ export { type TextAreaProps, type TextareaHeightChangeMeta, Textarea as default };