123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168 |
- import {
- memo,
- useCallback,
- useState,
- } from 'react'
- import { useTranslation } from 'react-i18next'
- import { RiArrowDownSLine } from '@remixicon/react'
- import { capitalize } from 'lodash-es'
- import { useBoolean } from 'ahooks'
- import { VarType as NumberVarType } from '../../tool/types'
- import VariableTag from '../../_base/components/variable-tag'
- import {
- PortalToFollowElem,
- PortalToFollowElemContent,
- PortalToFollowElemTrigger,
- } from '@/app/components/base/portal-to-follow-elem'
- import Button from '@/app/components/base/button'
- import cn from '@/utils/classnames'
- import VarReferenceVars from '@/app/components/workflow/nodes/_base/components/variable/var-reference-vars'
- import type {
- NodeOutPutVar,
- ValueSelector,
- } from '@/app/components/workflow/types'
- import { VarType } from '@/app/components/workflow/types'
- import { variableTransformer } from '@/app/components/workflow/utils'
- import { Variable02 } from '@/app/components/base/icons/src/vender/solid/development'
- const options = [
- NumberVarType.variable,
- NumberVarType.constant,
- ]
- type ConditionNumberInputProps = {
- numberVarType?: NumberVarType
- onNumberVarTypeChange: (v: NumberVarType) => void
- value: string
- onValueChange: (v: string) => void
- variables: NodeOutPutVar[]
- isShort?: boolean
- unit?: string
- }
- const ConditionNumberInput = ({
- numberVarType = NumberVarType.constant,
- onNumberVarTypeChange,
- value,
- onValueChange,
- variables,
- isShort,
- unit,
- }: ConditionNumberInputProps) => {
- const { t } = useTranslation()
- const [numberVarTypeVisible, setNumberVarTypeVisible] = useState(false)
- const [variableSelectorVisible, setVariableSelectorVisible] = useState(false)
- const [isFocus, {
- setTrue: setFocus,
- setFalse: setBlur,
- }] = useBoolean()
- const handleSelectVariable = useCallback((valueSelector: ValueSelector) => {
- onValueChange(variableTransformer(valueSelector) as string)
- setVariableSelectorVisible(false)
- }, [onValueChange])
- return (
- <div className='flex items-center cursor-pointer'>
- <PortalToFollowElem
- open={numberVarTypeVisible}
- onOpenChange={setNumberVarTypeVisible}
- placement='bottom-start'
- offset={{ mainAxis: 2, crossAxis: 0 }}
- >
- <PortalToFollowElemTrigger onClick={() => setNumberVarTypeVisible(v => !v)}>
- <Button
- className='shrink-0'
- variant='ghost'
- size='small'
- >
- {capitalize(numberVarType)}
- <RiArrowDownSLine className='ml-[1px] w-3.5 h-3.5' />
- </Button>
- </PortalToFollowElemTrigger>
- <PortalToFollowElemContent className='z-[1000]'>
- <div className='p-1 w-[112px] rounded-xl border-[0.5px] border-components-panel-border bg-components-panel-bg-blur shadow-lg'>
- {
- options.map(option => (
- <div
- key={option}
- className={cn(
- 'flex items-center px-3 h-7 rounded-md hover:bg-state-base-hover cursor-pointer',
- 'text-[13px] font-medium text-text-secondary',
- numberVarType === option && 'bg-state-base-hover',
- )}
- onClick={() => {
- onNumberVarTypeChange(option)
- setNumberVarTypeVisible(false)
- }}
- >
- {capitalize(option)}
- </div>
- ))
- }
- </div>
- </PortalToFollowElemContent>
- </PortalToFollowElem>
- <div className='mx-1 w-[1px] h-4 bg-divider-regular'></div>
- <div className='grow w-0 ml-0.5'>
- {
- numberVarType === NumberVarType.variable && (
- <PortalToFollowElem
- open={variableSelectorVisible}
- onOpenChange={setVariableSelectorVisible}
- placement='bottom-start'
- offset={{ mainAxis: 2, crossAxis: 0 }}
- >
- <PortalToFollowElemTrigger
- className='w-full'
- onClick={() => setVariableSelectorVisible(v => !v)}>
- {
- value && (
- <VariableTag
- valueSelector={variableTransformer(value) as string[]}
- varType={VarType.number}
- isShort={isShort}
- />
- )
- }
- {
- !value && (
- <div className='flex items-center p-1 h-6 text-components-input-text-placeholder text-[13px]'>
- <Variable02 className='shrink-0 mr-1 w-4 h-4' />
- <div className='w-0 grow truncate'>{t('workflow.nodes.ifElse.selectVariable')}</div>
- </div>
- )
- }
- </PortalToFollowElemTrigger>
- <PortalToFollowElemContent className='z-[1000]'>
- <div className={cn('w-[296px] pt-1 bg-components-panel-bg-blur rounded-lg border-[0.5px] border-components-panel-border shadow-lg', isShort && 'w-[200px]')}>
- <VarReferenceVars
- vars={variables}
- onChange={handleSelectVariable}
- />
- </div>
- </PortalToFollowElemContent>
- </PortalToFollowElem>
- )
- }
- {
- numberVarType === NumberVarType.constant && (
- <div className=' relative'>
- <input
- className={cn('block w-full px-2 text-[13px] text-components-input-text-filled placeholder:text-components-input-text-placeholder outline-none appearance-none bg-transparent', unit && 'pr-6')}
- type='number'
- value={value}
- onChange={e => onValueChange(e.target.value)}
- placeholder={t('workflow.nodes.ifElse.enterValue') || ''}
- onFocus={setFocus}
- onBlur={setBlur}
- />
- {!isFocus && unit && <div className='absolute right-2 top-[50%] translate-y-[-50%] text-text-tertiary system-sm-regular'>{unit}</div>}
- </div>
- )
- }
- </div>
- </div>
- )
- }
- export default memo(ConditionNumberInput)
|