/*! © 2026 Yahoo, Inc. UDS v0.0.0-development */
"use client";
import { cx, getStyles } from "../../../styles/styler.js";
import { IconSlot } from "../../IconSlot.js";
import { Box } from "../../Box.js";
import { HStack } from "../../HStack.js";
import { VStack } from "../../VStack.js";
import { AnimateHeightChange } from "../AnimateHeightChange.js";
import { InputHelpTextInternal as InputHelpTextInternalMemo } from "./InputHelpTextInternal.js";
import { forwardRef, memo, useCallback, useEffect, useId, useImperativeHandle, useRef, useState } from "react";
import { jsx, jsxs } from "react/jsx-runtime";
import { isFunction } from "lodash-es";
import { useReducedMotion } from "motion/react";
//#region src/components/client/Input/Input.tsx
const HelpTextContent = memo(function HelpTextContentOriginal({ helpText, helperTextIcon, spacingStart, spacingTop, size, isFilled, helperTextSlotProps, ...rest }) {
	if (!helpText) return null;
	return /* @__PURE__ */ jsx(Box, {
		spacingTop,
		spacingStart,
		...rest,
		children: /* @__PURE__ */ jsx(InputHelpTextInternalMemo, {
			startIcon: helperTextIcon,
			size,
			isFilled,
			slotProps: {
				startIcon: helperTextSlotProps?.helperTextIcon,
				text: helperTextSlotProps?.helperText
			},
			children: isFunction(helpText) ? helpText() : helpText
		})
	});
});
const StartIcon = memo(function StartIcon({ icon, className, iconProps }) {
	if (!icon) return null;
	return /* @__PURE__ */ jsx(IconSlot, {
		icon,
		iconProps: {
			variant: "outline",
			...iconProps
		},
		className
	});
});
const EndIcon = memo(function EndIcon({ icon, className, iconProps }) {
	if (!icon) return null;
	return /* @__PURE__ */ jsx(IconSlot, {
		icon,
		iconProps: {
			variant: "outline",
			...iconProps
		},
		className
	});
});
/**
* **📦 An input that allows users to enter text and collect data.**
*
* @componentType Client component
*
* @description
* An input field is a component that takes text typed into it. It can also serve as a way to display a selection and trigger a dropdown menu. Inputs are interactive elements that users can click, tap, or otherwise engage with to collect data and open dropdowns, or both.
*
* @see
* Check out the {@link https://uds.build/docs/components/input Input Docs} for more info
*
* @usage
* - Forms: For collecting data like names, emails, passwords, etc. (e.g., sign-up, login, or contact forms).
* - Search Bars: Allowing users to enter search queries to find content.
* - Filters/Settings: When users need to specify preferences, like selecting a date or adjusting a number value.
* - Feedback/Comments: Letting users leave reviews, comments, or feedback.
*
* @example
* ```tsx
* 'use client';
* import { Input } from "@yahoo/uds";
*
* <Input label="Name" placeholder="Enter your name" required />
*```
*
* @related [Checkbox](https://uds.build/docs/components/checkbox), [Radio](https://uds.build/docs/components/radio).
**/
const Input = forwardRef(function Input({ id, label, type = "text", size = "md", startIcon, endIcon, helpText, helperTextIcon, hasError, width: containerWidth = "full", defaultValue, value: valueProp, required, readOnly, disabled, reduceMotion: forceReduceMotion, onChange, slotProps, style, className, ...otherProps }, forwardedRef) {
	const generatedId = useId();
	const uid = id ?? `uds-input-${generatedId}`;
	const helpTextId = `uds-input-${uid}-help-text`;
	const { className: inputClassName, ...inputProps } = slotProps?.input ?? {};
	const { className: inputWrapperClassName, ...inputWrapperProps } = slotProps?.inputWrapper ?? {};
	const ref = useRef(null);
	useImperativeHandle(forwardedRef, () => ref.current);
	const isControlled = valueProp !== void 0;
	const [value, setValue] = useState(isControlled ? valueProp : defaultValue ?? "");
	useEffect(() => {
		if (isControlled) setValue(valueProp);
	}, [valueProp, isControlled]);
	const handleChange = useCallback((e) => {
		if (!isControlled) setValue(e.target.value);
		onChange?.(e);
	}, [isControlled, onChange]);
	const layoutVariant = useReducedMotion() ? "smooth" : "bouncy";
	const reduceMotion = forceReduceMotion ? "always" : "user";
	const isInteractive = !readOnly && !disabled;
	const classNames = {
		root: getStyles({
			inputSizeRoot: size,
			inputVariantRoot: "default",
			inputVariantValueRoot: !value ? "empty" : "filled",
			className: cx([className, disabled ? "opacity-50" : ""])
		}),
		inputWrapper: cx(getStyles({
			inputSizeInputWrapper: size,
			inputVariantInputWrapper: "default",
			inputVariantValueInputWrapper: !value ? "empty" : "filled"
		}), "min-w-[200px]", inputWrapperClassName),
		input: getStyles({
			inputSizeInput: size,
			inputVariantInput: "default",
			inputVariantValueInput: !value ? "empty" : "filled",
			inputVariantInputPlaceholder: "default",
			inputVariantValueInputPlaceholder: !value ? "empty" : "filled",
			className: cx("grow", "uds-hit-target", "bg-clip-text", "focus:outline-none", isInteractive ? "cursor-text" : "cursor-not-allowed", inputClassName)
		}),
		label: cx(getStyles({
			inputSizeLabel: size,
			inputVariantLabel: "default",
			inputVariantValueLabel: !value ? "empty" : "filled"
		})),
		labelRequired: getStyles({
			inputVariantLabelRequired: "default",
			inputVariantValueLabelRequired: !value ? "empty" : "filled"
		}),
		startIcon: getStyles({
			inputSizeStartIcon: size,
			inputVariantStartIcon: "default",
			inputVariantValueStartIcon: !value ? "empty" : "filled"
		}),
		endIcon: getStyles({
			inputSizeEndIcon: size,
			inputVariantEndIcon: "default",
			inputVariantValueEndIcon: !value ? "empty" : "filled"
		})
	};
	return /* @__PURE__ */ jsxs(VStack, {
		width: containerWidth,
		className: classNames.root,
		style,
		children: [
			label && /* @__PURE__ */ jsxs(Box, {
				spacingBottom: "2",
				columnGap: "0.5",
				alignItems: "flex-end",
				className: classNames.label,
				children: [/* @__PURE__ */ jsx("label", {
					htmlFor: uid,
					...slotProps?.label,
					children: isFunction(label) ? label() : label
				}), required && /* @__PURE__ */ jsx("span", {
					className: classNames.labelRequired,
					children: "*"
				})]
			}),
			/* @__PURE__ */ jsxs(Box, {
				position: "relative",
				alignItems: "center",
				...inputWrapperProps,
				className: classNames.inputWrapper,
				children: [
					/* @__PURE__ */ jsx(StartIcon, {
						icon: startIcon,
						className: classNames.startIcon,
						iconProps: slotProps?.startIcon
					}),
					/* @__PURE__ */ jsx("input", {
						ref,
						id: uid,
						type,
						value,
						required,
						readOnly,
						disabled,
						"aria-describedby": helpTextId,
						"aria-invalid": hasError,
						onChange: handleChange,
						className: classNames.input,
						...otherProps,
						...inputProps
					}),
					endIcon && /* @__PURE__ */ jsx(HStack, {
						alignItems: "center",
						gap: "1",
						children: /* @__PURE__ */ jsx(EndIcon, {
							icon: endIcon,
							className: classNames.endIcon,
							iconProps: slotProps?.endIcon
						})
					})
				]
			}),
			/* @__PURE__ */ jsx(AnimateHeightChange, {
				reduceMotion,
				layoutVariant,
				children: /* @__PURE__ */ jsx(HelpTextContent, {
					id: helpTextId,
					helpText,
					spacingTop: "2",
					size,
					isFilled: !!value,
					helperTextIcon,
					helperTextSlotProps: slotProps
				})
			})
		]
	});
});
Input.displayName = "Input";
//#endregion
export { Input };
