UNPKG

1.92 kBPlain TextView Raw
1import * as React from "react";
2import { createComponent } from "reakit-system/createComponent";
3import { createHook } from "reakit-system/createHook";
4import { RadioOptions, RadioHTMLProps, useRadio } from "../Radio/Radio";
5import { MenuStateReturn } from "./MenuState";
6import { useMenuItem, MenuItemOptions, MenuItemHTMLProps } from "./MenuItem";
7import { MENU_ITEM_RADIO_KEYS } from "./__keys";
8
9export type MenuItemRadioOptions = RadioOptions &
10 MenuItemOptions &
11 Pick<MenuStateReturn, "unstable_values" | "unstable_setValue"> & {
12 /**
13 * MenuItemRadio's name as in `menu.values`.
14 */
15 name: string;
16 };
17
18export type MenuItemRadioHTMLProps = RadioHTMLProps & MenuItemHTMLProps;
19
20export type MenuItemRadioProps = MenuItemRadioOptions & MenuItemRadioHTMLProps;
21
22export const useMenuItemRadio = createHook<
23 MenuItemRadioOptions,
24 MenuItemRadioHTMLProps
25>({
26 name: "MenuItemRadio",
27 compose: [useMenuItem, useRadio],
28 keys: MENU_ITEM_RADIO_KEYS,
29
30 propsAreEqual(prev, next) {
31 if (prev.name !== next.name) {
32 return useMenuItem.unstable_propsAreEqual(prev, next);
33 }
34 const { unstable_values: prevValues, ...prevProps } = prev;
35 const { unstable_values: nextValues, ...nextProps } = next;
36 if (prevValues[next.name] !== nextValues[next.name]) {
37 return false;
38 }
39 return useMenuItem.unstable_propsAreEqual(prevProps, nextProps);
40 },
41
42 useOptions(options) {
43 const setState = React.useCallback(
44 (value) => options.unstable_setValue(options.name, value),
45 [options.unstable_setValue, options.name]
46 );
47 return {
48 ...options,
49 unstable_checkOnFocus: false,
50 state: options.unstable_values[options.name],
51 setState,
52 };
53 },
54
55 useProps(_, htmlProps) {
56 return { role: "menuitemradio", ...htmlProps };
57 },
58});
59
60export const MenuItemRadio = createComponent({
61 as: "button",
62 memo: true,
63 useHook: useMenuItemRadio,
64});