perf(renderer): share sidebar task theme state
This commit is contained in:
parent
5f5b3dc62c
commit
da7d71c0b8
2 changed files with 37 additions and 3 deletions
|
|
@ -6,6 +6,7 @@ import { confirm } from '@renderer/components/common/ConfirmDialog';
|
||||||
import { Tooltip, TooltipContent, TooltipTrigger } from '@renderer/components/ui/tooltip';
|
import { Tooltip, TooltipContent, TooltipTrigger } from '@renderer/components/ui/tooltip';
|
||||||
import { useCollapsedGroups } from '@renderer/hooks/useCollapsedGroups';
|
import { useCollapsedGroups } from '@renderer/hooks/useCollapsedGroups';
|
||||||
import { useTaskLocalState } from '@renderer/hooks/useTaskLocalState';
|
import { useTaskLocalState } from '@renderer/hooks/useTaskLocalState';
|
||||||
|
import { useTheme } from '@renderer/hooks/useTheme';
|
||||||
import { cn } from '@renderer/lib/utils';
|
import { cn } from '@renderer/lib/utils';
|
||||||
import { markTaskUnread } from '@renderer/services/commentReadStorage';
|
import { markTaskUnread } from '@renderer/services/commentReadStorage';
|
||||||
import { useStore } from '@renderer/store';
|
import { useStore } from '@renderer/store';
|
||||||
|
|
@ -347,6 +348,7 @@ interface GlobalTaskRowProps {
|
||||||
hideTeamName?: boolean;
|
hideTeamName?: boolean;
|
||||||
hideProjectName?: boolean;
|
hideProjectName?: boolean;
|
||||||
showTeamName?: boolean;
|
showTeamName?: boolean;
|
||||||
|
isLight: boolean;
|
||||||
onTogglePin: TaskRowAction;
|
onTogglePin: TaskRowAction;
|
||||||
onToggleArchive: TaskRowAction;
|
onToggleArchive: TaskRowAction;
|
||||||
onMarkUnread: TaskRowAction;
|
onMarkUnread: TaskRowAction;
|
||||||
|
|
@ -409,6 +411,7 @@ const GlobalTaskRow = memo(
|
||||||
hideTeamName,
|
hideTeamName,
|
||||||
hideProjectName,
|
hideProjectName,
|
||||||
showTeamName,
|
showTeamName,
|
||||||
|
isLight,
|
||||||
onTogglePin,
|
onTogglePin,
|
||||||
onToggleArchive,
|
onToggleArchive,
|
||||||
onMarkUnread,
|
onMarkUnread,
|
||||||
|
|
@ -459,6 +462,7 @@ const GlobalTaskRow = memo(
|
||||||
hideTeamName={hideTeamName}
|
hideTeamName={hideTeamName}
|
||||||
hideProjectName={hideProjectName}
|
hideProjectName={hideProjectName}
|
||||||
showTeamName={showTeamName}
|
showTeamName={showTeamName}
|
||||||
|
isLight={isLight}
|
||||||
teamOffline={teamOffline}
|
teamOffline={teamOffline}
|
||||||
renamingKey={effectiveRenamingKey}
|
renamingKey={effectiveRenamingKey}
|
||||||
onRenameComplete={onRenameComplete}
|
onRenameComplete={onRenameComplete}
|
||||||
|
|
@ -481,6 +485,7 @@ const GlobalTaskRow = memo(
|
||||||
prev.hideTeamName === next.hideTeamName &&
|
prev.hideTeamName === next.hideTeamName &&
|
||||||
prev.hideProjectName === next.hideProjectName &&
|
prev.hideProjectName === next.hideProjectName &&
|
||||||
prev.showTeamName === next.showTeamName &&
|
prev.showTeamName === next.showTeamName &&
|
||||||
|
prev.isLight === next.isLight &&
|
||||||
prev.onTogglePin === next.onTogglePin &&
|
prev.onTogglePin === next.onTogglePin &&
|
||||||
prev.onToggleArchive === next.onToggleArchive &&
|
prev.onToggleArchive === next.onToggleArchive &&
|
||||||
prev.onMarkUnread === next.onMarkUnread &&
|
prev.onMarkUnread === next.onMarkUnread &&
|
||||||
|
|
@ -504,6 +509,7 @@ interface TaskRowsProps {
|
||||||
hideTeamName?: boolean;
|
hideTeamName?: boolean;
|
||||||
hideProjectName?: boolean;
|
hideProjectName?: boolean;
|
||||||
showTeamName?: boolean;
|
showTeamName?: boolean;
|
||||||
|
isLight: boolean;
|
||||||
showTeamHeader?: boolean;
|
showTeamHeader?: boolean;
|
||||||
pinnedOverride?: boolean;
|
pinnedOverride?: boolean;
|
||||||
archivedOverride?: boolean;
|
archivedOverride?: boolean;
|
||||||
|
|
@ -594,6 +600,7 @@ const TaskRows = memo(function TaskRows({
|
||||||
hideTeamName,
|
hideTeamName,
|
||||||
hideProjectName,
|
hideProjectName,
|
||||||
showTeamName,
|
showTeamName,
|
||||||
|
isLight,
|
||||||
showTeamHeader,
|
showTeamHeader,
|
||||||
pinnedOverride,
|
pinnedOverride,
|
||||||
archivedOverride,
|
archivedOverride,
|
||||||
|
|
@ -625,6 +632,7 @@ const TaskRows = memo(function TaskRows({
|
||||||
hideTeamName={hideTeamName}
|
hideTeamName={hideTeamName}
|
||||||
hideProjectName={hideProjectName}
|
hideProjectName={hideProjectName}
|
||||||
showTeamName={showTeamName}
|
showTeamName={showTeamName}
|
||||||
|
isLight={isLight}
|
||||||
teamOffline={isTeamOffline(task.teamName)}
|
teamOffline={isTeamOffline(task.teamName)}
|
||||||
ownerColorName={getOwnerColorName(task)}
|
ownerColorName={getOwnerColorName(task)}
|
||||||
renamingKey={renamingKey}
|
renamingKey={renamingKey}
|
||||||
|
|
@ -668,6 +676,7 @@ function areTaskRowsPropsEqual(prev: TaskRowsProps, next: TaskRowsProps): boolea
|
||||||
prev.hideTeamName === next.hideTeamName &&
|
prev.hideTeamName === next.hideTeamName &&
|
||||||
prev.hideProjectName === next.hideProjectName &&
|
prev.hideProjectName === next.hideProjectName &&
|
||||||
prev.showTeamName === next.showTeamName &&
|
prev.showTeamName === next.showTeamName &&
|
||||||
|
prev.isLight === next.isLight &&
|
||||||
prev.showTeamHeader === next.showTeamHeader &&
|
prev.showTeamHeader === next.showTeamHeader &&
|
||||||
prev.pinnedOverride === next.pinnedOverride &&
|
prev.pinnedOverride === next.pinnedOverride &&
|
||||||
prev.archivedOverride === next.archivedOverride &&
|
prev.archivedOverride === next.archivedOverride &&
|
||||||
|
|
@ -710,6 +719,7 @@ interface ProjectTaskGroupProps {
|
||||||
isNewTask: (task: GlobalTask) => boolean;
|
isNewTask: (task: GlobalTask) => boolean;
|
||||||
isTeamOffline: TeamBooleanResolver;
|
isTeamOffline: TeamBooleanResolver;
|
||||||
renamingKey: string | null;
|
renamingKey: string | null;
|
||||||
|
isLight: boolean;
|
||||||
formatTeamHeader: TeamHeaderFormatter;
|
formatTeamHeader: TeamHeaderFormatter;
|
||||||
onToggleGroup: (projectKey: string) => void;
|
onToggleGroup: (projectKey: string) => void;
|
||||||
onVisibleCountChange: ProjectGroupVisibleCountChange;
|
onVisibleCountChange: ProjectGroupVisibleCountChange;
|
||||||
|
|
@ -737,6 +747,7 @@ const ProjectTaskGroup = memo(
|
||||||
isNewTask,
|
isNewTask,
|
||||||
isTeamOffline,
|
isTeamOffline,
|
||||||
renamingKey,
|
renamingKey,
|
||||||
|
isLight,
|
||||||
formatTeamHeader,
|
formatTeamHeader,
|
||||||
onToggleGroup,
|
onToggleGroup,
|
||||||
onVisibleCountChange,
|
onVisibleCountChange,
|
||||||
|
|
@ -799,6 +810,7 @@ const ProjectTaskGroup = memo(
|
||||||
isArchived={isArchived}
|
isArchived={isArchived}
|
||||||
isNewTask={isNewTask}
|
isNewTask={isNewTask}
|
||||||
isTeamOffline={isTeamOffline}
|
isTeamOffline={isTeamOffline}
|
||||||
|
isLight={isLight}
|
||||||
hideTeamName
|
hideTeamName
|
||||||
hideProjectName
|
hideProjectName
|
||||||
showTeamHeader
|
showTeamHeader
|
||||||
|
|
@ -860,6 +872,7 @@ const ProjectTaskGroup = memo(
|
||||||
prev.showMoreLabel === next.showMoreLabel &&
|
prev.showMoreLabel === next.showMoreLabel &&
|
||||||
prev.showLessLabel === next.showLessLabel &&
|
prev.showLessLabel === next.showLessLabel &&
|
||||||
prev.renamingKey === next.renamingKey &&
|
prev.renamingKey === next.renamingKey &&
|
||||||
|
prev.isLight === next.isLight &&
|
||||||
prev.formatTeamHeader === next.formatTeamHeader &&
|
prev.formatTeamHeader === next.formatTeamHeader &&
|
||||||
prev.onToggleGroup === next.onToggleGroup &&
|
prev.onToggleGroup === next.onToggleGroup &&
|
||||||
prev.onVisibleCountChange === next.onVisibleCountChange &&
|
prev.onVisibleCountChange === next.onVisibleCountChange &&
|
||||||
|
|
@ -902,6 +915,7 @@ export const GlobalTaskList = memo(function GlobalTaskList({
|
||||||
onFiltersPopoverOpenChange: externalOnFiltersPopoverOpenChange,
|
onFiltersPopoverOpenChange: externalOnFiltersPopoverOpenChange,
|
||||||
}: GlobalTaskListProps = {}): React.JSX.Element {
|
}: GlobalTaskListProps = {}): React.JSX.Element {
|
||||||
const { t } = useAppTranslation('common');
|
const { t } = useAppTranslation('common');
|
||||||
|
const { isLight } = useTheme();
|
||||||
const {
|
const {
|
||||||
globalTasks,
|
globalTasks,
|
||||||
globalTasksLoading,
|
globalTasksLoading,
|
||||||
|
|
@ -1498,6 +1512,7 @@ export const GlobalTaskList = memo(function GlobalTaskList({
|
||||||
isArchived={taskLocalState.isArchived}
|
isArchived={taskLocalState.isArchived}
|
||||||
isNewTask={isNewTask}
|
isNewTask={isNewTask}
|
||||||
isTeamOffline={isTeamOffline}
|
isTeamOffline={isTeamOffline}
|
||||||
|
isLight={isLight}
|
||||||
pinnedOverride={true}
|
pinnedOverride={true}
|
||||||
archivedOverride={false}
|
archivedOverride={false}
|
||||||
showTeamName
|
showTeamName
|
||||||
|
|
@ -1601,6 +1616,7 @@ export const GlobalTaskList = memo(function GlobalTaskList({
|
||||||
isArchived={taskLocalState.isArchived}
|
isArchived={taskLocalState.isArchived}
|
||||||
isNewTask={isNewTask}
|
isNewTask={isNewTask}
|
||||||
isTeamOffline={isTeamOffline}
|
isTeamOffline={isTeamOffline}
|
||||||
|
isLight={isLight}
|
||||||
showTeamName
|
showTeamName
|
||||||
renamingKey={renamingTaskKey}
|
renamingKey={renamingTaskKey}
|
||||||
onTogglePin={handleToggleTaskPin}
|
onTogglePin={handleToggleTaskPin}
|
||||||
|
|
@ -1634,6 +1650,7 @@ export const GlobalTaskList = memo(function GlobalTaskList({
|
||||||
isArchived={taskLocalState.isArchived}
|
isArchived={taskLocalState.isArchived}
|
||||||
isNewTask={isNewTask}
|
isNewTask={isNewTask}
|
||||||
isTeamOffline={isTeamOffline}
|
isTeamOffline={isTeamOffline}
|
||||||
|
isLight={isLight}
|
||||||
renamingKey={renamingTaskKey}
|
renamingKey={renamingTaskKey}
|
||||||
formatTeamHeader={formatTeamHeader}
|
formatTeamHeader={formatTeamHeader}
|
||||||
onToggleGroup={handleToggleProjectGroup}
|
onToggleGroup={handleToggleProjectGroup}
|
||||||
|
|
@ -1682,6 +1699,7 @@ export const GlobalTaskList = memo(function GlobalTaskList({
|
||||||
isArchived={taskLocalState.isArchived}
|
isArchived={taskLocalState.isArchived}
|
||||||
isNewTask={isNewTask}
|
isNewTask={isNewTask}
|
||||||
isTeamOffline={isTeamOffline}
|
isTeamOffline={isTeamOffline}
|
||||||
|
isLight={isLight}
|
||||||
showTeamHeader
|
showTeamHeader
|
||||||
formatTeamHeader={formatTeamHeader}
|
formatTeamHeader={formatTeamHeader}
|
||||||
renamingKey={renamingTaskKey}
|
renamingKey={renamingTaskKey}
|
||||||
|
|
|
||||||
|
|
@ -69,6 +69,8 @@ interface SidebarTaskItemProps {
|
||||||
hideTeamName?: boolean;
|
hideTeamName?: boolean;
|
||||||
hideProjectName?: boolean;
|
hideProjectName?: boolean;
|
||||||
showTeamName?: boolean;
|
showTeamName?: boolean;
|
||||||
|
/** Optional theme value from list parents to avoid one theme subscription per row. */
|
||||||
|
isLight?: boolean;
|
||||||
/** Pauses the in-progress spinner when the parent team is offline. */
|
/** Pauses the in-progress spinner when the parent team is offline. */
|
||||||
teamOffline?: boolean;
|
teamOffline?: boolean;
|
||||||
/** The composite key "teamName:taskId" of the task being renamed, or null */
|
/** The composite key "teamName:taskId" of the task being renamed, or null */
|
||||||
|
|
@ -82,18 +84,19 @@ interface SidebarTaskItemProps {
|
||||||
ownerColorName?: string | null;
|
ownerColorName?: string | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const SidebarTaskItem = memo(function SidebarTaskItem({
|
const SidebarTaskItemContent = ({
|
||||||
task,
|
task,
|
||||||
hideTeamName,
|
hideTeamName,
|
||||||
hideProjectName,
|
hideProjectName,
|
||||||
showTeamName,
|
showTeamName,
|
||||||
|
isLight,
|
||||||
teamOffline = false,
|
teamOffline = false,
|
||||||
renamingKey,
|
renamingKey,
|
||||||
onRenameComplete,
|
onRenameComplete,
|
||||||
onRenameCancel,
|
onRenameCancel,
|
||||||
getDisplaySubject,
|
getDisplaySubject,
|
||||||
ownerColorName,
|
ownerColorName,
|
||||||
}: SidebarTaskItemProps): React.JSX.Element {
|
}: SidebarTaskItemProps & { isLight: boolean }): React.JSX.Element => {
|
||||||
const { t } = useAppTranslation('team');
|
const { t } = useAppTranslation('team');
|
||||||
const { t: tCommon } = useAppTranslation('common');
|
const { t: tCommon } = useAppTranslation('common');
|
||||||
const openGlobalTaskDetail = useStore((s) => s.openGlobalTaskDetail);
|
const openGlobalTaskDetail = useStore((s) => s.openGlobalTaskDetail);
|
||||||
|
|
@ -104,7 +107,6 @@ export const SidebarTaskItem = memo(function SidebarTaskItem({
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
const unreadCount = useUnreadCommentCount(task.teamName, task.id, task.comments);
|
const unreadCount = useUnreadCommentCount(task.teamName, task.id, task.comments);
|
||||||
const { isLight } = useTheme();
|
|
||||||
|
|
||||||
const isRenaming = renamingKey === `${task.teamName}:${task.id}`;
|
const isRenaming = renamingKey === `${task.teamName}:${task.id}`;
|
||||||
const displaySubject = getDisplaySubject?.(task) ?? task.subject;
|
const displaySubject = getDisplaySubject?.(task) ?? task.subject;
|
||||||
|
|
@ -317,4 +319,18 @@ export const SidebarTaskItem = memo(function SidebarTaskItem({
|
||||||
)}
|
)}
|
||||||
</button>
|
</button>
|
||||||
);
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const ThemedSidebarTaskItem = (props: SidebarTaskItemProps): React.JSX.Element => {
|
||||||
|
const { isLight } = useTheme();
|
||||||
|
return <SidebarTaskItemContent {...props} isLight={isLight} />;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const SidebarTaskItem = memo(function SidebarTaskItem(
|
||||||
|
props: SidebarTaskItemProps
|
||||||
|
): React.JSX.Element {
|
||||||
|
if (typeof props.isLight === 'boolean') {
|
||||||
|
return <SidebarTaskItemContent {...props} isLight={props.isLight} />;
|
||||||
|
}
|
||||||
|
return <ThemedSidebarTaskItem {...props} />;
|
||||||
});
|
});
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue