fix: hide empty input status row

Only show the pending changes accessory when workspace changes exist
Remove wasted vertical space above the composer when the status row is empty
This commit is contained in:
Bohdan Triapitsyn
2026-04-23 10:55:27 +03:00
parent cb6ba34811
commit 522cebf127
+16 -2
View File
@@ -65,11 +65,13 @@ import { useChatSearchDirectory } from '@/hooks/useChatSearchDirectory';
import { opencodeClient } from '@/lib/opencode/client'; import { opencodeClient } from '@/lib/opencode/client';
import { useProjectsStore } from '@/stores/useProjectsStore'; import { useProjectsStore } from '@/stores/useProjectsStore';
import { PROJECT_COLOR_MAP, PROJECT_ICON_MAP, getProjectIconImageUrl } from '@/lib/projectMeta'; import { PROJECT_COLOR_MAP, PROJECT_ICON_MAP, getProjectIconImageUrl } from '@/lib/projectMeta';
import { useGitBranches, useGitStore } from '@/stores/useGitStore'; import { useGitBranches, useGitStore, useIsGitRepo } from '@/stores/useGitStore';
import { useDirectoryStore } from '@/stores/useDirectoryStore';
import { useRuntimeAPIs } from '@/hooks/useRuntimeAPIs'; import { useRuntimeAPIs } from '@/hooks/useRuntimeAPIs';
import { createWorktreeDraft } from '@/lib/worktreeSessionCreator'; import { createWorktreeDraft } from '@/lib/worktreeSessionCreator';
import { buildSessionTargetOptions } from '@/sync/session-worktree-contract'; import { buildSessionTargetOptions } from '@/sync/session-worktree-contract';
import { usePermissionStore } from '@/stores/permissionStore'; import { usePermissionStore } from '@/stores/permissionStore';
import { extractGitChangedFiles } from './changedFiles';
const MAX_VISIBLE_TEXTAREA_LINES = 8; const MAX_VISIBLE_TEXTAREA_LINES = 8;
const EMPTY_QUEUE: QueuedMessage[] = []; const EMPTY_QUEUE: QueuedMessage[] = [];
@@ -750,6 +752,7 @@ const ChatInputComponent: React.FC<ChatInputProps> = ({ onOpenSettings, scrollTo
Promise.resolve((useSessionUIStore.getState().sendMessage as (...a: unknown[]) => unknown)(...args)), Promise.resolve((useSessionUIStore.getState().sendMessage as (...a: unknown[]) => unknown)(...args)),
).current; ).current;
const currentSessionId = useSessionUIStore((s) => s.currentSessionId); const currentSessionId = useSessionUIStore((s) => s.currentSessionId);
const currentDirectory = useDirectoryStore((s) => s.currentDirectory);
const newSessionDraft = useSessionUIStore((s) => s.newSessionDraft); const newSessionDraft = useSessionUIStore((s) => s.newSessionDraft);
const newSessionDraftOpen = Boolean(newSessionDraft?.open); const newSessionDraftOpen = Boolean(newSessionDraft?.open);
const setNewSessionDraftTarget = useSessionUIStore((s) => s.setNewSessionDraftTarget); const setNewSessionDraftTarget = useSessionUIStore((s) => s.setNewSessionDraftTarget);
@@ -792,6 +795,10 @@ const ChatInputComponent: React.FC<ChatInputProps> = ({ onOpenSettings, scrollTo
const { git: runtimeGit } = useRuntimeAPIs(); const { git: runtimeGit } = useRuntimeAPIs();
const { currentTheme } = useThemeSystem(); const { currentTheme } = useThemeSystem();
const chatSearchDirectory = useChatSearchDirectory(); const chatSearchDirectory = useChatSearchDirectory();
const isGitRepo = useIsGitRepo(currentDirectory);
const currentGitStatus = useGitStore((state) =>
currentDirectory ? state.directories.get(currentDirectory)?.status ?? null : null,
);
const [showAbortStatus, setShowAbortStatus] = React.useState(false); const [showAbortStatus, setShowAbortStatus] = React.useState(false);
const setSessionAutoAccept = usePermissionStore((state) => state.setSessionAutoAccept); const setSessionAutoAccept = usePermissionStore((state) => state.setSessionAutoAccept);
const composerHighlightRef = React.useRef<HTMLDivElement | null>(null); const composerHighlightRef = React.useRef<HTMLDivElement | null>(null);
@@ -3139,6 +3146,13 @@ const ChatInputComponent: React.FC<ChatInputProps> = ({ onOpenSettings, scrollTo
return draftBranchItems.find((item) => item.value === selectedValue)?.label ?? formatDirectoryName(selectedValue); return draftBranchItems.find((item) => item.value === selectedValue)?.label ?? formatDirectoryName(selectedValue);
}, [draftBranchItems, selectedDraftDirectory]); }, [draftBranchItems, selectedDraftDirectory]);
const hasPendingChanges = React.useMemo(() => {
if (isGitRepo !== true || !currentGitStatus || currentGitStatus.isClean) {
return false;
}
return extractGitChangedFiles(currentGitStatus.files, currentGitStatus.diffStats, currentDirectory).length > 0;
}, [currentDirectory, currentGitStatus, isGitRepo]);
const selectedDraftBranchIsKnown = React.useMemo(() => { const selectedDraftBranchIsKnown = React.useMemo(() => {
if (!selectedDraftDirectory) { if (!selectedDraftDirectory) {
return true; return true;
@@ -3448,7 +3462,7 @@ const ChatInputComponent: React.FC<ChatInputProps> = ({ onOpenSettings, scrollTo
showAbortStatus={showAbortStatus} showAbortStatus={showAbortStatus}
showAssistantStatus={false} showAssistantStatus={false}
showTodos showTodos
leftAccessory={newSessionDraftOpen ? null : <PendingChangesBar />} leftAccessory={newSessionDraftOpen || !hasPendingChanges ? null : <PendingChangesBar />}
/> />
{showDraftTargetSelectors && selectedDraftProject ? ( {showDraftTargetSelectors && selectedDraftProject ? (
<div className="mb-1.5 flex min-w-0 items-center gap-1.5 px-0.5"> <div className="mb-1.5 flex min-w-0 items-center gap-1.5 px-0.5">