| @tailwind components; | |||||
| @layer components { | |||||
| .action-btn { | |||||
| @apply inline-flex justify-center items-center cursor-pointer text-text-tertiary | |||||
| hover:text-text-secondary | |||||
| hover:bg-state-base-hover | |||||
| } | |||||
| .action-btn-disabled { | |||||
| @apply cursor-not-allowed | |||||
| } | |||||
| .action-btn-xl { | |||||
| @apply p-2 w-9 h-9 rounded-lg | |||||
| } | |||||
| .action-btn-l { | |||||
| @apply p-1.5 w-[34px] h-[34px] rounded-lg | |||||
| } | |||||
| /* m is for the regular button */ | |||||
| .action-btn-m { | |||||
| @apply p-0.5 w-6 h-6 rounded-lg | |||||
| } | |||||
| .action-btn-xs { | |||||
| @apply p-0 w-5 h-5 rounded | |||||
| } | |||||
| .action-btn.action-btn-active { | |||||
| @apply | |||||
| text-text-accent | |||||
| bg-state-accent-active | |||||
| hover:bg-state-accent-active-alt | |||||
| } | |||||
| .action-btn.action-btn-disabled { | |||||
| @apply | |||||
| text-text-disabled | |||||
| } | |||||
| .action-btn.action-btn-destructive { | |||||
| @apply | |||||
| text-text-destructive | |||||
| bg-state-destructive-hover | |||||
| } | |||||
| } |
| import type { CSSProperties } from 'react' | |||||
| import React from 'react' | |||||
| import { type VariantProps, cva } from 'class-variance-authority' | |||||
| import classNames from '@/utils/classnames' | |||||
| enum ActionButtonState { | |||||
| Destructive = 'destructive', | |||||
| Active = 'active', | |||||
| Disabled = 'disabled', | |||||
| Default = '', | |||||
| } | |||||
| const actionButtonVariants = cva( | |||||
| 'action-btn', | |||||
| { | |||||
| variants: { | |||||
| size: { | |||||
| xs: 'action-btn-xs', | |||||
| m: 'action-btn-m', | |||||
| l: 'action-btn-l', | |||||
| xl: 'action-btn-xl', | |||||
| }, | |||||
| }, | |||||
| defaultVariants: { | |||||
| size: 'm', | |||||
| }, | |||||
| }, | |||||
| ) | |||||
| export type ActionButtonProps = { | |||||
| size?: 'xs' | 'm' | 'l' | 'xl' | |||||
| state?: ActionButtonState | |||||
| styleCss?: CSSProperties | |||||
| } & React.ButtonHTMLAttributes<HTMLButtonElement> & VariantProps<typeof actionButtonVariants> | |||||
| function getActionButtonState(state: ActionButtonState) { | |||||
| switch (state) { | |||||
| case ActionButtonState.Destructive: | |||||
| return 'action-btn-destructive' | |||||
| case ActionButtonState.Active: | |||||
| return 'action-btn-active' | |||||
| case ActionButtonState.Disabled: | |||||
| return 'action-btn-disabled' | |||||
| default: | |||||
| return '' | |||||
| } | |||||
| } | |||||
| const ActionButton = React.forwardRef<HTMLButtonElement, ActionButtonProps>( | |||||
| ({ className, size, state = ActionButtonState.Default, styleCss, children, ...props }, ref) => { | |||||
| return ( | |||||
| <button | |||||
| type='button' | |||||
| className={classNames( | |||||
| actionButtonVariants({ className, size }), | |||||
| getActionButtonState(state), | |||||
| )} | |||||
| ref={ref} | |||||
| style={styleCss} | |||||
| {...props} | |||||
| > | |||||
| {children} | |||||
| </button> | |||||
| ) | |||||
| }, | |||||
| ) | |||||
| ActionButton.displayName = 'ActionButton' | |||||
| export default ActionButton | |||||
| export { ActionButton, ActionButtonState, actionButtonVariants } |
| hideArrow?: boolean | hideArrow?: boolean | ||||
| popupClassName?: string | popupClassName?: string | ||||
| offset?: OffsetOptions | offset?: OffsetOptions | ||||
| asChild?: boolean | |||||
| } | } | ||||
| const arrow = ( | const arrow = ( | ||||
| hideArrow, | hideArrow, | ||||
| popupClassName, | popupClassName, | ||||
| offset, | offset, | ||||
| asChild, | |||||
| }) => { | }) => { | ||||
| const [open, setOpen] = useState(false) | const [open, setOpen] = useState(false) | ||||
| const [isHoverPopup, { | const [isHoverPopup, { | ||||
| } | } | ||||
| }} | }} | ||||
| onMouseLeave={() => triggerMethod === 'hover' && handleLeave(true)} | onMouseLeave={() => triggerMethod === 'hover' && handleLeave(true)} | ||||
| asChild={asChild} | |||||
| > | > | ||||
| {children} | {children} | ||||
| </PortalToFollowElemTrigger> | </PortalToFollowElemTrigger> |
| IS_CE_EDITION | IS_CE_EDITION | ||||
| ? <Link href={'https://github.com/langgenius/dify/blob/main/LICENSE'} target='_blank' rel='noopener noreferrer'>Open Source License</Link> | ? <Link href={'https://github.com/langgenius/dify/blob/main/LICENSE'} target='_blank' rel='noopener noreferrer'>Open Source License</Link> | ||||
| : <> | : <> | ||||
| <Link href='https://dify.ai/privacy' target='_blank' rel='noopener noreferrer'>Privacy Policy</Link>, | |||||
| <Link href='https://dify.ai/privacy' target='_blank' rel='noopener noreferrer'>Privacy Policy</Link>,<span> </span> | |||||
| <Link href='https://dify.ai/terms' target='_blank' rel='noopener noreferrer'>Terms of Service</Link> | <Link href='https://dify.ai/terms' target='_blank' rel='noopener noreferrer'>Terms of Service</Link> | ||||
| </> | </> | ||||
| } | } |
| import { useEventEmitterContextContext } from '@/context/event-emitter' | import { useEventEmitterContextContext } from '@/context/event-emitter' | ||||
| import { PROMPT_EDITOR_INSERT_QUICKLY } from '@/app/components/base/prompt-editor/plugins/update-block' | import { PROMPT_EDITOR_INSERT_QUICKLY } from '@/app/components/base/prompt-editor/plugins/update-block' | ||||
| import { Variable02 } from '@/app/components/base/icons/src/vender/solid/development' | import { Variable02 } from '@/app/components/base/icons/src/vender/solid/development' | ||||
| import ActionButton from '@/app/components/base/action-button' | |||||
| import TooltipPlus from '@/app/components/base/tooltip-plus' | import TooltipPlus from '@/app/components/base/tooltip-plus' | ||||
| import CodeEditor from '@/app/components/workflow/nodes/_base/components/editor/code-editor/editor-support-vars' | import CodeEditor from '@/app/components/workflow/nodes/_base/components/editor/code-editor/editor-support-vars' | ||||
| import Switch from '@/app/components/base/switch' | import Switch from '@/app/components/base/switch' | ||||
| <Wrap className={cn(className, wrapClassName)} style={wrapStyle} isInNode isExpand={isExpand}> | <Wrap className={cn(className, wrapClassName)} style={wrapStyle} isInNode isExpand={isExpand}> | ||||
| <div ref={ref} className={cn(isFocus ? s.gradientBorder : 'bg-gray-100', isExpand && 'h-full', '!rounded-[9px] p-0.5')}> | <div ref={ref} className={cn(isFocus ? s.gradientBorder : 'bg-gray-100', isExpand && 'h-full', '!rounded-[9px] p-0.5')}> | ||||
| <div className={cn(isFocus ? 'bg-gray-50' : 'bg-gray-100', isExpand && 'h-full flex flex-col', 'rounded-lg')}> | <div className={cn(isFocus ? 'bg-gray-50' : 'bg-gray-100', isExpand && 'h-full flex flex-col', 'rounded-lg')}> | ||||
| <div className={cn(headerClassName, 'pt-1 pl-3 pr-2 flex justify-between h-6 items-center')}> | |||||
| <div className={cn(headerClassName, 'pt-1 pl-3 pr-2 flex justify-between items-center')}> | |||||
| <div className='leading-4 text-xs font-semibold text-gray-700 uppercase'>{title}</div> | <div className='leading-4 text-xs font-semibold text-gray-700 uppercase'>{title}</div> | ||||
| <div className='flex items-center'> | <div className='flex items-center'> | ||||
| <div className='leading-[18px] text-xs font-medium text-gray-500'>{value?.length || 0}</div> | <div className='leading-[18px] text-xs font-medium text-gray-500'>{value?.length || 0}</div> | ||||
| <div className='w-px h-3 ml-2 mr-2 bg-gray-200'></div> | <div className='w-px h-3 ml-2 mr-2 bg-gray-200'></div> | ||||
| {/* Operations */} | {/* Operations */} | ||||
| <div className='flex items-center space-x-2'> | |||||
| <div className='flex items-center space-x-[2px]'> | |||||
| {isSupportJinja && ( | {isSupportJinja && ( | ||||
| <TooltipPlus | <TooltipPlus | ||||
| popupContent={ | popupContent={ | ||||
| {!readOnly && ( | {!readOnly && ( | ||||
| <TooltipPlus | <TooltipPlus | ||||
| popupContent={`${t('workflow.common.insertVarTip')}`} | popupContent={`${t('workflow.common.insertVarTip')}`} | ||||
| asChild | |||||
| > | > | ||||
| <Variable02 className='w-3.5 h-3.5 text-gray-500 cursor-pointer' onClick={handleInsertVariable} /> | |||||
| <ActionButton onClick={handleInsertVariable}> | |||||
| <Variable02 className='w-4 h-4' /> | |||||
| </ActionButton> | |||||
| </TooltipPlus> | </TooltipPlus> | ||||
| )} | )} | ||||
| {showRemove && ( | {showRemove && ( | ||||
| <RiDeleteBinLine className='w-3.5 h-3.5 text-gray-500 cursor-pointer' onClick={onRemove} /> | |||||
| <ActionButton onClick={onRemove}> | |||||
| <RiDeleteBinLine className='w-4 h-4' /> | |||||
| </ActionButton> | |||||
| )} | )} | ||||
| {!isCopied | {!isCopied | ||||
| ? ( | ? ( | ||||
| <Clipboard className='w-3.5 h-3.5 text-gray-500 cursor-pointer' onClick={handleCopy} /> | |||||
| <ActionButton onClick={handleCopy}> | |||||
| <Clipboard className='w-4 h-4' /> | |||||
| </ActionButton> | |||||
| ) | ) | ||||
| : ( | : ( | ||||
| <ClipboardCheck className='mx-1 w-3.5 h-3.5 text-gray-500' /> | |||||
| <ActionButton> | |||||
| <ClipboardCheck className='w-4 h-4' /> | |||||
| </ActionButton> | |||||
| ) | ) | ||||
| } | } | ||||
| <ToggleExpandBtn isExpand={isExpand} onExpandChange={setIsExpand} /> | <ToggleExpandBtn isExpand={isExpand} onExpandChange={setIsExpand} /> |
| <div | <div | ||||
| onClick={toggleShow} | onClick={toggleShow} | ||||
| className={cn(showOption && 'bg-black/5', 'flex items-center h-5 pl-1 pr-0.5 rounded-md text-xs font-semibold text-gray-700 cursor-pointer hover:bg-black/5')}> | className={cn(showOption && 'bg-black/5', 'flex items-center h-5 pl-1 pr-0.5 rounded-md text-xs font-semibold text-gray-700 cursor-pointer hover:bg-black/5')}> | ||||
| <div className={cn(triggerClassName, 'text-sm font-semibold', uppercase && 'uppercase', noValue && 'text-gray-400')}>{!noValue ? item?.label : placeholder}</div> | |||||
| <div className={cn(triggerClassName, 'text-xs font-semibold', uppercase && 'uppercase', noValue && 'text-gray-400')}>{!noValue ? item?.label : placeholder}</div> | |||||
| {!readonly && <DropDownIcon className='w-3 h-3 ' />} | {!readonly && <DropDownIcon className='w-3 h-3 ' />} | ||||
| </div> | </div> | ||||
| )} | )} |
| RiCollapseDiagonalLine, | RiCollapseDiagonalLine, | ||||
| RiExpandDiagonalLine, | RiExpandDiagonalLine, | ||||
| } from '@remixicon/react' | } from '@remixicon/react' | ||||
| import ActionButton from '@/app/components/base/action-button' | |||||
| type Props = { | type Props = { | ||||
| isExpand: boolean | isExpand: boolean | ||||
| const Icon = isExpand ? RiCollapseDiagonalLine : RiExpandDiagonalLine | const Icon = isExpand ? RiCollapseDiagonalLine : RiExpandDiagonalLine | ||||
| return ( | return ( | ||||
| <Icon className='w-3.5 h-3.5 text-gray-500 cursor-pointer' onClick={handleToggle} /> | |||||
| <ActionButton onClick={handleToggle}> | |||||
| <Icon className='w-4 h-4' /> | |||||
| </ActionButton> | |||||
| ) | ) | ||||
| } | } | ||||
| export default React.memo(ExpandBtn) | export default React.memo(ExpandBtn) |
| import { useBoolean } from 'ahooks' | import { useBoolean } from 'ahooks' | ||||
| import cn from 'classnames' | import cn from 'classnames' | ||||
| import { Generator } from '@/app/components/base/icons/src/vender/other' | import { Generator } from '@/app/components/base/icons/src/vender/other' | ||||
| import { ActionButton } from '@/app/components/base/action-button' | |||||
| import GetAutomaticResModal from '@/app/components/app/configuration/config/automatic/get-automatic-res' | import GetAutomaticResModal from '@/app/components/app/configuration/config/automatic/get-automatic-res' | ||||
| import { AppType } from '@/types/app' | import { AppType } from '@/types/app' | ||||
| import type { AutomaticRes } from '@/service/debug' | import type { AutomaticRes } from '@/service/debug' | ||||
| }, [onGenerated, showAutomaticFalse]) | }, [onGenerated, showAutomaticFalse]) | ||||
| return ( | return ( | ||||
| <div className={cn(className)}> | <div className={cn(className)}> | ||||
| <div className='p-[5px] rounded-md hover:bg-[#155EEF]/8 cursor-pointer' onClick={showAutomaticTrue}> | |||||
| <Generator className='w-3.5 h-3.5 text-primary-600' /> | |||||
| </div> | |||||
| <ActionButton | |||||
| className='hover:bg-[#155EFF]/8' | |||||
| onClick={showAutomaticTrue}> | |||||
| <Generator className='w-4 h-4 text-primary-600' /> | |||||
| </ActionButton> | |||||
| {showAutomatic && ( | {showAutomatic && ( | ||||
| <GetAutomaticResModal | <GetAutomaticResModal | ||||
| mode={AppType.chat} | mode={AppType.chat} |
| } | } | ||||
| @import '../components/base/button/index.css'; | @import '../components/base/button/index.css'; | ||||
| @import '../components/base/action-button/index.css'; | |||||
| @import '../components/base/modal/index.css'; | @import '../components/base/modal/index.css'; | ||||
| @tailwind utilities; | @tailwind utilities; |