diff --git a/apps/web/lib/features/daily-plan/daily-plan-compare-estimate-modal.tsx b/apps/web/lib/features/daily-plan/daily-plan-compare-estimate-modal.tsx index 38786bd7a..11bafee72 100644 --- a/apps/web/lib/features/daily-plan/daily-plan-compare-estimate-modal.tsx +++ b/apps/web/lib/features/daily-plan/daily-plan-compare-estimate-modal.tsx @@ -11,6 +11,7 @@ import { TaskEstimateInput } from '../team/user-team-card/task-estimate'; import { useDailyPlan, useTeamMemberCard, useTimer, useTMCardTaskEdit } from '@app/hooks'; import { dailyPlanCompareEstimated } from '@app/helpers/daily-plan-estimated'; import { secondsToTime } from '@app/helpers'; +import { ScrollArea } from '@components/ui/scroll-bar'; import { DAILY_PLAN_ESTIMATE_HOURS_MODAL_DATE } from '@app/constants'; export interface IDailyPlanCompareEstimated { @@ -51,59 +52,60 @@ export function DailyPlanCompareEstimatedModal({ } }; - return ( - - - - - - - - setTimes(value)} - /> - - - - {todayPlan.map((plan, i) => { - return ( - - {plan.tasks?.map((data, index) => { - return ( - - - - ); - })} - - ); - })} - - - - {!difference && !estimated?.every(Boolean) && ( - <> - - Please correct planned work hours or re-estimate task(s) - > - )} - - 0 ? false : true)} - /> - - - - - ); + return ( + + + + + + + + setTimes(value)} + /> + + + + {todayPlan.map((plan, i) => { + return + {plan.tasks?.map((data, index) => { + return + + + })} + + })} + + + + {!difference && !estimated?.every(Boolean) && ( + <> + + Please correct planned work hours or re-estimate task(s) + > + ) + } + + 0 ? false : true)} + /> + + + + + ) } export function DailyPlanTask({ task, profile }: { task?: ITeamTask; profile: any }) { const taskEdition = useTMCardTaskEdit(task); diff --git a/apps/web/lib/features/user-profile-plans.tsx b/apps/web/lib/features/user-profile-plans.tsx index edb026b18..0c78c5b42 100644 --- a/apps/web/lib/features/user-profile-plans.tsx +++ b/apps/web/lib/features/user-profile-plans.tsx @@ -3,7 +3,7 @@ import { useEffect, useState } from 'react'; import { useRecoilState, useRecoilValue } from 'recoil'; import { useCanSeeActivityScreen, useDailyPlan, useUserProfilePage } from '@app/hooks'; import { TaskCard } from './task/task-card'; -import { IDailyPlan } from '@app/interfaces'; +import { IDailyPlan, ITeamTask } from '@app/interfaces'; import { AlertPopup, Container, HorizontalSeparator, NoData, ProgressBar, VerticalSeparator } from 'lib/components'; import { clsxm } from '@app/utils'; import { dataDailyPlanState } from '@app/stores'; @@ -45,9 +45,12 @@ export function UserProfilePlans() { const [currentTab, setCurrentTab] = useState(defaultTab || 'Today Tasks'); const [currentOutstanding, setCurrentOutstanding] = useState(defaultOutstanding || 'ALL'); - const [currentDataDailyPlan, setCurrentDataDailyPlan] = useRecoilState(dataDailyPlanState); + + const [currentDataDailyPlan, setCurrentDataDailyPlan] = useRecoilState(dataDailyPlanState) const { setDate, date } = useDateRange(currentTab); + + const screenOutstanding = { ALL: , DATE: @@ -63,21 +66,24 @@ export function UserProfilePlans() { const [filterPastPlanData, setFilteredPastPlanData] = useState(pastPlans); const [filterAllPlanData, setFilterAllPlanData] = useState(sortedPlans); + useEffect(() => { window.localStorage.setItem('daily-plan-tab', currentTab); if (!currentDataDailyPlan) return; if (currentTab === 'All Tasks') { - setCurrentDataDailyPlan(sortedPlans); - setFilterAllPlanData(filterDailyPlan(date as any, sortedPlans)); + setCurrentDataDailyPlan(sortedPlans) + setFilterAllPlanData(filterDailyPlan(date as any, sortedPlans)) } else if (currentTab === 'Past Tasks') { - setCurrentDataDailyPlan(pastPlans); - setFilteredPastPlanData(filterDailyPlan(date as any, pastPlans)); + setCurrentDataDailyPlan(pastPlans) + setFilteredPastPlanData(filterDailyPlan(date as any, pastPlans)) } else if (currentTab === 'Future Tasks') { - setCurrentDataDailyPlan(futurePlans); - setFilterFuturePlanData(filterDailyPlan(date as any, futurePlans)); + setCurrentDataDailyPlan(futurePlans) + setFilterFuturePlanData(filterDailyPlan(date as any, futurePlans)) } + }, [currentTab, setCurrentDataDailyPlan, setDate, date]); + useEffect(() => { window.localStorage.setItem('outstanding', currentOutstanding); }, [currentOutstanding]); @@ -99,8 +105,8 @@ export function UserProfilePlans() { currentTab == filter && 'text-blue-600 dark:text-white font-medium' )} onClick={() => { - setDate(undefined); - setCurrentTab(filter as FilterTabs); + setDate(undefined) + setCurrentTab(filter as FilterTabs) }} > {filter} @@ -115,6 +121,7 @@ export function UserProfilePlans() { {filter === 'Past Tasks' && filterPastPlanData?.length} {filter === 'All Tasks' && filterAllPlanData?.length} {filter === 'Outstanding' && outstandingPlans.length} + @@ -177,8 +184,8 @@ function AllPlans({ profile, currentTab = 'All Tasks' }: { profile: any; current const [plans, setPlans] = useState(filteredPlans); useEffect(() => { - setPlans(filterDailyPlan(date as any, filteredPlans)); - }, [date, setDate]); + setPlans(filterDailyPlan(date as any, filteredPlans)) + }, [date, setDate]) return ( {Array.isArray(plans) && plans?.length > 0 ? ( @@ -254,7 +261,7 @@ function AllPlans({ profile, currentTab = 'All Tasks' }: { profile: any; current : undefined } plan={plan} - className="shadow-[0px_0px_15px_0px_#e2e8f0]" + className='shadow-[0px_0px_15px_0px_#e2e8f0]' /> )} @@ -344,32 +351,26 @@ export function PlanHeader({ plan, planMode }: { plan: IDailyPlan; planMode: Fil const [editTime, setEditTime] = useState(false); const [time, setTime] = useState(0); const { updateDailyPlan, updateDailyPlanLoading } = useDailyPlan(); - // Get all tasks's estimations time - const times = - plan.tasks?.map((task) => task?.estimate).filter((time): time is number => typeof time === 'number') ?? []; - - let estimatedTime = 0; - if (times.length > 0) estimatedTime = times.reduce((acc, cur) => acc + cur, 0) ?? 0; + // Helper function to sum times + const sumTimes = (tasks: ITeamTask[], key: any) => tasks?.map((task: any) => + task[key]).filter((time): time is number => typeof time === 'number') + .reduce((acc, cur) => acc + cur, 0) ?? 0; - // Get all tasks's worked time - const workedTimes = - plan.tasks?.map((task) => task.totalWorkedTime).filter((time): time is number => typeof time === 'number') ?? - []; - let totalWorkTime = 0; - if (workedTimes.length > 0) totalWorkTime = workedTimes.reduce((acc, cur) => acc + cur, 0) ?? 0; + // Get all tasks' estimation and worked times + const estimatedTime = sumTimes(plan.tasks!, 'estimate'); + const totalWorkTime = sumTimes(plan.tasks!, 'totalWorkedTime'); - // Get completed tasks from a plan - const completedTasks = plan.tasks?.filter((task) => task.status === 'completed' && task.status).length ?? 0; + // Get completed and ready tasks from a plan + const completedTasks = plan.tasks?.filter(task => task.status === 'completed').length ?? 0; + const readyTasks = plan.tasks?.filter(task => task.status === 'ready').length ?? 0; - // Get ready tasks from a plan - const readyTasks = plan.tasks?.filter((task) => task.status === 'ready').length ?? 0; - - // Total tasks for plan + // Total tasks for the plan const totalTasks = plan.tasks?.length ?? 0; // Completion percent - const completionPercent = ((completedTasks * 100) / totalTasks).toFixed(2); + const completionPercent = totalTasks > 0 ? ((completedTasks * 100) / totalTasks).toFixed(0) : '0.0'; + return ( Completed tasks: - {completedTasks} + {`${completedTasks}/${totalTasks}`} Ready: @@ -486,8 +487,7 @@ export function EmptyPlans({ planMode }: { planMode?: FilterTabs }) { } - /> + component={} /> ); }