feat: enhance GlobalTaskDetailDialog and TaskDetailDialog with loading state management
- Added a loading state to the TaskDetailDialog to display a loading indicator while fetching team data. - Updated GlobalTaskDetailDialog to pass the loading state to TaskDetailDialog. - Modified the selectTeam function in teamSlice to accept options for skipping project auto-selection, improving team data handling.
This commit is contained in:
parent
b2e48c6966
commit
ae2f7d9570
3 changed files with 27 additions and 4 deletions
|
|
@ -69,7 +69,8 @@ export const GlobalTaskDetailDialog = (): React.JSX.Element | null => {
|
|||
return (
|
||||
<TaskDetailDialog
|
||||
open
|
||||
task={selectedTeamLoading ? null : task}
|
||||
loading={selectedTeamLoading}
|
||||
task={task}
|
||||
teamName={teamName}
|
||||
kanbanTaskState={kanbanTaskState}
|
||||
taskMap={taskMap}
|
||||
|
|
|
|||
|
|
@ -61,6 +61,7 @@ import type { KanbanTaskState, ResolvedTeamMember, TeamTaskWithKanban } from '@s
|
|||
|
||||
interface TaskDetailDialogProps {
|
||||
open: boolean;
|
||||
loading?: boolean;
|
||||
task: TeamTaskWithKanban | null;
|
||||
teamName: string;
|
||||
kanbanTaskState?: KanbanTaskState;
|
||||
|
|
@ -77,6 +78,7 @@ interface TaskDetailDialogProps {
|
|||
|
||||
export const TaskDetailDialog = ({
|
||||
open,
|
||||
loading = false,
|
||||
task,
|
||||
teamName,
|
||||
kanbanTaskState,
|
||||
|
|
@ -225,6 +227,22 @@ export const TaskDetailDialog = ({
|
|||
onScrollToTask?.(taskId);
|
||||
};
|
||||
|
||||
if (loading) {
|
||||
return (
|
||||
<Dialog open={open} onOpenChange={(v) => !v && onClose()}>
|
||||
<DialogContent className="sm:max-w-4xl">
|
||||
<DialogHeader>
|
||||
<DialogTitle>Loading task…</DialogTitle>
|
||||
</DialogHeader>
|
||||
<div className="flex items-center gap-2 text-sm text-[var(--color-text-muted)]">
|
||||
<Loader2 className="size-4 animate-spin" />
|
||||
<span>Fetching team data</span>
|
||||
</div>
|
||||
</DialogContent>
|
||||
</Dialog>
|
||||
);
|
||||
}
|
||||
|
||||
if (!currentTask) {
|
||||
return (
|
||||
<Dialog open={open} onOpenChange={(v) => !v && handleClose()}>
|
||||
|
|
|
|||
|
|
@ -126,7 +126,7 @@ export interface TeamSlice {
|
|||
openTeamsTab: () => void;
|
||||
openTeamTab: (teamName: string, projectPath?: string, taskId?: string) => void;
|
||||
clearKanbanFilter: () => void;
|
||||
selectTeam: (teamName: string) => Promise<void>;
|
||||
selectTeam: (teamName: string, opts?: { skipProjectAutoSelect?: boolean }) => Promise<void>;
|
||||
refreshTeamData: (teamName: string) => Promise<void>;
|
||||
sendTeamMessage: (teamName: string, request: SendMessageRequest) => Promise<void>;
|
||||
requestReview: (teamName: string, taskId: string) => Promise<void>;
|
||||
|
|
@ -207,7 +207,7 @@ export const createTeamSlice: StateCreator<AppState, [], [], TeamSlice> = (set,
|
|||
// Ensure team data is loaded for the dialog
|
||||
const state = get();
|
||||
if (state.selectedTeamName !== teamName || !state.selectedTeamData) {
|
||||
void state.selectTeam(teamName);
|
||||
void state.selectTeam(teamName, { skipProjectAutoSelect: true });
|
||||
}
|
||||
},
|
||||
closeGlobalTaskDetail: () => set({ globalTaskDetail: null }),
|
||||
|
|
@ -358,7 +358,7 @@ export const createTeamSlice: StateCreator<AppState, [], [], TeamSlice> = (set,
|
|||
set({ kanbanFilterQuery: null });
|
||||
},
|
||||
|
||||
selectTeam: async (teamName: string) => {
|
||||
selectTeam: async (teamName: string, opts) => {
|
||||
// Clear stale data immediately to prevent flash of previous team's content
|
||||
const prev = get().selectedTeamName;
|
||||
set({
|
||||
|
|
@ -407,6 +407,10 @@ export const createTeamSlice: StateCreator<AppState, [], [], TeamSlice> = (set,
|
|||
get().updateTabLabel(teamTab.id, displayName);
|
||||
}
|
||||
|
||||
if (opts?.skipProjectAutoSelect) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Auto-select the project associated with this team's cwd/projectPath.
|
||||
// Must search both flat projects and grouped repositoryGroups/worktrees
|
||||
// because the default viewMode is 'grouped' and flat projects may be empty.
|
||||
|
|
|
|||
Loading…
Reference in a new issue