import { VariablesButton } from '@/features/variables/components/VariablesButton' import { NumberInputProps, NumberInput as ChakraNumberInput, NumberInputField, NumberInputStepper, NumberIncrementStepper, NumberDecrementStepper, HStack, FormControl, FormLabel, Stack, Text, FormHelperText, } from '@chakra-ui/react' import { Variable, VariableString } from '@typebot.io/schemas' import { ReactNode, useEffect, useState } from 'react' import { useDebouncedCallback } from 'use-debounce' import { env } from '@typebot.io/env' import { MoreInfoTooltip } from '../MoreInfoTooltip' type Value = HasVariable extends true | undefined ? number | VariableString : number type Props = { defaultValue: Value | undefined debounceTimeout?: number withVariableButton?: HasVariable label?: string moreInfoTooltip?: string isRequired?: boolean direction?: 'row' | 'column' suffix?: string helperText?: ReactNode onValueChange: (value?: Value) => void } & Omit export const NumberInput = ({ defaultValue, onValueChange, withVariableButton, debounceTimeout = 1000, label, moreInfoTooltip, isRequired, direction = 'column', suffix, helperText, ...props }: Props) => { const [value, setValue] = useState(defaultValue?.toString() ?? '') const onValueChangeDebounced = useDebouncedCallback( onValueChange, env.NEXT_PUBLIC_E2E_TEST ? 0 : debounceTimeout ) useEffect( () => () => { onValueChangeDebounced.flush() }, [onValueChangeDebounced] ) const handleValueChange = (newValue: string) => { if (value.startsWith('{{') && value.endsWith('}}') && newValue !== '') return setValue(newValue) if (newValue.endsWith('.') || newValue.endsWith(',')) return if (newValue === '') return onValueChangeDebounced(undefined) if ( newValue.startsWith('{{') && newValue.endsWith('}}') && newValue.length > 4 && (withVariableButton ?? true) ) { onValueChangeDebounced(newValue as Value) return } const numberedValue = parseFloat(newValue) if (isNaN(numberedValue)) return onValueChangeDebounced(numberedValue) } const handleVariableSelected = (variable?: Variable) => { if (!variable) return const newValue = `{{${variable.name}}}` handleValueChange(newValue) } const Input = ( ) return ( {label && ( {label}{' '} {moreInfoTooltip && ( {moreInfoTooltip} )} )} {withVariableButton ?? true ? ( {Input} ) : ( Input )} {suffix ? {suffix} : null} {helperText ? {helperText} : null} ) }