Skip to content

Commit

Permalink
docs: update upgrading guide (#2199)
Browse files Browse the repository at this point in the history
  • Loading branch information
gpbl authored Jun 8, 2024
1 parent ea4072b commit 41107e5
Show file tree
Hide file tree
Showing 3 changed files with 127 additions and 49 deletions.
41 changes: 18 additions & 23 deletions src/types-deprecated.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { Calendar } from "./components/Calendar";
import { MonthCaption } from "./components/MonthCaption";
import { MonthCaption, MonthCaptionProps } from "./components/MonthCaption";
import { Week, type WeekProps } from "./components/Week";
import { useCalendar } from "./contexts/calendar";
import { PropsContext, useProps } from "./contexts/props";
Expand Down Expand Up @@ -44,11 +44,10 @@ export const Root = Calendar;
export const Caption = MonthCaption;

/**
* @deprecated This type has been renamed. Use `Parameters<typeof
* MonthCaption>[0]` instead.
* @deprecated This type has been renamed. Use `MonthCaptionProps` instead.
* @protected
*/
export type CaptionProps = Parameters<typeof MonthCaption>[0];
export type CaptionProps = MonthCaptionProps;

/**
* @deprecated This component has been removed.
Expand Down Expand Up @@ -134,22 +133,21 @@ export type SelectRangeEventHandler = SelectHandler<"range", false>;
export type DayPickerProviderProps = any;

/**
* @deprecated This type has been renamed to `useProps`
* @deprecated This type has been renamed to `useProps`.
* @protected
* @group Hooks
*/
export const useDayPicker = useProps;

/**
* @deprecated This type has been renamed to `useProps`
* @deprecated This type has been renamed to `useProps`.
* @protected
* @group Hooks
*/
export const useNavigation = useCalendar;

/**
* @deprecated This hook has been removed. To customize the rendering of a day,
* use the `htmlAttributes` prop in a custom `Day` component.
* @deprecated This hook has been removed. Use a custom `Day` component instead.
* @protected
* @group Hooks
* @see https://react-day-picker.js.org/advanced-guides/custom-components
Expand Down Expand Up @@ -187,53 +185,50 @@ export type WeekdayLabel = typeof labelWeekday;
export type WeekNumberLabel = typeof labelWeekNumber;

/**
* @deprecated The event handler when a day is clicked. Use
* {@link DayMouseEventHandler} instead.
* @deprecated Use {@link DayMouseEventHandler} instead.
* @protected
*/
export type DayClickEventHandler = DayEventHandler<React.MouseEvent>;

/**
* @deprecated The event handler when a day is focused. This type will be
* removed. Use `DayEventHandler<React.FocusEvent | React.KeyboardEvent>`
* instead.
* @deprecated This type will be removed. Use `DayEventHandler<React.FocusEvent
* | React.KeyboardEvent>` instead.
* @protected
*/
export type DayFocusEventHandler = DayEventHandler<
React.FocusEvent | React.KeyboardEvent
>;

/**
* @deprecated The event handler when a day gets a keyboard event. This type
* will be removed. Use `DayEventHandler<React.KeyboardEvent>` instead.
* @deprecated This type will be removed. Use
* `DayEventHandler<React.KeyboardEvent>` instead.
* @protected
*/
export type DayKeyboardEventHandler = DayEventHandler<React.KeyboardEvent>;

/**
* @deprecated The event handler when a day gets a mouse event. This type will
* be removed. Use `DayEventHandler<React.MouseEvent>` instead.
* @deprecated This type will be removed. Use
* `DayEventHandler<React.MouseEvent>` instead.
* @protected
*/
export type DayMouseEventHandler = DayEventHandler<React.MouseEvent>;

/**
* @deprecated The event handler when a day gets a pointer event. This type will
* be removed. Use `DayEventHandler<React.PointerEvent>` instead.
* @deprecated This type will be removed. Use
* `DayEventHandler<React.PointerEvent>` instead.
* @protected
*/
export type DayPointerEventHandler = DayEventHandler<React.PointerEvent>;

/**
* @deprecated The event handler when a day gets a touch event. This type will
* be removed. Use `DayEventHandler<React.TouchEvent>` instead.
* @deprecated This type will be removed. Use
* `DayEventHandler<React.TouchEvent>` instead.
* @protected
*/
export type DayTouchEventHandler = DayEventHandler<React.TouchEvent>;

/**
* @deprecated The type has been renamed and needs a `Mode` argument. Use
* `PropsContext` instead.
* @deprecated The type has been renamed. Use `PropsContext` instead.
* @protected
*/
export type DayPickerContext = PropsContext;
42 changes: 35 additions & 7 deletions website/docs/advanced-guides/custom-components.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,24 @@ sidebar_position: 4

# Custom Components

Use the `components` prop to swap the components used to render DayPicker. A list of the components that can be customized is available in the [Components Reference](../api#components).
Use the `components` prop to swap the components used to render DayPicker.

:::tip Advanced Feature
:::warning Advanced Feature

- Custom components may not have a stable API yet and may break in a next release.
- Get familiar with the [API reference](../api#components) and the [DayPicker Anatomy](../using-daypicker/anatomy.mdx) first.
- This feature requires basic understanding of the output generated by DayPicker.
- Get familiar with the [API Reference](../api#components) and the [DayPicker Anatomy](../using-daypicker/anatomy.mdx) first.
- Make sure you don't break [accessibility](../using-daypicker/accessibility.mdx) when customizing components.
- Custom components may not have a stable API yet and may break in a minor release.

:::
:::

---
## List of Custom Components

See the [Components API Reference](../api#components) for a list of components you can customize.

For example, if you need to customize the component displaying the date, you can replace the `Day` component with a custom implementation.
## Example: Custom DayDate component

For example, if you need to customize the component displaying the date, replace the [`DayDate`](../api/functions//DayDate.md) component:

```tsx title="./CustomDayDate.tsx"
import { DayPicker, type DayDateProps } from "react-day-picker";
Expand All @@ -38,6 +44,28 @@ export function MyDatePicker() {
<Examples.CustomDayDate />
</BrowserWindow>

### Extending the Default Components

You can also import the default components to add custom behavior. Just make sure you pass the default component to the root.

For example, to add a custom class to the `Day` component:

```tsx title="./CustomDay.tsx"
import { DayPicker, Day, type DayProps } from "react-day-picker";

function CustomDay(props: DayProps) {
return (
<Day {...props}>
<div className="custom-day">{props.children}</div>
</Day>
);
}

export function MyDatePicker() {
return <DayPicker components={{ Day: CustomDay }} />;
}
```

## DayPicker Hooks

When creating custom components, you will find useful the [DayPicker hooks](../api/index.md#hooks). These utilities provide access to the internal state and methods of the DayPicker component.
Expand Down
93 changes: 74 additions & 19 deletions website/docs/upgrading.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -14,50 +14,74 @@ This document is still a work in progress. Please help us complete this guide by

:::

### Checklist

Follow these steps to upgrade your project from v8 to v9:

#### 1. Upgrade to the next version
### 1. Upgrade to the next version

```bash npm2yarn
npm install react-day-picker@next date-fns
```

#### 2. Update test selectors
### 2. Check for removed props

The following props have been removed. Check in your code if you are using them.

| Removed prop | Notes |
| ------------ | -------------------------------------------------------------------------------------------- |
| ~`fromDate`~ | Replace it with the `hidden` prop and the `before` [Matcher](./api/type-aliases/Matcher.md). |
| ~`toDate`~ | Replace it with the `hidden` prop and the `after` [Matcher](./api/type-aliases/Matcher.md). |

```diff
- <DayPicker fromDate={new Date(2010, 11, 03)} toDate={new Date(2012, 10, 01)} />
+ <DayPicker hidden={[{ before: new Date(2010, 11, 03)}, { after: new Date(2012, 10, 01) }]} />
```

### 3. Check for deprecated props

The following props have been deprecated, and will be removed in the next major version.

| Deprecated prop | Replacement | Notes |
| --------------- | ------------ | ----------------------------------------------------------------------- |
| ~`fromMonth`~ | `startMonth` | |
| ~`toMonth`~ | `endMonth` | |
| ~`fromYear`~ | `startMonth` | Pass the first month of the year, e.g. `startMonth = new Date(2024,0)`. |
| ~`toYear`~ | `endMonth` | Pass the last month of the year, e.g. `endMonth = new Date(2024,11)`. |

### 2. Updates for ARIA labels

The following ARIA labels have been updated:

- `Week nr.` to `Week`
- `Previous Month` and `NextMonth`
| Label | Old label | New label |
| ------------------------------------------------------- | ---------------------- | ---------------- |
| [`labelPrevious`](./api/functions/labelPrevious) | `Go to previous month` | `Previous Month` |
| [`labelNext`](./api/functions/labelNext) | `Go to next month` | `Next Month` |
| [`labelWeekNumber`](./api/functions/labelWeekNumber.md) | `Week nr.` | `Week` |

You may need to update your test selectors - for example:
You may need to update your test selectors for example:

```diff
```diff title="./test.js"
- screen.getByRole('button', 'Go to previous month');
+ screen.getByRole('button', 'Previous Month');
```

#### 3. Formatters return type
### 3. Formatters: update to return a string

The `formatters` prop now requires functions returning a `string` instead of a `ReactNode`.

The formatters now return a string instead of a ReactNode. If you were using the formatters in a React component, you may need to update your code:
If you were [using the formatters](./using-daypicker/localization.mdx#formatters), you may need to update your code or use a `DayDate` component to render a `ReactElement` again: see [custom components guide](./advanced-guides//custom-components.mdx).

```diff
- const MyComponent = () => <DayPicker formatters={{ caption: () => <strong>My caption</strong> }} />;
+ const MyComponent = () => <DayPicker formatters={{ caption: () => 'My caption' }} />;
```

### 4. Custom Components: update the hooks

#### 4. DayPicker

```diff
- import { DayPickerProps } from 'react-day-picker';
+ import { DayPickerProps, Mode } from 'react-day-picker';
- const props: DayPickerProps;
+ const props: DayPickerProps<Mode, boolan>;
```
- `useDayPicker` has ben deprecated and renamed to [`useProps`](./api/functions/useProps.md).
- `useNavigation` has been deprecated and renamed to [`useCalendar`](./api/functions/useCalendar.md).
- `useDayPicker` has been removed in favor of the `Day` custom component. See [custom components guide](./advanced-guides/custom-components.mdx) for more details.

#### 4. Rename deprecated typings
### 5. TypeScript: check for deprecated types

Many typings have been deprecated in favor of clarity and shorter names. If you were using the typings, you may need to update your code or it will break in the next major version.

Expand All @@ -66,6 +90,37 @@ Many typings have been deprecated in favor of clarity and shorter names. If you
+ import { PropsDefault } from 'react-day-picker/types';
```

See also the source of [types-deprecated.ts](https://github.com/gpbl/react-day-picker/blob/next/src/types-deprecated.ts).

| Deprecated Type | Deprecation Reason |
| ---------------------------- | --------------------------------------------------------------------------------------------------------------------------- |
| `Caption` | This component has been renamed. Use [`MonthCaption`](./api/functions/MonthCaption.md) instead. |
| `HeadRow` | This component has been removed. |
| `Row` | This component has been renamed. Use [`Week`](./api/functions/Week.md) instead. |
| `DayPickerSingleProps` | This type has been renamed. Use [`PropsSingle`](./api/interfaces/PropsSingle.md) instead. |
| `DayPickerMultipleProps` | This type has been renamed. Use [`PropsMulti`](./api/interfaces/PropsMulti.md) instead. |
| `DayPickerRangeProps` | This type has been renamed. Use [`PropsRange`](./api/interfaces/PropsRange.md) instead. |
| `DayPickerDefaultProps` | This type has been renamed. Use [`PropsDefault`](./api/interfaces/PropsDefault.md) instead. |
| `DaySelectionMode` | This type has been renamed. Use [`Mode`](./api/type-aliases/Mode.md) instead. |
| `Modifier` | This type will be removed. Use `string` instead. |
| `SelectSingleEventHandler` | This type will be removed. Use [`SelectHandler<"single">`](./api/type-aliases/SelectHandler.md) instead. |
| `SelectMultipleEventHandler` | This type will be removed. Use [`SelectHandler<"multiple">`](./api/type-aliases/SelectHandler.md) instead. |
| `SelectRangeEventHandler` | This type will be removed. Use [`SelectHandler<"range">`](./api/type-aliases/SelectHandler.md) instead. |
| `DayPickerProviderProps` | This type is not used anymore. |
| `useDayPicker` | This type has been renamed to [`useProps`](./api/functions/useProps.md). |
| `useNavigation` | This type has been renamed to [`useCalendar`](./api/functions/useCalendar.md). |
| `useDayRender` | This hook has been removed. To customize the rendering of a day, use the `htmlAttributes` prop in a custom `Day` component. |
| `ContextProvidersProps` | This type is not used anymore. |
| `DayLabel` | Use `typeof labelDay` instead. |
| `NavButtonLabel` | Use `typeof labelNext` or `typeof labelPrevious` instead. |
| `WeekdayLabel` | Use `typeof labelWeekday` instead. |
| `WeekNumberLabel` | Use `typeof labelWeekNumber` instead. |
| `DayClickEventHandler` | Use `DayMouseEventHandler` instead. |
| `DayFocusEventHandler` | This type will be removed. Use `DayEventHandlerReact.FocusEvent \| React.KeyboardEvent>` instead. |
| `DayKeyboardEventHandler` | This type will be removed. Use `DayEventHandler<React.KeyboardEvent>` instead. |
| `DayMouseEventHandler` | This type will be removed. Use `DayEventHandler<React.MouseEvent>` instead. |
| `DayPointerEventHandler` | This type will be removed. Use `DayEventHandler<React.PointerEvent>` instead. |
| `DayTouchEventHandler` | This type will be removed. Use `DayEventHandler<React.TouchEvent>` instead. |

---

Expand Down

0 comments on commit 41107e5

Please sign in to comment.