diff --git a/app/application/habits/[habitId]/progress/[selectedDate].tsx b/app/application/habits/[habitId]/progress/[selectedDate].tsx new file mode 100644 index 0000000..1a1a0cc --- /dev/null +++ b/app/application/habits/[habitId]/progress/[selectedDate].tsx @@ -0,0 +1,26 @@ +import { Redirect, useLocalSearchParams } from "expo-router" + +import { HabitProgress } from "@/presentation/react-native/components/HabitProgress" +import { useHabitsTracker } from "@/presentation/react/contexts/HabitsTracker" + +const HabitProgressPage: React.FC = () => { + const { habitId, selectedDate } = useLocalSearchParams() + const { habitsTracker } = useHabitsTracker() + + const habitHistory = habitsTracker.getHabitHistoryById(habitId as string) + const selectedDateParsed = new Date(selectedDate as string) + + if (habitHistory == null) { + return + } + + return ( + + ) +} + +export default HabitProgressPage diff --git a/domain/use-cases/HabitGoalProgressUpdate.ts b/domain/use-cases/HabitGoalProgressUpdate.ts index add7350..6b2b8e9 100644 --- a/domain/use-cases/HabitGoalProgressUpdate.ts +++ b/domain/use-cases/HabitGoalProgressUpdate.ts @@ -51,6 +51,16 @@ export class HabitGoalProgressUpdateUseCase }) } + if (goalProgress.isNumeric()) { + return await this.habitProgressCreateRepository.execute({ + habitProgressData: { + date, + goalProgress, + habitId: habitHistory.habit.id, + }, + }) + } + throw new Error("Not implemented") } } diff --git a/presentation/react-native/components/HabitForm/HabitCreateForm.tsx b/presentation/react-native/components/HabitForm/HabitCreateForm.tsx index 34bec8f..f1fe154 100644 --- a/presentation/react-native/components/HabitForm/HabitCreateForm.tsx +++ b/presentation/react-native/components/HabitForm/HabitCreateForm.tsx @@ -185,19 +185,6 @@ export const HabitCreateForm: React.FC = ({ user }) => { ]} > Habit Type - {/* - {}} - style={{ alignSelf: "center" }} - /> - */} = ({ + habitHistory, + selectedDate, +}) => { + const { habitsTrackerPresenter, habitGoalProgressUpdate } = useHabitsTracker() + + const [isVisibleSnackbar, setIsVisibleSnackbar] = useState(false) + + const onDismissSnackbar = (): void => { + setIsVisibleSnackbar(false) + } + + const goalProgress = habitHistory.getGoalProgressByDate(selectedDate) + + const values = { + progress: 0, + min: 0, + max: 0, + } + if (goalProgress.isNumeric()) { + values.max = goalProgress.goal.target.value + } + const [progressValue, setProgressValue] = useState(values.progress) + + if (!goalProgress.isNumeric()) { + return <> + } + + const progressTotal = goalProgress.progress + progressValue + + const handleSave = async (): Promise => { + setIsVisibleSnackbar(true) + await habitsTrackerPresenter.habitUpdateProgress({ + date: selectedDate, + habitHistory, + goalProgress: new GoalNumericProgress({ + goal: habitHistory.habit.goal as GoalNumeric, + progress: progressValue, + }), + }) + setProgressValue(0) + } + + return ( + + + + {habitHistory.habit.name} + + + + {capitalize(habitHistory.habit.goal.frequency)} Progress + + + + {selectedDate.toLocaleDateString(LOCALE, { + weekday: "long", + year: "numeric", + month: "long", + day: "numeric", + })} + + + + + + {goalProgress.progress.toLocaleString()} /{" "} + {goalProgress.goal.target.value.toLocaleString()}{" "} + {goalProgress.goal.target.unit} + + + { + const hasDigits = /\d+$/.test(text) + if (text.length <= 0 || !hasDigits) { + setProgressValue(0) + return + } + setProgressValue(Number.parseInt(text, 10)) + }} + style={[ + styles.spacing, + { + width: "80%", + }, + ]} + mode="outlined" + keyboardType="numeric" + /> + + {goalProgress.progress > 0 && progressValue > 0 ? ( + + {goalProgress.progress.toLocaleString()} +{" "} + {progressValue.toLocaleString()} = {progressTotal.toLocaleString()}{" "} + {goalProgress.goal.target.unit} + + ) : ( + <> + )} + + + + + + + + ✅ Habit Saved successfully! + + + ) +} + +const styles = StyleSheet.create({ + spacing: { + marginVertical: 16, + }, +}) diff --git a/presentation/react-native/components/HabitsMainPage/HabitCard.tsx b/presentation/react-native/components/HabitsMainPage/HabitCard.tsx index c7b40cd..26fa01b 100644 --- a/presentation/react-native/components/HabitsMainPage/HabitCard.tsx +++ b/presentation/react-native/components/HabitsMainPage/HabitCard.tsx @@ -1,16 +1,17 @@ import type { IconName } from "@fortawesome/free-solid-svg-icons" import { FontAwesomeIcon } from "@fortawesome/react-native-fontawesome" -import { useRouter } from "expo-router" +import { Link, useRouter } from "expo-router" import type LottieView from "lottie-react-native" import { useState } from "react" import { View } from "react-native" -import { Checkbox, List, Text } from "react-native-paper" +import { Button, Checkbox, List, Text } from "react-native-paper" import type { GoalBoolean } from "@/domain/entities/Goal" import { GoalBooleanProgress } from "@/domain/entities/Goal" import type { HabitHistory } from "@/domain/entities/HabitHistory" import { useHabitsTracker } from "@/presentation/react/contexts/HabitsTracker" import { getColorRGBAFromHex } from "@/utils/colors" +import { getISODate } from "@/utils/dates" export interface HabitCardProps { habitHistory: HabitHistory @@ -80,14 +81,32 @@ export const HabitCard: React.FC = (props) => { }} right={() => { if (goalProgress.isNumeric()) { + const href = { + pathname: "/application/habits/[habitId]/progress/[selectedDate]/", + params: { + habitId: habit.id, + selectedDate: getISODate(selectedDate), + }, + } return ( - - - {goalProgress.progress.toLocaleString()} /{" "} - {goalProgress.goal.target.value.toLocaleString()}{" "} - {goalProgress.goal.target.unit} - - + + + + {goalProgress.progress.toLocaleString()} /{" "} + {goalProgress.goal.target.value.toLocaleString()}{" "} + {goalProgress.goal.target.unit} + + + + + ) }