Files
cally/components/pages/calendar/DetailedCalendar.tsx
2024-12-24 13:03:42 +01:00

105 lines
3.6 KiB
TypeScript

import React, {useCallback, useEffect, useMemo, useRef} from "react";
import {useAuthContext} from "@/contexts/AuthContext";
import {useAtomValue} from "jotai";
import {modeAtom, selectedDateAtom, selectedUserAtom} from "@/components/pages/calendar/atoms";
import {useGetFamilyMembers} from "@/hooks/firebase/useGetFamilyMembers";
import {CalendarBody, CalendarContainer, CalendarHeader, CalendarKitHandle} from "@howljs/calendar-kit";
import {useGetEvents} from "@/hooks/firebase/useGetEvents";
import {useFormattedEvents} from "@/components/pages/calendar/useFormattedEvents";
import {useCalendarControls} from "@/components/pages/calendar/useCalendarControls";
import {EventCell} from "@/components/pages/calendar/EventCell";
import {isToday} from "date-fns";
import { View } from "react-native-ui-lib";
interface EventCalendarProps {
calendarHeight: number;
calendarWidth: number;
}
export const DetailedCalendar: React.FC<EventCalendarProps> = ({calendarHeight, calendarWidth}) => {
const {profileData} = useAuthContext();
const selectedDate = useAtomValue(selectedDateAtom);
const mode = useAtomValue(modeAtom);
const {data: familyMembers} = useGetFamilyMembers();
const calendarRef = useRef<CalendarKitHandle>(null);
const {data: events} = useGetEvents();
const selectedUser = useAtomValue(selectedUserAtom);
const {data: formattedEvents} = useFormattedEvents(events ?? [], selectedDate, selectedUser);
const {
handlePressEvent,
handlePressCell,
debouncedOnDateChanged
} = useCalendarControls(events ?? []);
const numberOfDays = useMemo(() => {
return mode === 'week' ? 7 : mode === '3days' ? 3 : 1;
}, [mode]);
const firstDay = useMemo(() => {
return profileData?.firstDayOfWeek === "Mondays" ? 1 : 0;
}, [profileData?.firstDayOfWeek]);
const headerProps = useMemo(() => ({
dayBarHeight: 60,
headerBottomHeight: 20
}), []);
const bodyProps = useMemo(() => ({
showNowIndicator: true,
hourFormat: "h:mm a"
}), []);
const containerProps = useMemo(() => ({
hourWidth: 70,
allowPinchToZoom: true,
useHaptic: true,
scrollToNow: true,
initialDate: selectedDate.toISOString(),
}), [selectedDate]);
const renderEvent = useCallback((event: any) => {
const attendees = useMemo(() =>
familyMembers?.filter(member => event?.attendees?.includes(member?.uid!)) || [],
[familyMembers, event.attendees]
);
return (
<EventCell
event={event}
onPress={handlePressEvent}
attendees={attendees}
/>
);
}, [familyMembers, handlePressEvent]);
useEffect(() => {
if (selectedDate && isToday(selectedDate)) {
calendarRef?.current?.goToDate({date: selectedDate});
}
}, [selectedDate]);
return (
<CalendarContainer
ref={calendarRef}
{...containerProps}
numberOfDays={numberOfDays}
calendarWidth={calendarWidth}
onDateChanged={debouncedOnDateChanged}
firstDay={firstDay}
events={formattedEvents ?? []}
onPressEvent={handlePressEvent}
onPressBackground={handlePressCell}
>
<CalendarHeader {...headerProps} />
<CalendarBody
{...bodyProps}
renderEvent={renderEvent}
/>
<View marginB-0/>
</CalendarContainer>
);
};
export default DetailedCalendar;