mirror of
https://github.com/stablyai/orca.git
synced 2026-10-18 16:03:17 +00:00
192 lines
7.3 KiB
TypeScript
192 lines
7.3 KiB
TypeScript
import { Suspense, type JSX, type Ref } from 'react'
|
|
import { useAppStore } from '@/store'
|
|
import { findWorktreeById } from '@/store/slices/worktree-helpers'
|
|
import type { OpenFile } from '@/store/slices/editor'
|
|
import { EditorContent } from './EditorContent'
|
|
import { EditorPanelHeader } from './EditorPanelHeader'
|
|
import { UntitledFileRenameDialog } from './UntitledFileRenameDialog'
|
|
import type { getEditorPanelRenderModel } from './editor-panel-render-model'
|
|
import type { DiffContent, FileContent } from './editor-panel-content-types'
|
|
import type { EditorToggleValue } from './EditorViewToggle'
|
|
import { getUntitledFileRoot } from './untitled-file-rename-path'
|
|
import { translate } from '@/i18n/i18n'
|
|
|
|
type EditorPanelRenderModel = ReturnType<typeof getEditorPanelRenderModel>
|
|
|
|
type EditorPanelShellProps = {
|
|
panelRef: Ref<HTMLDivElement>
|
|
activeFile: OpenFile
|
|
activeViewStateId: string | null | undefined
|
|
model: EditorPanelRenderModel
|
|
copiedPathVisible: boolean
|
|
showMarkdownTableOfContents: boolean
|
|
canShowMarkdownFrontmatterToggle: boolean
|
|
markdownFrontmatterVisible: boolean
|
|
sideBySide: boolean
|
|
openFiles: OpenFile[]
|
|
fileContents: Record<string, FileContent>
|
|
diffContents: Record<string, DiffContent>
|
|
editorDrafts: Record<string, string>
|
|
pendingEditorReveal: ReturnType<typeof useAppStore.getState>['pendingEditorReveal']
|
|
renameDialogFile: OpenFile | null
|
|
renameError: string | null
|
|
disableRenameBrowse: boolean
|
|
onCopyPath: () => void
|
|
onOpenDiffTargetFile: (preferredMarkdownViewMode?: 'rich') => void
|
|
onOpenPreviewToSide: () => void
|
|
onOpenMarkdownPreview: () => void
|
|
onOpenContainingFolder: () => void
|
|
onToggleSideBySide: () => void
|
|
onEditorToggleChange: (next: EditorToggleValue) => void
|
|
onToggleMarkdownTableOfContents: () => void
|
|
onToggleMarkdownFrontmatter: () => void
|
|
onExportMarkdownToPdf: () => void
|
|
onContentChange: (content: string) => void
|
|
onContentChangeForFile: (file: OpenFile, content: string) => void
|
|
onDirtyStateHint: (dirty: boolean) => void
|
|
onSave: (content: string) => Promise<boolean>
|
|
onSaveForFile: (file: OpenFile, content: string) => Promise<boolean>
|
|
onReloadContent: (file: OpenFile) => void
|
|
onCloseMarkdownTableOfContents: () => void
|
|
onCloseRenameDialog: () => void
|
|
onRenameConfirm: (newRelPath: string) => Promise<void>
|
|
markdownAnnotationsEnabled: boolean
|
|
}
|
|
|
|
export function EditorPanelShell({
|
|
panelRef,
|
|
activeFile,
|
|
activeViewStateId,
|
|
model,
|
|
copiedPathVisible,
|
|
showMarkdownTableOfContents,
|
|
canShowMarkdownFrontmatterToggle,
|
|
markdownFrontmatterVisible,
|
|
sideBySide,
|
|
openFiles,
|
|
fileContents,
|
|
diffContents,
|
|
editorDrafts,
|
|
pendingEditorReveal,
|
|
renameDialogFile,
|
|
renameError,
|
|
disableRenameBrowse,
|
|
onCopyPath,
|
|
onOpenDiffTargetFile,
|
|
onOpenPreviewToSide,
|
|
onOpenMarkdownPreview,
|
|
onOpenContainingFolder,
|
|
onToggleSideBySide,
|
|
onEditorToggleChange,
|
|
onToggleMarkdownTableOfContents,
|
|
onToggleMarkdownFrontmatter,
|
|
onExportMarkdownToPdf,
|
|
onContentChange,
|
|
onContentChangeForFile,
|
|
onDirtyStateHint,
|
|
onSave,
|
|
onSaveForFile,
|
|
onReloadContent,
|
|
onCloseMarkdownTableOfContents,
|
|
onCloseRenameDialog,
|
|
onRenameConfirm,
|
|
markdownAnnotationsEnabled
|
|
}: EditorPanelShellProps): JSX.Element {
|
|
return (
|
|
<div ref={panelRef} className="flex flex-col flex-1 min-w-0 min-h-0">
|
|
{!model.isCombinedDiff && activeFile.mode !== 'check-details' && (
|
|
<EditorPanelHeader
|
|
activeFile={activeFile}
|
|
copiedPathVisible={copiedPathVisible}
|
|
isSingleDiff={model.isSingleDiff}
|
|
isDiffSurface={model.isDiffSurface}
|
|
isMarkdown={model.isMarkdown}
|
|
isCsv={model.isCsv}
|
|
isNotebook={model.isNotebook}
|
|
hasEditorToggle={model.hasEditorToggle}
|
|
availableEditorToggleModes={model.availableEditorToggleModes}
|
|
effectiveToggleValue={model.effectiveToggleValue}
|
|
canOpenPreviewToSide={model.canOpenPreviewToSide}
|
|
canShowMarkdownPreview={model.canShowMarkdownPreview}
|
|
canShowMarkdownTableOfContents={model.canShowMarkdownTableOfContents}
|
|
isMarkdownTableOfContentsDisabled={model.isMarkdownTableOfContentsDisabled}
|
|
shouldShowMarkdownExportAction={model.shouldShowMarkdownExportAction}
|
|
canExportMarkdownToPdf={model.canExportMarkdownToPdf}
|
|
showMarkdownTableOfContents={showMarkdownTableOfContents}
|
|
canShowMarkdownFrontmatterToggle={canShowMarkdownFrontmatterToggle}
|
|
markdownFrontmatterVisible={markdownFrontmatterVisible}
|
|
sideBySide={sideBySide}
|
|
openFileState={model.openFileState}
|
|
onCopyPath={onCopyPath}
|
|
onOpenDiffTargetFile={onOpenDiffTargetFile}
|
|
onOpenPreviewToSide={onOpenPreviewToSide}
|
|
onOpenMarkdownPreview={onOpenMarkdownPreview}
|
|
onOpenContainingFolder={onOpenContainingFolder}
|
|
onToggleSideBySide={onToggleSideBySide}
|
|
onEditorToggleChange={onEditorToggleChange}
|
|
onToggleMarkdownTableOfContents={onToggleMarkdownTableOfContents}
|
|
onToggleMarkdownFrontmatter={onToggleMarkdownFrontmatter}
|
|
onExportMarkdownToPdf={onExportMarkdownToPdf}
|
|
/>
|
|
)}
|
|
<Suspense fallback={<EditorLoadingFallback />}>
|
|
<EditorContent
|
|
activeFile={activeFile}
|
|
viewStateScopeId={activeViewStateId ?? activeFile.id}
|
|
fileContents={fileContents}
|
|
diffContents={diffContents}
|
|
editBuffers={editorDrafts}
|
|
openFiles={openFiles}
|
|
worktreeEntries={model.worktreeEntries}
|
|
resolvedLanguage={model.resolvedLanguage}
|
|
isMarkdown={model.isMarkdown}
|
|
isMermaid={model.isMermaid}
|
|
isCsv={model.isCsv}
|
|
isNotebook={model.isNotebook}
|
|
mdViewMode={model.mdViewMode}
|
|
isChangesMode={model.isDiffSurface && !model.isSingleDiff}
|
|
sideBySide={sideBySide}
|
|
pendingEditorReveal={pendingEditorReveal}
|
|
handleContentChange={onContentChange}
|
|
handleContentChangeForFile={onContentChangeForFile}
|
|
handleDirtyStateHint={onDirtyStateHint}
|
|
handleSave={onSave}
|
|
handleSaveForFile={onSaveForFile}
|
|
reloadContent={onReloadContent}
|
|
showMarkdownTableOfContents={showMarkdownTableOfContents}
|
|
showMarkdownFrontmatter={markdownFrontmatterVisible}
|
|
onCloseMarkdownTableOfContents={onCloseMarkdownTableOfContents}
|
|
markdownAnnotationsEnabled={markdownAnnotationsEnabled}
|
|
/>
|
|
</Suspense>
|
|
<UntitledFileRenameDialog
|
|
open={renameDialogFile !== null}
|
|
currentName={renameDialogFile?.relativePath ?? ''}
|
|
worktreePath={
|
|
renameDialogFile
|
|
? getUntitledFileRoot(
|
|
renameDialogFile,
|
|
findWorktreeById(
|
|
useAppStore.getState().worktreesByRepo,
|
|
renameDialogFile.worktreeId
|
|
)?.path
|
|
)
|
|
: ''
|
|
}
|
|
disableBrowse={disableRenameBrowse}
|
|
externalError={renameError}
|
|
onClose={onCloseRenameDialog}
|
|
onConfirm={onRenameConfirm}
|
|
/>
|
|
</div>
|
|
)
|
|
}
|
|
|
|
function EditorLoadingFallback(): JSX.Element {
|
|
return (
|
|
<div className="flex items-center justify-center h-full text-muted-foreground text-sm">
|
|
{translate('auto.components.editor.EditorPanelShell.e2c4dec350', 'Loading editor...')}
|
|
</div>
|
|
)
|
|
}
|