method-selector.tsx 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. import type { FC } from 'react'
  2. import { useState } from 'react'
  3. import { useTranslation } from 'react-i18next'
  4. import { RiArrowDownSLine } from '@remixicon/react'
  5. import cn from '@/utils/classnames'
  6. import {
  7. PortalToFollowElem,
  8. PortalToFollowElemContent,
  9. PortalToFollowElemTrigger,
  10. } from '@/app/components/base/portal-to-follow-elem'
  11. import { Check } from '@/app/components/base/icons/src/vender/line/general'
  12. type MethodSelectorProps = {
  13. value?: string
  14. onChange: (v: string) => void
  15. }
  16. const MethodSelector: FC<MethodSelectorProps> = ({
  17. value,
  18. onChange,
  19. }) => {
  20. const { t } = useTranslation()
  21. const [open, setOpen] = useState(false)
  22. return (
  23. <PortalToFollowElem
  24. open={open}
  25. onOpenChange={setOpen}
  26. placement='bottom-start'
  27. offset={4}
  28. >
  29. <div className='relative'>
  30. <PortalToFollowElemTrigger
  31. onClick={() => setOpen(v => !v)}
  32. className='block'
  33. >
  34. <div className={cn(
  35. 'flex items-center gap-1 min-h-[56px] px-3 py-2 h-9 bg-transparent cursor-pointer hover:bg-background-section-burn',
  36. open && '!bg-background-section-burn hover:bg-background-section-burn',
  37. )}>
  38. <div className={cn('grow text-[13px] leading-[18px] text-text-secondary truncate')}>
  39. {value === 'llm' ? t('tools.createTool.toolInput.methodParameter') : t('tools.createTool.toolInput.methodSetting')}
  40. </div>
  41. <div className='shrink-0 ml-1 text-text-secondary opacity-60'>
  42. <RiArrowDownSLine className='h-4 w-4' />
  43. </div>
  44. </div>
  45. </PortalToFollowElemTrigger>
  46. <PortalToFollowElemContent className='z-[1040]'>
  47. <div className='relative w-[320px] bg-components-panel-bg-blur backdrop-blur-sm rounded-lg border-[0.5px] border-components-panel-border shadow-lg'>
  48. <div className='p-1'>
  49. <div className='pl-3 pr-2 py-2.5 rounded-lg hover:bg-components-panel-on-panel-item-bg-hover cursor-pointer' onClick={() => onChange('llm')}>
  50. <div className='flex item-center gap-1'>
  51. <div className='shrink-0 w-4 h-4'>
  52. {value === 'llm' && <Check className='shrink-0 w-4 h-4 text-text-accent' />}
  53. </div>
  54. <div className='text-[13px] text-text-secondary font-medium leading-[18px]'>{t('tools.createTool.toolInput.methodParameter')}</div>
  55. </div>
  56. <div className='pl-5 text-text-tertiary text-[13px] leading-[18px]'>{t('tools.createTool.toolInput.methodParameterTip')}</div>
  57. </div>
  58. <div className='pl-3 pr-2 py-2.5 rounded-lg hover:bg-components-panel-on-panel-item-bg-hover cursor-pointer' onClick={() => onChange('form')}>
  59. <div className='flex item-center gap-1'>
  60. <div className='shrink-0 w-4 h-4'>
  61. {value === 'form' && <Check className='shrink-0 w-4 h-4 text-text-accent' />}
  62. </div>
  63. <div className='text-[13px] text-text-secondary font-medium leading-[18px]'>{t('tools.createTool.toolInput.methodSetting')}</div>
  64. </div>
  65. <div className='pl-5 text-text-tertiary text-[13px] leading-[18px]'>{t('tools.createTool.toolInput.methodSettingTip')}</div>
  66. </div>
  67. </div>
  68. </div>
  69. </PortalToFollowElemContent>
  70. </div>
  71. </PortalToFollowElem>
  72. )
  73. }
  74. export default MethodSelector