mirror of
https://github.com/voideditor/void
synced 2026-05-24 09:58:23 +00:00
prepare edit button
This commit is contained in:
parent
7dd5171bd2
commit
261736bde5
2 changed files with 73 additions and 28 deletions
|
|
@ -28,6 +28,7 @@ import { useScrollbarStyles } from '../util/useScrollbarStyles.js';
|
||||||
import { VOID_CTRL_L_ACTION_ID } from '../../../actionIDs.js';
|
import { VOID_CTRL_L_ACTION_ID } from '../../../actionIDs.js';
|
||||||
import { ArrowBigLeftDash, CopyX, Delete, FileX2, SquareX, X } from 'lucide-react';
|
import { ArrowBigLeftDash, CopyX, Delete, FileX2, SquareX, X } from 'lucide-react';
|
||||||
import { filenameToVscodeLanguage } from '../../../helpers/detectLanguage.js';
|
import { filenameToVscodeLanguage } from '../../../helpers/detectLanguage.js';
|
||||||
|
import { Pencil } from 'lucide-react'
|
||||||
|
|
||||||
|
|
||||||
export const IconX = ({ size, className = '', ...props }: { size: number, className?: string } & React.SVGProps<SVGSVGElement>) => {
|
export const IconX = ({ size, className = '', ...props }: { size: number, className?: string } & React.SVGProps<SVGSVGElement>) => {
|
||||||
|
|
@ -332,7 +333,7 @@ export const SelectedFiles = (
|
||||||
{/* X button */}
|
{/* X button */}
|
||||||
{type === 'staging' &&
|
{type === 'staging' &&
|
||||||
<span
|
<span
|
||||||
className='cursor-pointer hover:bg-vscode-toolbar-hover-bg rounded-md z-1'
|
className='cursor-pointer hover:brightness-95 rounded-md z-1'
|
||||||
onClick={(e) => {
|
onClick={(e) => {
|
||||||
e.stopPropagation(); // don't open/close selection
|
e.stopPropagation(); // don't open/close selection
|
||||||
if (type !== 'staging') return;
|
if (type !== 'staging') return;
|
||||||
|
|
@ -346,7 +347,7 @@ export const SelectedFiles = (
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* delete all selections button */}
|
{/* clear all selections button */}
|
||||||
{type !== 'staging' || selections.length === 0 || i !== selections.length - 1
|
{type !== 'staging' || selections.length === 0 || i !== selections.length - 1
|
||||||
? null
|
? null
|
||||||
: <div key={i} className={`flex items-center gap-0.5 ${isThisSelectionOpened ? 'w-full' : ''}`}>
|
: <div key={i} className={`flex items-center gap-0.5 ${isThisSelectionOpened ? 'w-full' : ''}`}>
|
||||||
|
|
@ -357,10 +358,14 @@ export const SelectedFiles = (
|
||||||
>
|
>
|
||||||
<Delete
|
<Delete
|
||||||
size={16}
|
size={16}
|
||||||
className='stroke-[1] stroke-void-fg-3
|
className={`stroke-[1]
|
||||||
fill-void-bg-3
|
stroke-void-fg-1
|
||||||
hover:brightness-105
|
fill-void-bg-3
|
||||||
cursor-pointer'
|
opacity-40
|
||||||
|
hover:opacity-60
|
||||||
|
transition-all duration-150
|
||||||
|
cursor-pointer
|
||||||
|
`}
|
||||||
onClick={() => { setStaging([]) }}
|
onClick={() => { setStaging([]) }}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
@ -381,7 +386,8 @@ export const SelectedFiles = (
|
||||||
maxHeight={100}
|
maxHeight={100}
|
||||||
showScrollbars={true}
|
showScrollbars={true}
|
||||||
/>
|
/>
|
||||||
</div>}
|
</div>
|
||||||
|
}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
})}
|
})}
|
||||||
|
|
@ -393,6 +399,7 @@ export const SelectedFiles = (
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
const ChatBubble = ({ chatMessage, isLoading }: {
|
const ChatBubble = ({ chatMessage, isLoading }: {
|
||||||
chatMessage: ChatMessage,
|
chatMessage: ChatMessage,
|
||||||
isLoading?: boolean,
|
isLoading?: boolean,
|
||||||
|
|
@ -400,6 +407,9 @@ const ChatBubble = ({ chatMessage, isLoading }: {
|
||||||
|
|
||||||
const role = chatMessage.role
|
const role = chatMessage.role
|
||||||
|
|
||||||
|
// edit mode state
|
||||||
|
const [isEditMode, setIsEditMode] = useState(false)
|
||||||
|
|
||||||
if (!chatMessage.displayContent)
|
if (!chatMessage.displayContent)
|
||||||
return null
|
return null
|
||||||
|
|
||||||
|
|
@ -409,30 +419,61 @@ const ChatBubble = ({ chatMessage, isLoading }: {
|
||||||
chatbubbleContents = <>
|
chatbubbleContents = <>
|
||||||
<SelectedFiles type='past' selections={chatMessage.selections} />
|
<SelectedFiles type='past' selections={chatMessage.selections} />
|
||||||
{chatMessage.displayContent}
|
{chatMessage.displayContent}
|
||||||
|
|
||||||
|
{/* {!isEditMode ? chatMessage.displayContent : <></>} */}
|
||||||
|
{/* edit mode content */}
|
||||||
|
{/* TODO this should be the same input box as in the Sidebar */}
|
||||||
|
{/* <textarea
|
||||||
|
value={editModeText}
|
||||||
|
className={`
|
||||||
|
w-full max-w-full
|
||||||
|
h-auto min-h-[81px] max-h-[500px]
|
||||||
|
bg-void-bg-1 resize-none
|
||||||
|
`}
|
||||||
|
style={{ marginTop: 0 }}
|
||||||
|
hidden={!isEditMode}
|
||||||
|
/> */}
|
||||||
|
|
||||||
</>
|
</>
|
||||||
}
|
}
|
||||||
else if (role === 'assistant') {
|
else if (role === 'assistant') {
|
||||||
chatbubbleContents = <ChatMarkdownRender string={chatMessage.displayContent} /> // sectionsHTML
|
chatbubbleContents = <ChatMarkdownRender string={chatMessage.displayContent} />
|
||||||
}
|
}
|
||||||
|
|
||||||
return <div
|
return <div
|
||||||
// align chatbubble accoridng to role
|
// align chatbubble accoridng to role
|
||||||
className={`
|
className={`
|
||||||
${role === 'user' ? `px-2 self-end w-fit max-w-full` : ''}
|
relative
|
||||||
${role === 'assistant' ? `px-2 self-start w-full max-w-full` : ''}
|
${isEditMode ? 'px-2 w-full max-w-full'
|
||||||
`}
|
: role === 'user' ? `px-2 self-end w-fit max-w-full`
|
||||||
|
: role === 'assistant' ? `px-2 self-start w-full max-w-full` : ''
|
||||||
|
}
|
||||||
|
`}
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
// style chatbubble according to role
|
// style chatbubble according to role
|
||||||
className={`
|
className={`
|
||||||
p-2 text-left space-y-2 rounded-lg
|
p-2 text-left space-y-2 rounded-lg
|
||||||
overflow-x-auto max-w-full
|
overflow-x-auto max-w-full
|
||||||
${role === 'user' ? 'bg-vscode-input-bg text-vscode-input-fg' : ''}
|
${role === 'user' ? 'bg-void-bg-1 text-void-fg-1' : ''}
|
||||||
`}
|
`}
|
||||||
>
|
>
|
||||||
{chatbubbleContents}
|
{chatbubbleContents}
|
||||||
{isLoading && <IconLoading className='opacity-50 text-sm' />}
|
{isLoading && <IconLoading className='opacity-50 text-sm' />}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
{/* edit button */}
|
||||||
|
{/* {role === 'user' &&
|
||||||
|
<Pencil
|
||||||
|
size={16}
|
||||||
|
className={`
|
||||||
|
absolute top-0 right-2
|
||||||
|
translate-x-0 -translate-y-0
|
||||||
|
cursor-pointer z-1
|
||||||
|
`}
|
||||||
|
onClick={() => { setIsEditMode(v => !v); }}
|
||||||
|
/>
|
||||||
|
} */}
|
||||||
</div>
|
</div>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -610,7 +651,7 @@ export const SidebarChat = () => {
|
||||||
>
|
>
|
||||||
{/* thread selector */}
|
{/* thread selector */}
|
||||||
<div ref={historyRef}
|
<div ref={historyRef}
|
||||||
className={`w-full h-auto mb-2 ${isHistoryOpen ? '' : 'hidden'} ring-2 ring-widget-shadow ring-inset z-10`}
|
className={`w-full h-auto ${isHistoryOpen ? '' : 'hidden'} ring-2 ring-widget-shadow ring-inset z-10`}
|
||||||
>
|
>
|
||||||
<SidebarThreadSelector />
|
<SidebarThreadSelector />
|
||||||
</div>
|
</div>
|
||||||
|
|
@ -623,6 +664,7 @@ export const SidebarChat = () => {
|
||||||
flex flex-col gap-0
|
flex flex-col gap-0
|
||||||
overflow-x-hidden
|
overflow-x-hidden
|
||||||
overflow-y-auto
|
overflow-y-auto
|
||||||
|
${previousMessages.length > 0 ? 'pt-2' : ''}
|
||||||
`}
|
`}
|
||||||
style={{ maxHeight: sidebarDimensions.height - historyDimensions.height - formDimensions.height - 30 }} // the height of the previousMessages is determined by all other heights
|
style={{ maxHeight: sidebarDimensions.height - historyDimensions.height - formDimensions.height - 30 }} // the height of the previousMessages is determined by all other heights
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -51,9 +51,8 @@ export const SidebarThreadSelector = () => {
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* a list of all the past threads */}
|
{/* a list of all the past threads */}
|
||||||
|
<div className="px-1">
|
||||||
<div className="px-1 ">
|
<ul className="flex flex-col gap-y-0.5 overflow-y-auto list-disc">
|
||||||
<ul className="flex flex-col gap-y-1 overflow-y-auto list-disc">
|
|
||||||
|
|
||||||
{sortedThreadIds.length === 0
|
{sortedThreadIds.length === 0
|
||||||
|
|
||||||
|
|
@ -66,25 +65,26 @@ export const SidebarThreadSelector = () => {
|
||||||
|
|
||||||
const pastThread = allThreads[threadId];
|
const pastThread = allThreads[threadId];
|
||||||
let firstMsg = null;
|
let firstMsg = null;
|
||||||
let secondMsg = null;
|
// let secondMsg = null;
|
||||||
|
|
||||||
const firstMsgIdx = pastThread.messages.findIndex(
|
const firstMsgIdx = pastThread.messages.findIndex(
|
||||||
(msg) => msg.role !== 'system' && !!msg.displayContent
|
(msg) => msg.role !== 'system' && !!msg.displayContent
|
||||||
);
|
);
|
||||||
|
|
||||||
if (firstMsgIdx !== -1) {
|
if (firstMsgIdx !== -1) {
|
||||||
firstMsg = truncate(pastThread.messages[firstMsgIdx].displayContent ?? '');
|
// firstMsg = truncate(pastThread.messages[firstMsgIdx].displayContent ?? '');
|
||||||
|
firstMsg = pastThread.messages[firstMsgIdx].displayContent ?? '';
|
||||||
} else {
|
} else {
|
||||||
firstMsg = '""';
|
firstMsg = '""';
|
||||||
}
|
}
|
||||||
|
|
||||||
const secondMsgIdx = pastThread.messages.findIndex(
|
// const secondMsgIdx = pastThread.messages.findIndex(
|
||||||
(msg, i) => msg.role !== 'system' && !!msg.displayContent && i > firstMsgIdx
|
// (msg, i) => msg.role !== 'system' && !!msg.displayContent && i > firstMsgIdx
|
||||||
);
|
// );
|
||||||
|
|
||||||
if (secondMsgIdx !== -1) {
|
// if (secondMsgIdx !== -1) {
|
||||||
secondMsg = truncate(pastThread.messages[secondMsgIdx].displayContent ?? '');
|
// secondMsg = truncate(pastThread.messages[secondMsgIdx].displayContent ?? '');
|
||||||
}
|
// }
|
||||||
|
|
||||||
const numMessages = pastThread.messages.filter(
|
const numMessages = pastThread.messages.filter(
|
||||||
(msg) => msg.role !== 'system'
|
(msg) => msg.role !== 'system'
|
||||||
|
|
@ -93,17 +93,20 @@ export const SidebarThreadSelector = () => {
|
||||||
return (
|
return (
|
||||||
<li key={pastThread.id}>
|
<li key={pastThread.id}>
|
||||||
<button
|
<button
|
||||||
|
type='button'
|
||||||
className={`
|
className={`
|
||||||
hover:bg-void-bg-1
|
hover:bg-void-bg-1
|
||||||
${threadsState._currentThreadId === pastThread.id ? 'bg-void-bg-1' : ''}
|
${threadsState._currentThreadId === pastThread.id ? 'bg-void-bg-1' : ''}
|
||||||
rounded-sm px-2 py-1
|
rounded-sm px-2 py-1
|
||||||
w-full
|
w-full
|
||||||
text-left
|
text-left
|
||||||
|
flex items-center
|
||||||
`}
|
`}
|
||||||
onClick={() => threadsStateService.switchToThread(pastThread.id)}
|
onClick={() => threadsStateService.switchToThread(pastThread.id)}
|
||||||
title={new Date(pastThread.createdAt).toLocaleString()}
|
title={new Date(pastThread.createdAt).toLocaleString()}
|
||||||
>
|
>
|
||||||
{`${firstMsg} (${numMessages})`}
|
<div className='truncate'>{`${firstMsg}`}</div>
|
||||||
|
<div>{`\u00A0(${numMessages})`}</div>
|
||||||
</button>
|
</button>
|
||||||
</li>
|
</li>
|
||||||
);
|
);
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue