Skip to content

Commit b210f85

Browse files
authored
Clarify referential equality (#72)
* Clarify referential equality * fix ci
1 parent b66668c commit b210f85

File tree

3 files changed

+103
-0
lines changed

3 files changed

+103
-0
lines changed

.changeset/smart-pans-sleep.md

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
---
2+
---

apps/docs/docs/fundamentals/usage.mdx

+47
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ sidebar_position: 2
33
---
44

55
import Image from "@theme/IdealImage";
6+
import Admonition from "@theme/Admonition";
67
import { HStack } from "@site/src/components/HStack";
78
import basicCalendar from "./assets/basic-calendar.png";
89
import basicCalendarList from "./assets/basic-calendar-list.png";
@@ -225,6 +226,52 @@ export const CalendarCustomFormatting = () => {
225226

226227
</HStack>
227228

229+
#### Note on referential equality
230+
231+
Due to Flash Calendar's architecture, it's important to make your date
232+
formatting functions stable. You should move them outside the component
233+
scope (preferred) or memoize them with `useCallback`. Refer to [Issue
234+
69](https://github.com/MarceloPrado/flash-calendar/issues/69) for more.
235+
236+
<HStack spacing={12}>
237+
<Admonition type="tip" title="DO">
238+
Make the formatting functions stable.
239+
240+
```tsx
241+
const today = toDateId(new Date());
242+
243+
const Example = () => {
244+
return (
245+
<View style={{ flex: 1 }}>
246+
<Calendar
247+
calendarMonthId={today}
248+
getCalendarWeekDayFormat={formatWeekDay}
249+
/>
250+
</View>
251+
);
252+
};
253+
254+
const formatWeekDay = (date: Date) =>
255+
format(date, "EEEEEE");
256+
```
257+
258+
</Admonition>
259+
<Admonition type="danger" title="DON'T">
260+
Break referential equality by inlining the formatting functions.
261+
262+
```tsx
263+
<Calendar
264+
calendarMonthId={today}
265+
getCalendarWeekDayFormat={(date) =>
266+
// prettier-ignore
267+
format(date, "EEEEEE")
268+
}
269+
/>
270+
```
271+
272+
</Admonition>
273+
</HStack>
274+
228275
## Min, max and disabled dates
229276

230277
You can limit the range of selectable dates by using the `calendarMinDateId` and
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
import {
2+
Calendar,
3+
toDateId,
4+
useDateRange,
5+
} from "@marceloterreiro/flash-calendar";
6+
import type { Meta } from "@storybook/react";
7+
import { addDays, format } from "date-fns";
8+
import { useEffect, useState } from "react";
9+
import { View } from "react-native";
10+
11+
const CalendarMeta: Meta<typeof Calendar> = {
12+
title: "Calendar/Github Issues",
13+
decorators: [],
14+
};
15+
16+
export default CalendarMeta;
17+
18+
const today = toDateId(new Date());
19+
const todayPlusFive = toDateId(addDays(new Date(), 5));
20+
21+
// See more: https://github.com/MarceloPrado/flash-calendar/issues/69
22+
export const Issue69 = () => {
23+
// This state is simplified for the example. In my case it would come from a context.
24+
const [start, setStart] = useState<string | undefined>(today);
25+
const [end, setEnd] = useState<string | undefined>(todayPlusFive);
26+
27+
const { onCalendarDayPress, isDateRangeValid, calendarActiveDateRanges } =
28+
useDateRange({ startId: start, endId: end }); // I am setting the default range here because I want the data from my context to be pre-selected here
29+
30+
useEffect(() => {
31+
// Every time the selected range changed I want to update my context (in this example the state)
32+
if (isDateRangeValid && calendarActiveDateRanges.length > 0) {
33+
const range = calendarActiveDateRanges[0];
34+
setStart(range.startId);
35+
setEnd(range?.endId);
36+
}
37+
}, [calendarActiveDateRanges, isDateRangeValid]);
38+
39+
return (
40+
<View style={{ flex: 1 }}>
41+
<Calendar
42+
calendarActiveDateRanges={calendarActiveDateRanges}
43+
calendarColorScheme="light"
44+
calendarFirstDayOfWeek="monday"
45+
calendarMonthId={today}
46+
getCalendarWeekDayFormat={formatWeekDay}
47+
// getCalendarWeekDayFormat={(date) => format(date, "EEEEEE")}
48+
onCalendarDayPress={onCalendarDayPress}
49+
/>
50+
</View>
51+
);
52+
};
53+
54+
const formatWeekDay = (date: Date) => format(date, "EEEEEE");

0 commit comments

Comments
 (0)