mirror of
https://git.mirrors.martin98.com/https://github.com/langgenius/dify.git
synced 2025-08-11 17:59:03 +08:00
feat: prompt IDE support change height (#2232)
This commit is contained in:
parent
bd0af2e921
commit
20bd33fada
@ -10,6 +10,7 @@ import produce from 'immer'
|
||||
import s from './style.module.css'
|
||||
import MessageTypeSelector from './message-type-selector'
|
||||
import ConfirmAddVar from './confirm-add-var'
|
||||
import PromptEditorHeightResizeWrap from './prompt-editor-height-resize-wrap'
|
||||
import type { PromptRole, PromptVariable } from '@/models/debug'
|
||||
import { HelpCircle, Trash03 } from '@/app/components/base/icons/src/vender/line/general'
|
||||
import { Clipboard, ClipboardCheck } from '@/app/components/base/icons/src/vender/line/files'
|
||||
@ -25,7 +26,6 @@ import { useToastContext } from '@/app/components/base/toast'
|
||||
import { useEventEmitterContextContext } from '@/context/event-emitter'
|
||||
import { ADD_EXTERNAL_DATA_TOOL } from '@/app/components/app/configuration/config-var'
|
||||
import { INSERT_VARIABLE_VALUE_BLOCK_COMMAND } from '@/app/components/base/prompt-editor/plugins/variable-block'
|
||||
|
||||
type Props = {
|
||||
type: PromptRole
|
||||
isChatMode: boolean
|
||||
@ -130,7 +130,8 @@ const AdvancedPromptInput: FC<Props> = ({
|
||||
}
|
||||
}
|
||||
|
||||
const editorHeight = isChatMode ? 'h-[200px]' : 'h-[508px]'
|
||||
const minHeight = 102
|
||||
const [editorHeight, setEditorHeight] = React.useState(isChatMode ? 200 : 508)
|
||||
const contextMissing = (
|
||||
<div
|
||||
className='flex justify-between items-center h-11 pt-2 pr-3 pb-1 pl-4 rounded-tl-xl rounded-tr-xl'
|
||||
@ -139,7 +140,7 @@ const AdvancedPromptInput: FC<Props> = ({
|
||||
}}
|
||||
>
|
||||
<div className='flex items-center pr-2' >
|
||||
<AlertCircle className='mr-1 w-4 h-4 text-[#F79009]'/>
|
||||
<AlertCircle className='mr-1 w-4 h-4 text-[#F79009]' />
|
||||
<div className='leading-[18px] text-[13px] font-medium text-[#DC6803]'>{t('appDebug.promptMode.contextMissing')}</div>
|
||||
</div>
|
||||
<div
|
||||
@ -190,9 +191,19 @@ const AdvancedPromptInput: FC<Props> = ({
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className={cn(editorHeight, 'px-4 min-h-[102px] overflow-y-auto text-sm text-gray-700')}>
|
||||
<PromptEditorHeightResizeWrap
|
||||
className='px-4 min-h-[102px] overflow-y-auto text-sm text-gray-700'
|
||||
height={editorHeight}
|
||||
minHeight={minHeight}
|
||||
onHeightChange={setEditorHeight}
|
||||
footer={(
|
||||
<div className='pl-4 pb-2 flex'>
|
||||
<div className="h-[18px] leading-[18px] px-1 rounded-md bg-gray-100 text-xs text-gray-500">{value.length}</div>
|
||||
</div>
|
||||
)}
|
||||
>
|
||||
<PromptEditor
|
||||
className={editorHeight}
|
||||
className='min-h-[84px]'
|
||||
value={value}
|
||||
contextBlock={{
|
||||
show: true,
|
||||
@ -233,10 +244,8 @@ const AdvancedPromptInput: FC<Props> = ({
|
||||
onChange={handlePromptChange}
|
||||
onBlur={handleBlur}
|
||||
/>
|
||||
</div>
|
||||
<div className='pl-4 pb-2 flex'>
|
||||
<div className="h-[18px] leading-[18px] px-1 rounded-md bg-gray-100 text-xs text-gray-500">{value.length}</div>
|
||||
</div>
|
||||
</PromptEditorHeightResizeWrap>
|
||||
|
||||
</div>
|
||||
|
||||
{isShowConfirmAddVar && (
|
||||
|
@ -0,0 +1,91 @@
|
||||
'use client'
|
||||
import React, { useCallback, useEffect, useState } from 'react'
|
||||
import type { FC } from 'react'
|
||||
import { useDebounceFn } from 'ahooks'
|
||||
import cn from 'classnames'
|
||||
|
||||
type Props = {
|
||||
className?: string
|
||||
height: number
|
||||
minHeight: number
|
||||
onHeightChange: (height: number) => void
|
||||
children: JSX.Element
|
||||
footer?: JSX.Element
|
||||
}
|
||||
|
||||
const PromptEditorHeightResizeWrap: FC<Props> = ({
|
||||
className,
|
||||
height,
|
||||
minHeight,
|
||||
onHeightChange,
|
||||
children,
|
||||
footer,
|
||||
}) => {
|
||||
const [clientY, setClientY] = useState(0)
|
||||
const [isResizing, setIsResizing] = useState(false)
|
||||
const [prevUserSelectStyle, setPrevUserSelectStyle] = useState(getComputedStyle(document.body).userSelect)
|
||||
|
||||
const handleStartResize = useCallback((e: React.MouseEvent<HTMLElement>) => {
|
||||
setClientY(e.clientY)
|
||||
setIsResizing(true)
|
||||
setPrevUserSelectStyle(getComputedStyle(document.body).userSelect)
|
||||
document.body.style.userSelect = 'none'
|
||||
}, [])
|
||||
|
||||
const handleStopResize = useCallback(() => {
|
||||
setIsResizing(false)
|
||||
document.body.style.userSelect = prevUserSelectStyle
|
||||
}, [prevUserSelectStyle])
|
||||
|
||||
const { run: didHandleResize } = useDebounceFn((e) => {
|
||||
if (!isResizing)
|
||||
return
|
||||
|
||||
const offset = e.clientY - clientY
|
||||
let newHeight = height + offset
|
||||
setClientY(e.clientY)
|
||||
if (newHeight < minHeight)
|
||||
newHeight = minHeight
|
||||
onHeightChange(newHeight)
|
||||
}, {
|
||||
wait: 0,
|
||||
})
|
||||
|
||||
const handleResize = useCallback(didHandleResize, [isResizing, height, minHeight, clientY])
|
||||
|
||||
useEffect(() => {
|
||||
document.addEventListener('mousemove', handleResize)
|
||||
return () => {
|
||||
document.removeEventListener('mousemove', handleResize)
|
||||
}
|
||||
}, [handleResize])
|
||||
|
||||
useEffect(() => {
|
||||
document.addEventListener('mouseup', handleStopResize)
|
||||
return () => {
|
||||
document.removeEventListener('mouseup', handleStopResize)
|
||||
}
|
||||
}, [handleStopResize])
|
||||
|
||||
return (
|
||||
<div
|
||||
className='relative'
|
||||
>
|
||||
<div className={cn(className, 'overflow-y-auto')}
|
||||
style={{
|
||||
height,
|
||||
}}
|
||||
>
|
||||
{children}
|
||||
</div>
|
||||
{/* resize handler */}
|
||||
{footer}
|
||||
<div
|
||||
className='absolute bottom-0 left-0 w-full flex justify-center h-2 cursor-row-resize'
|
||||
onMouseDown={handleStartResize}>
|
||||
<div className='w-5 h-[3px] rounded-sm bg-gray-300'></div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
export default React.memo(PromptEditorHeightResizeWrap)
|
@ -1,6 +1,6 @@
|
||||
'use client'
|
||||
import type { FC } from 'react'
|
||||
import React from 'react'
|
||||
import React, { useState } from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import { useBoolean } from 'ahooks'
|
||||
import cn from 'classnames'
|
||||
@ -8,6 +8,7 @@ import produce from 'immer'
|
||||
import { useContext } from 'use-context-selector'
|
||||
import ConfirmAddVar from './confirm-add-var'
|
||||
import s from './style.module.css'
|
||||
import PromptEditorHeightResizeWrap from './prompt-editor-height-resize-wrap'
|
||||
import { PromptMode, type PromptVariable } from '@/models/debug'
|
||||
import Tooltip from '@/app/components/base/tooltip'
|
||||
import { AppType } from '@/types/app'
|
||||
@ -125,6 +126,8 @@ const Prompt: FC<ISimplePromptInput> = ({
|
||||
setIntroduction(res.opening_statement)
|
||||
showAutomaticFalse()
|
||||
}
|
||||
const minHeight = 228
|
||||
const [editorHeight, setEditorHeight] = useState(minHeight)
|
||||
|
||||
return (
|
||||
<div className={cn(!readonly ? `${s.gradientBorder}` : 'bg-gray-50', ' relative shadow-md')}>
|
||||
@ -161,7 +164,12 @@ const Prompt: FC<ISimplePromptInput> = ({
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
<div className='px-4 py-2 min-h-[228px] max-h-[156px] overflow-y-auto bg-white rounded-xl text-sm text-gray-700'>
|
||||
<PromptEditorHeightResizeWrap
|
||||
className='px-4 py-2 min-h-[228px] bg-white rounded-xl text-sm text-gray-700'
|
||||
height={editorHeight}
|
||||
minHeight={minHeight}
|
||||
onHeightChange={setEditorHeight}
|
||||
>
|
||||
<PromptEditor
|
||||
className='min-h-[210px]'
|
||||
value={promptTemplate}
|
||||
@ -208,7 +216,7 @@ const Prompt: FC<ISimplePromptInput> = ({
|
||||
handleChange(promptTemplate, getVars(promptTemplate))
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</PromptEditorHeightResizeWrap>
|
||||
</div>
|
||||
|
||||
{isShowConfirmAddVar && (
|
||||
|
Loading…
x
Reference in New Issue
Block a user