UNPKG

koval-ui

Version:

React components collection with minimalistic design. Supports theming, layout, and input validation.

1 lines 8.17 kB
{"version":3,"file":"InputNumber.cjs","sources":["../../../../src/lib/InputNumber/InputNumber.tsx"],"sourcesContent":["import type {ChangeEvent, InputHTMLAttributes, FormEvent} from 'react';\nimport {useEffect} from 'react';\nimport {forwardRef, useCallback, useMemo} from 'react';\nimport classNames from 'classnames';\nimport {useLocalTheme} from 'css-vars-hook';\n\nimport {IconArrowUp, IconArrowDown} from '@/internal/Icons';\nimport type {DataAttributes, LibraryProps} from '@/internal/LibraryAPI';\nimport type {NativePropsNumeric, CallbackPropsTextual, ValidationProps} from '@/internal/inputs';\nimport {\n ValidationState,\n useValidation,\n useExternalValidation,\n useRevalidateOnFormChange,\n useValidationIcon,\n} from '@/internal/inputs';\nimport {useInternalRef} from '@/internal/hooks/useInternalRef.ts';\n\nimport classes from './InputNumber.module.css';\n\nexport type Props = DataAttributes &\n LibraryProps &\n NativePropsNumeric &\n CallbackPropsTextual &\n ValidationProps & {\n /**\n * Define the width of the input in characters\n */\n size?: InputHTMLAttributes<HTMLInputElement>['size'];\n };\n\nconst SPINNER_EVENT_TYPE = 'change_spinner';\n\nconst ChangeEventSpinner = new Event(SPINNER_EVENT_TYPE, {bubbles: true});\n\nexport const InputNumber = forwardRef<HTMLInputElement, Props>(\n (\n {\n className,\n placeholder = '',\n disabled,\n value,\n onChange = () => {},\n onFocus = () => {},\n onBlur = () => {},\n onKeyDown = () => {},\n onKeyUp = () => {},\n defaultValue,\n size = 10,\n step,\n revalidateOnFormChange,\n errorMessage = ValidationState.error,\n validation,\n displayIcon = true,\n ...nativeProps\n },\n ref\n ) => {\n const hasValidators =\n Boolean(validation) ||\n Boolean(nativeProps.required) ||\n typeof nativeProps.min === 'number' ||\n typeof nativeProps.min === 'string' ||\n typeof nativeProps.max === 'number' ||\n typeof nativeProps.max === 'string';\n\n const {validateTextual, validity, setValidity} = useValidation({validation, hasValidators});\n\n const inputRef = useInternalRef(ref);\n useRevalidateOnFormChange(inputRef, validateTextual, revalidateOnFormChange);\n useExternalValidation({errorMessage, inputRef, setValidity, validation});\n\n const ValidationIcon = useValidationIcon(validity);\n const handleChange = useCallback(\n (event: ChangeEvent<HTMLInputElement>) => {\n onChange(event);\n },\n [onChange]\n );\n\n useEffect(() => {\n inputRef.current?.addEventListener(SPINNER_EVENT_TYPE, event => {\n // TODO: improve type\n onChange(event as unknown as ChangeEvent<HTMLInputElement>);\n });\n }, [inputRef, onChange]);\n\n const handleInvalid = useCallback(() => {\n setValidity(ValidationState.error);\n }, [setValidity]);\n\n const handleDecrement = useCallback(() => {\n inputRef.current!.stepDown();\n inputRef.current!.dispatchEvent(ChangeEventSpinner);\n validateTextual(ChangeEventSpinner as unknown as FormEvent);\n }, [inputRef, validateTextual]);\n\n const handleIncrement = useCallback(() => {\n inputRef.current!.stepUp();\n inputRef.current!.dispatchEvent(ChangeEventSpinner);\n validateTextual(ChangeEventSpinner as unknown as FormEvent);\n }, [inputRef, validateTextual]);\n\n const {LocalRoot} = useLocalTheme();\n const theme = useMemo(() => ({size}), [size]);\n\n return (\n <LocalRoot\n className={classNames(\n classes.wrapper,\n {[classes.withValidationIcon]: displayIcon},\n className\n )}\n theme={theme}>\n <div className={classes.spinner}>\n <IconArrowUp tabIndex={-1} onClick={handleIncrement} />\n <IconArrowDown tabIndex={-1} onClick={handleDecrement} />\n </div>\n <input\n {...nativeProps}\n step={step}\n size={size}\n type=\"number\"\n placeholder={placeholder}\n className={classes.input}\n ref={inputRef}\n disabled={disabled}\n value={value}\n defaultValue={defaultValue}\n onChange={handleChange}\n onBlur={onBlur}\n onFocus={onFocus}\n onKeyUp={onKeyUp}\n onKeyDown={onKeyDown}\n onInvalid={handleInvalid}\n onInput={validateTextual}\n />\n {displayIcon && validity && <ValidationIcon className={classes.validation} />}\n </LocalRoot>\n );\n }\n);\n\nInputNumber.displayName = 'InputNumber';\n"],"names":["SPINNER_EVENT_TYPE","ChangeEventSpinner","InputNumber","forwardRef","className","placeholder","disabled","value","onChange","onFocus","onBlur","onKeyDown","onKeyUp","defaultValue","size","step","revalidateOnFormChange","errorMessage","ValidationState","validation","displayIcon","nativeProps","ref","hasValidators","validateTextual","validity","setValidity","useValidation","inputRef","useInternalRef","useRevalidateOnFormChange","useExternalValidation","ValidationIcon","useValidationIcon","handleChange","useCallback","event","useEffect","_a","handleInvalid","handleDecrement","handleIncrement","LocalRoot","useLocalTheme","theme","useMemo","jsxs","classNames","classes","jsx","IconArrowUp","IconArrowDown"],"mappings":"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"}