diff --git a/packages/components/src/menu/README.md b/packages/components/src/menu/README.md index a0fe52d060b2a1..b34e21696459d5 100644 --- a/packages/components/src/menu/README.md +++ b/packages/components/src/menu/README.md @@ -72,6 +72,9 @@ The placement of the menu popover. ### Menu.TriggerButton +Renders a menu button that toggles the visibility of a sibling +`Menu.Popover` component when clicked or when using arrow keys. + #### Props ##### `accessibleWhenDisabled` @@ -125,6 +128,14 @@ merged. ### Menu.Popover +Renders a dropdown menu element that's controlled by a sibling +`Menu.TriggerButton` component. It renders a popover and automatically +focuses on items when the menu is shown. + +The only valid children of `Menu.Popover` are `Menu.Item`, +`Menu.RadioItem`, `Menu.CheckboxItem`, `Menu.Group`, `Menu.Separator`, +and `Menu` (for nested dropdown menus). + #### Props ##### `children` @@ -185,6 +196,11 @@ negative values to make the popover shift to the opposite side. ### Menu.Item +Renders a menu item inside the `Menu.Popover` or `Menu.Group` components. + +It can optionally contain one instance of the `Menu.ItemLabel` component +and one instance of the `Menu.ItemHelpText` component. + #### Props ##### `children` @@ -244,6 +260,12 @@ The contents of the menu item's suffix, such as a keyboard shortcut. ### Menu.RadioItem +Renders a radio menu item inside the `Menu.Popover` or `Menu.Group` +components. + +It can optionally contain one instance of the `Menu.ItemLabel` component +and one instance of the `Menu.ItemHelpText` component. + #### Props ##### `children` @@ -336,6 +358,12 @@ The radio item's value. ### Menu.CheckboxItem +Renders a checkbox menu item inside the `Menu.Popover` or `Menu.Group` +components. + +It can optionally contain one instance of the `Menu.ItemLabel` component +and one instance of the `Menu.ItemHelpText` component. + #### Props ##### `children` @@ -429,6 +457,9 @@ associated to the same `name`. ### Menu.ItemLabel +Renders a menu item's label text. It should be wrapped with `Menu.Item`, +`Menu.RadioItem`, or `Menu.CheckboxItem`. + #### Props ##### `as` @@ -440,6 +471,9 @@ The HTML element or React component to render the component as. ### Menu.ItemHelpText +Renders a menu item's help text. It should be wrapped with `Menu.Item`, +`Menu.RadioItem`, or `Menu.CheckboxItem`. + #### Props ##### `as` @@ -451,6 +485,11 @@ The HTML element or React component to render the component as. ### Menu.Group +Renders a group for menu items. + +It should contain one instance of `Menu.GroupLabel` and one or more +instances of `Menu.Item`, `Menu.RadioItem`, or `Menu.CheckboxItem`. + #### Props ##### `children` @@ -464,6 +503,11 @@ The contents of the menu group, which should include one instance of the ### Menu.GroupLabel +Renders a label in a menu group. + +This component should be wrapped with `Menu.Group` so the +`aria-labelledby` is correctly set on the group element. + #### Props ##### `children` @@ -476,10 +520,17 @@ label for the menu group. ### Menu.Separator +Renders a divider between menu items or menu groups. + #### Props ### Menu.SubmenuTriggerItem +Renders a menu item that toggles the visibility of a sibling +`Menu.Popover` component when clicked or when using arrow keys. + +This component is used to create a nested dropdown menu. + #### Props ##### `children` diff --git a/packages/components/src/menu/checkbox-item.tsx b/packages/components/src/menu/checkbox-item.tsx index 69339387c3add5..a3ae4d77085986 100644 --- a/packages/components/src/menu/checkbox-item.tsx +++ b/packages/components/src/menu/checkbox-item.tsx @@ -13,18 +13,18 @@ import { Icon, check } from '@wordpress/icons'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; -import type { MenuCheckboxItemProps } from './types'; +import { Context } from './context'; +import type { CheckboxItemProps } from './types'; import * as Styled from './styles'; -export const MenuCheckboxItem = forwardRef< +export const CheckboxItem = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuCheckboxItemProps, 'div', false > ->( function MenuCheckboxItem( + WordPressComponentProps< CheckboxItemProps, 'div', false > +>( function CheckboxItem( { suffix, children, disabled = false, hideOnClick = false, ...props }, ref ) { - const menuContext = useContext( MenuContext ); + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -33,7 +33,7 @@ export const MenuCheckboxItem = forwardRef< } return ( - - - + + { children } - + { suffix && ( { suffix } ) } - - + + ); } ); diff --git a/packages/components/src/menu/context.tsx b/packages/components/src/menu/context.tsx index 1205015c57cbee..fa38f2c75aea61 100644 --- a/packages/components/src/menu/context.tsx +++ b/packages/components/src/menu/context.tsx @@ -6,8 +6,6 @@ import { createContext } from '@wordpress/element'; /** * Internal dependencies */ -import type { MenuContext as MenuContextType } from './types'; +import type { ContextProps } from './types'; -export const MenuContext = createContext< MenuContextType | undefined >( - undefined -); +export const Context = createContext< ContextProps | undefined >( undefined ); diff --git a/packages/components/src/menu/docs-manifest.json b/packages/components/src/menu/docs-manifest.json index 50e92189a39990..c47fd97e8e09f7 100644 --- a/packages/components/src/menu/docs-manifest.json +++ b/packages/components/src/menu/docs-manifest.json @@ -4,57 +4,57 @@ "filePath": "./index.tsx", "subcomponents": [ { - "displayName": "MenuTriggerButton", + "displayName": "TriggerButton", "preferredDisplayName": "Menu.TriggerButton", "filePath": "./trigger-button.tsx" }, { - "displayName": "MenuPopover", + "displayName": "Popover", "preferredDisplayName": "Menu.Popover", "filePath": "./popover.tsx" }, { - "displayName": "MenuItem", + "displayName": "Item", "preferredDisplayName": "Menu.Item", "filePath": "./item.tsx" }, { - "displayName": "MenuRadioItem", + "displayName": "RadioItem", "preferredDisplayName": "Menu.RadioItem", "filePath": "./radio-item.tsx" }, { - "displayName": "MenuCheckboxItem", + "displayName": "CheckboxItem", "preferredDisplayName": "Menu.CheckboxItem", "filePath": "./checkbox-item.tsx" }, { - "displayName": "MenuItemLabel", + "displayName": "ItemLabel", "preferredDisplayName": "Menu.ItemLabel", "filePath": "./item-label.tsx" }, { - "displayName": "MenuItemHelpText", + "displayName": "ItemHelpText", "preferredDisplayName": "Menu.ItemHelpText", "filePath": "./item-help-text.tsx" }, { - "displayName": "MenuGroup", + "displayName": "Group", "preferredDisplayName": "Menu.Group", "filePath": "./group.tsx" }, { - "displayName": "MenuGroupLabel", + "displayName": "GroupLabel", "preferredDisplayName": "Menu.GroupLabel", "filePath": "./group-label.tsx" }, { - "displayName": "MenuSeparator", + "displayName": "Separator", "preferredDisplayName": "Menu.Separator", "filePath": "./separator.tsx" }, { - "displayName": "MenuSubmenuTriggerItem", + "displayName": "SubmenuTriggerItem", "preferredDisplayName": "Menu.SubmenuTriggerItem", "filePath": "./submenu-trigger-item.tsx" } diff --git a/packages/components/src/menu/group-label.tsx b/packages/components/src/menu/group-label.tsx index 5bf081880cb1d7..ce6ecb06900d06 100644 --- a/packages/components/src/menu/group-label.tsx +++ b/packages/components/src/menu/group-label.tsx @@ -7,16 +7,16 @@ import { forwardRef, useContext } from '@wordpress/element'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; +import { Context } from './context'; import { Text } from '../text'; -import type { MenuGroupLabelProps } from './types'; +import type { GroupLabelProps } from './types'; import * as Styled from './styles'; -export const MenuGroupLabel = forwardRef< +export const GroupLabel = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuGroupLabelProps, 'div', false > ->( function MenuGroup( props, ref ) { - const menuContext = useContext( MenuContext ); + WordPressComponentProps< GroupLabelProps, 'div', false > +>( function Group( props, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -25,7 +25,7 @@ export const MenuGroupLabel = forwardRef< } return ( - ->( function MenuGroup( props, ref ) { - const menuContext = useContext( MenuContext ); + WordPressComponentProps< GroupProps, 'div', false > +>( function Group( props, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -24,10 +24,6 @@ export const MenuGroup = forwardRef< } return ( - + ); } ); diff --git a/packages/components/src/menu/index.tsx b/packages/components/src/menu/index.tsx index 4a99533c9d07c4..0af9468a198bc4 100644 --- a/packages/components/src/menu/index.tsx +++ b/packages/components/src/menu/index.tsx @@ -13,19 +13,19 @@ import { isRTL as isRTLFn } from '@wordpress/i18n'; * Internal dependencies */ import { useContextSystem, contextConnectWithoutRef } from '../context'; -import type { MenuContext as MenuContextType, MenuProps } from './types'; -import { MenuContext } from './context'; -import { MenuItem } from './item'; -import { MenuCheckboxItem } from './checkbox-item'; -import { MenuRadioItem } from './radio-item'; -import { MenuGroup } from './group'; -import { MenuGroupLabel } from './group-label'; -import { MenuSeparator } from './separator'; -import { MenuItemLabel } from './item-label'; -import { MenuItemHelpText } from './item-help-text'; -import { MenuTriggerButton } from './trigger-button'; -import { MenuSubmenuTriggerItem } from './submenu-trigger-item'; -import { MenuPopover } from './popover'; +import type { ContextProps, Props } from './types'; +import { Context } from './context'; +import { Item } from './item'; +import { CheckboxItem } from './checkbox-item'; +import { RadioItem } from './radio-item'; +import { Group } from './group'; +import { GroupLabel } from './group-label'; +import { Separator } from './separator'; +import { ItemLabel } from './item-label'; +import { ItemHelpText } from './item-help-text'; +import { TriggerButton } from './trigger-button'; +import { SubmenuTriggerItem } from './submenu-trigger-item'; +import { Popover } from './popover'; /** * Menu is a collection of React components that combine to render @@ -37,7 +37,7 @@ import { MenuPopover } from './popover'; * rendering the `Menu.TriggerButton` (or the `Menu.SubmenuTriggerItem`) * component, and the `Menu.Popover` component. */ -const UnconnectedMenu = ( props: MenuProps ) => { +const UnconnectedMenu = ( props: Props ) => { const { children, defaultOpen = false, @@ -49,10 +49,10 @@ const UnconnectedMenu = ( props: MenuProps ) => { variant, } = useContextSystem< // @ts-expect-error TODO: missing 'className' in MenuProps - typeof props & Pick< MenuContextType, 'variant' > + typeof props & Pick< ContextProps, 'variant' > >( props, 'Menu' ); - const parentContext = useContext( MenuContext ); + const parentContext = useContext( Context ); const rtl = isRTLFn(); @@ -94,9 +94,7 @@ const UnconnectedMenu = ( props: MenuProps ) => { ); return ( - - { children } - + { children } ); }; @@ -113,7 +111,7 @@ const UnconnectedMenu = ( props: MenuProps ) => { export const Menu = Object.assign( contextConnectWithoutRef( UnconnectedMenu, 'Menu' ), { - Context: Object.assign( MenuContext, { + Context: Object.assign( Context, { displayName: 'Menu.Context', } ), /** @@ -122,7 +120,7 @@ export const Menu = Object.assign( * It can optionally contain one instance of the `Menu.ItemLabel` component * and one instance of the `Menu.ItemHelpText` component. */ - Item: Object.assign( MenuItem, { + Item: Object.assign( Item, { displayName: 'Menu.Item', } ), /** @@ -132,7 +130,7 @@ export const Menu = Object.assign( * It can optionally contain one instance of the `Menu.ItemLabel` component * and one instance of the `Menu.ItemHelpText` component. */ - RadioItem: Object.assign( MenuRadioItem, { + RadioItem: Object.assign( RadioItem, { displayName: 'Menu.RadioItem', } ), /** @@ -142,7 +140,7 @@ export const Menu = Object.assign( * It can optionally contain one instance of the `Menu.ItemLabel` component * and one instance of the `Menu.ItemHelpText` component. */ - CheckboxItem: Object.assign( MenuCheckboxItem, { + CheckboxItem: Object.assign( CheckboxItem, { displayName: 'Menu.CheckboxItem', } ), /** @@ -151,7 +149,7 @@ export const Menu = Object.assign( * It should contain one instance of `Menu.GroupLabel` and one or more * instances of `Menu.Item`, `Menu.RadioItem`, or `Menu.CheckboxItem`. */ - Group: Object.assign( MenuGroup, { + Group: Object.assign( Group, { displayName: 'Menu.Group', } ), /** @@ -160,27 +158,27 @@ export const Menu = Object.assign( * This component should be wrapped with `Menu.Group` so the * `aria-labelledby` is correctly set on the group element. */ - GroupLabel: Object.assign( MenuGroupLabel, { + GroupLabel: Object.assign( GroupLabel, { displayName: 'Menu.GroupLabel', } ), /** * Renders a divider between menu items or menu groups. */ - Separator: Object.assign( MenuSeparator, { + Separator: Object.assign( Separator, { displayName: 'Menu.Separator', } ), /** * Renders a menu item's label text. It should be wrapped with `Menu.Item`, * `Menu.RadioItem`, or `Menu.CheckboxItem`. */ - ItemLabel: Object.assign( MenuItemLabel, { + ItemLabel: Object.assign( ItemLabel, { displayName: 'Menu.ItemLabel', } ), /** * Renders a menu item's help text. It should be wrapped with `Menu.Item`, * `Menu.RadioItem`, or `Menu.CheckboxItem`. */ - ItemHelpText: Object.assign( MenuItemHelpText, { + ItemHelpText: Object.assign( ItemHelpText, { displayName: 'Menu.ItemHelpText', } ), /** @@ -192,14 +190,14 @@ export const Menu = Object.assign( * `Menu.RadioItem`, `Menu.CheckboxItem`, `Menu.Group`, `Menu.Separator`, * and `Menu` (for nested dropdown menus). */ - Popover: Object.assign( MenuPopover, { + Popover: Object.assign( Popover, { displayName: 'Menu.Popover', } ), /** * Renders a menu button that toggles the visibility of a sibling * `Menu.Popover` component when clicked or when using arrow keys. */ - TriggerButton: Object.assign( MenuTriggerButton, { + TriggerButton: Object.assign( TriggerButton, { displayName: 'Menu.TriggerButton', } ), /** @@ -208,7 +206,7 @@ export const Menu = Object.assign( * * This component is used to create a nested dropdown menu. */ - SubmenuTriggerItem: Object.assign( MenuSubmenuTriggerItem, { + SubmenuTriggerItem: Object.assign( SubmenuTriggerItem, { displayName: 'Menu.SubmenuTriggerItem', } ), } diff --git a/packages/components/src/menu/item-help-text.tsx b/packages/components/src/menu/item-help-text.tsx index 13d14c294125bd..e47c54d702342f 100644 --- a/packages/components/src/menu/item-help-text.tsx +++ b/packages/components/src/menu/item-help-text.tsx @@ -7,14 +7,14 @@ import { forwardRef, useContext } from '@wordpress/element'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; +import { Context } from './context'; import * as Styled from './styles'; -export const MenuItemHelpText = forwardRef< +export const ItemHelpText = forwardRef< HTMLSpanElement, WordPressComponentProps< { children: React.ReactNode }, 'span', true > ->( function MenuItemHelpText( props, ref ) { - const menuContext = useContext( MenuContext ); +>( function ItemHelpText( props, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -22,7 +22,5 @@ export const MenuItemHelpText = forwardRef< ); } - return ( - - ); + return ; } ); diff --git a/packages/components/src/menu/item-label.tsx b/packages/components/src/menu/item-label.tsx index 4f5f80e547861f..3a3367f4b481fe 100644 --- a/packages/components/src/menu/item-label.tsx +++ b/packages/components/src/menu/item-label.tsx @@ -7,14 +7,14 @@ import { forwardRef, useContext } from '@wordpress/element'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; +import { Context } from './context'; import * as Styled from './styles'; -export const MenuItemLabel = forwardRef< +export const ItemLabel = forwardRef< HTMLSpanElement, WordPressComponentProps< { children: React.ReactNode }, 'span', true > ->( function MenuItemLabel( props, ref ) { - const menuContext = useContext( MenuContext ); +>( function ItemLabel( props, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -22,7 +22,5 @@ export const MenuItemLabel = forwardRef< ); } - return ( - - ); + return ; } ); diff --git a/packages/components/src/menu/item.tsx b/packages/components/src/menu/item.tsx index a716cbcc89654c..560d20c30436ce 100644 --- a/packages/components/src/menu/item.tsx +++ b/packages/components/src/menu/item.tsx @@ -7,14 +7,14 @@ import { forwardRef, useContext } from '@wordpress/element'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import type { MenuItemProps } from './types'; +import type { ItemProps } from './types'; import * as Styled from './styles'; -import { MenuContext } from './context'; +import { Context } from './context'; -export const MenuItem = forwardRef< +export const Item = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuItemProps, 'div', false > ->( function MenuItem( + WordPressComponentProps< ItemProps, 'div', false > +>( function Item( { prefix, suffix, @@ -26,7 +26,7 @@ export const MenuItem = forwardRef< }, ref ) { - const menuContext = useContext( MenuContext ); + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -41,7 +41,7 @@ export const MenuItem = forwardRef< const computedStore = store ?? menuContext.store; return ( - { prefix } - - + + { children } - + { suffix && ( { suffix } ) } - - + + ); } ); diff --git a/packages/components/src/menu/popover.tsx b/packages/components/src/menu/popover.tsx index 19972a31027ce1..6a3ad9eb683b51 100644 --- a/packages/components/src/menu/popover.tsx +++ b/packages/components/src/menu/popover.tsx @@ -17,18 +17,18 @@ import { * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import type { MenuPopoverProps } from './types'; +import type { PopoverProps } from './types'; import * as Styled from './styles'; -import { MenuContext } from './context'; +import { Context } from './context'; -export const MenuPopover = forwardRef< +export const Popover = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuPopoverProps, 'div', false > ->( function MenuPopover( + WordPressComponentProps< PopoverProps, 'div', false > +>( function Popover( { gutter, children, shift, modal = true, ...otherProps }, ref ) { - const menuContext = useContext( MenuContext ); + const menuContext = useContext( Context ); // Extract the side from the applied placement — useful for animations. // Using `currentPlacement` instead of `placement` to make sure that we @@ -92,9 +92,9 @@ export const MenuPopover = forwardRef< // container scales with a different factor than its contents. // The {...renderProps} are passed to the inner wrapper, so that the // menu element is the direct parent of the menu item elements. - - - + + + ) } > { children } diff --git a/packages/components/src/menu/radio-item.tsx b/packages/components/src/menu/radio-item.tsx index 28b3199d7d36b8..1da6d573c26852 100644 --- a/packages/components/src/menu/radio-item.tsx +++ b/packages/components/src/menu/radio-item.tsx @@ -13,8 +13,8 @@ import { Icon } from '@wordpress/icons'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; -import type { MenuRadioItemProps } from './types'; +import { Context } from './context'; +import type { RadioItemProps } from './types'; import * as Styled from './styles'; import { SVG, Circle } from '@wordpress/primitives'; @@ -24,14 +24,14 @@ const radioCheck = ( ); -export const MenuRadioItem = forwardRef< +export const RadioItem = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuRadioItemProps, 'div', false > ->( function MenuRadioItem( + WordPressComponentProps< RadioItemProps, 'div', false > +>( function RadioItem( { suffix, children, disabled = false, hideOnClick = false, ...props }, ref ) { - const menuContext = useContext( MenuContext ); + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -40,7 +40,7 @@ export const MenuRadioItem = forwardRef< } return ( - - - + + { children } - + { suffix && ( { suffix } ) } - - + + ); } ); diff --git a/packages/components/src/menu/separator.tsx b/packages/components/src/menu/separator.tsx index 57cff572c287a0..bdf79c8bb472a2 100644 --- a/packages/components/src/menu/separator.tsx +++ b/packages/components/src/menu/separator.tsx @@ -7,15 +7,15 @@ import { forwardRef, useContext } from '@wordpress/element'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import { MenuContext } from './context'; -import type { MenuSeparatorProps } from './types'; +import { Context } from './context'; +import type { SeparatorProps } from './types'; import * as Styled from './styles'; -export const MenuSeparator = forwardRef< +export const Separator = forwardRef< HTMLHRElement, - WordPressComponentProps< MenuSeparatorProps, 'hr', false > ->( function MenuSeparator( props, ref ) { - const menuContext = useContext( MenuContext ); + WordPressComponentProps< SeparatorProps, 'hr', false > +>( function Separator( props, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( @@ -24,7 +24,7 @@ export const MenuSeparator = forwardRef< } return ( - = { id: 'components-menu', @@ -67,7 +67,7 @@ const meta: Meta< typeof Menu > = { }; export default meta; -export const Default: StoryFn< typeof Menu > = ( props: MenuProps ) => ( +export const Default: StoryFn< typeof Menu > = ( props: Props ) => ( } @@ -119,7 +119,7 @@ export const Default: StoryFn< typeof Menu > = ( props: MenuProps ) => ( ); Default.args = {}; -export const WithSubmenu: StoryFn< typeof Menu > = ( props: MenuProps ) => ( +export const WithSubmenu: StoryFn< typeof Menu > = ( props: Props ) => ( } @@ -163,7 +163,7 @@ WithSubmenu.args = { ...Default.args, }; -export const WithCheckboxes: StoryFn< typeof Menu > = ( props: MenuProps ) => { +export const WithCheckboxes: StoryFn< typeof Menu > = ( props: Props ) => { const [ isAChecked, setAChecked ] = useState( false ); const [ isBChecked, setBChecked ] = useState( true ); const [ multipleCheckboxesValue, setMultipleCheckboxesValue ] = useState< @@ -297,7 +297,7 @@ WithCheckboxes.args = { ...Default.args, }; -export const WithRadios: StoryFn< typeof Menu > = ( props: MenuProps ) => { +export const WithRadios: StoryFn< typeof Menu > = ( props: Props ) => { const [ radioValue, setRadioValue ] = useState( 'two' ); const onRadioChange: React.ComponentProps< typeof Menu.RadioItem @@ -367,7 +367,7 @@ const modalOnTopOfMenuPopover = css` `; // For more examples with `Modal`, check https://ariakit.org/examples/menu-wordpress-modal -export const WithModals: StoryFn< typeof Menu > = ( props: MenuProps ) => { +export const WithModals: StoryFn< typeof Menu > = ( props: Props ) => { const [ isOuterModalOpen, setOuterModalOpen ] = useState( false ); const [ isInnerModalOpen, setInnerModalOpen ] = useState( false ); @@ -478,7 +478,7 @@ const Fill = ( { children }: { children: React.ReactNode } ) => { ); }; -export const WithSlotFill: StoryFn< typeof Menu > = ( props: MenuProps ) => { +export const WithSlotFill: StoryFn< typeof Menu > = ( props: Props ) => { return ( @@ -526,7 +526,7 @@ const toolbarVariantContextValue = { variant: 'toolbar', }, }; -export const ToolbarVariant: StoryFn< typeof Menu > = ( props: MenuProps ) => ( +export const ToolbarVariant: StoryFn< typeof Menu > = ( props: Props ) => ( // TODO: add toolbar @@ -561,7 +561,7 @@ ToolbarVariant.args = { ...Default.args, }; -export const InsideModal: StoryFn< typeof Menu > = ( props: MenuProps ) => { +export const InsideModal: StoryFn< typeof Menu > = ( props: Props ) => { const [ isModalOpen, setModalOpen ] = useState( false ); return ( <> diff --git a/packages/components/src/menu/styles.ts b/packages/components/src/menu/styles.ts index cda5c7321f38b4..1235d6ae7ec1b4 100644 --- a/packages/components/src/menu/styles.ts +++ b/packages/components/src/menu/styles.ts @@ -12,7 +12,7 @@ import { COLORS, font, rtl, CONFIG } from '../utils'; import { space } from '../utils/space'; import Icon from '../icon'; import { Truncate } from '../truncate'; -import type { MenuContext } from './types'; +import type { ContextProps } from './types'; const ANIMATION_PARAMS = { SCALE_AMOUNT_OUTER: 0.82, @@ -42,8 +42,8 @@ const TOOLBAR_VARIANT_BOX_SHADOW = `0 0 0 ${ CONFIG.borderWidth } ${ TOOLBAR_VAR const GRID_TEMPLATE_COLS = 'minmax( 0, max-content ) 1fr'; -export const MenuPopoverOuterWrapper = styled.div< - Pick< MenuContext, 'variant' > +export const PopoverOuterWrapper = styled.div< + Pick< ContextProps, 'variant' > >` position: relative; @@ -95,7 +95,7 @@ export const MenuPopoverOuterWrapper = styled.div< } `; -export const MenuPopoverInnerWrapper = styled.div` +export const PopoverInnerWrapper = styled.div` position: relative; /* Same as popover component */ /* TODO: is there a way to read the sass variable? */ @@ -219,7 +219,7 @@ const baseItem = css` } /* When the item is the trigger of an open submenu */ - ${ MenuPopoverInnerWrapper }:not(:focus) &:not(:focus)[aria-expanded="true"] { + ${ PopoverInnerWrapper }:not(:focus) &:not(:focus)[aria-expanded="true"] { background-color: ${ LIGHT_BACKGROUND_COLOR }; color: ${ COLORS.theme.foreground }; } @@ -229,15 +229,15 @@ const baseItem = css` } `; -export const MenuItem = styled( Ariakit.MenuItem )` +export const Item = styled( Ariakit.MenuItem )` ${ baseItem }; `; -export const MenuCheckboxItem = styled( Ariakit.MenuItemCheckbox )` +export const CheckboxItem = styled( Ariakit.MenuItemCheckbox )` ${ baseItem }; `; -export const MenuRadioItem = styled( Ariakit.MenuItemRadio )` +export const RadioItem = styled( Ariakit.MenuItemRadio )` ${ baseItem }; `; @@ -249,14 +249,14 @@ export const ItemPrefixWrapper = styled.span` * Even when the item is not checked, occupy the same screen space to avoid * the space collapside when no items are checked. */ - ${ MenuCheckboxItem } > &, - ${ MenuRadioItem } > & { + ${ CheckboxItem } > &, + ${ RadioItem } > & { /* Same width as the check icons */ min-width: ${ space( 6 ) }; } - ${ MenuCheckboxItem } > &, - ${ MenuRadioItem } > &, + ${ CheckboxItem } > &, + ${ RadioItem } > &, &:not( :empty ) { margin-inline-end: ${ space( 2 ) }; } @@ -278,7 +278,7 @@ export const ItemPrefixWrapper = styled.span` } `; -export const MenuItemContentWrapper = styled.div` +export const ItemContentWrapper = styled.div` /* * Always occupy the second column, since the first column * is taken by the prefix wrapper (when displayed). @@ -293,7 +293,7 @@ export const MenuItemContentWrapper = styled.div` pointer-events: none; `; -export const MenuItemChildrenWrapper = styled.div` +export const ItemChildrenWrapper = styled.div` flex: 1; display: inline-flex; @@ -317,19 +317,19 @@ export const ItemSuffixWrapper = styled.span` * When the parent menu item is active, except when it's a non-focused/hovered * submenu trigger (in that case, color should not be inherited) */ - [data-active-item]:not( [data-focus-visible] ) *:not(${ MenuPopoverInnerWrapper }) &, + [data-active-item]:not( [data-focus-visible] ) *:not(${ PopoverInnerWrapper }) &, /* When the parent menu item is disabled */ - [aria-disabled='true'] *:not(${ MenuPopoverInnerWrapper }) & { + [aria-disabled='true'] *:not(${ PopoverInnerWrapper }) & { color: inherit; } `; -export const MenuGroup = styled( Ariakit.MenuGroup )` +export const Group = styled( Ariakit.MenuGroup )` /* Ignore this element when calculating the layout. Useful for subgrid */ display: contents; `; -export const MenuGroupLabel = styled( Ariakit.MenuGroupLabel )` +export const GroupLabel = styled( Ariakit.MenuGroupLabel )` /* Occupy the width of all grid columns (ie. full width) */ grid-column: 1 / -1; @@ -338,8 +338,8 @@ export const MenuGroupLabel = styled( Ariakit.MenuGroupLabel )` padding-inline: ${ ITEM_PADDING_INLINE }; `; -export const MenuSeparator = styled( Ariakit.MenuSeparator )< - Pick< MenuContext, 'variant' > +export const Separator = styled( Ariakit.MenuSeparator )< + Pick< ContextProps, 'variant' > >` /* Occupy the width of all grid columns (ie. full width) */ grid-column: 1 / -1; @@ -370,22 +370,22 @@ export const SubmenuChevronIcon = styled( Icon )` ) }; `; -export const MenuItemLabel = styled( Truncate )` +export const ItemLabel = styled( Truncate )` font-size: ${ font( 'default.fontSize' ) }; line-height: 20px; color: inherit; `; -export const MenuItemHelpText = styled( Truncate )` +export const ItemHelpText = styled( Truncate )` font-size: ${ font( 'helpText.fontSize' ) }; line-height: 16px; color: ${ LIGHTER_TEXT_COLOR }; overflow-wrap: anywhere; [data-active-item]:not( [data-focus-visible] ) - *:not( ${ MenuPopoverInnerWrapper } ) + *:not( ${ PopoverInnerWrapper } ) &, - [aria-disabled='true'] *:not( ${ MenuPopoverInnerWrapper } ) & { + [aria-disabled='true'] *:not( ${ PopoverInnerWrapper } ) & { color: inherit; } `; diff --git a/packages/components/src/menu/submenu-trigger-item.tsx b/packages/components/src/menu/submenu-trigger-item.tsx index 23932a14bdaff4..9ea24d259af300 100644 --- a/packages/components/src/menu/submenu-trigger-item.tsx +++ b/packages/components/src/menu/submenu-trigger-item.tsx @@ -13,16 +13,16 @@ import { chevronRightSmall } from '@wordpress/icons'; * Internal dependencies */ import type { WordPressComponentProps } from '../context'; -import type { MenuItemProps } from './types'; -import { MenuContext } from './context'; -import { MenuItem } from './item'; +import type { ItemProps } from './types'; +import { Context } from './context'; +import { Item } from './item'; import * as Styled from './styles'; -export const MenuSubmenuTriggerItem = forwardRef< +export const SubmenuTriggerItem = forwardRef< HTMLDivElement, - WordPressComponentProps< MenuItemProps, 'div', false > ->( function MenuSubmenuTriggerItem( { suffix, ...otherProps }, ref ) { - const menuContext = useContext( MenuContext ); + WordPressComponentProps< ItemProps, 'div', false > +>( function SubmenuTriggerItem( { suffix, ...otherProps }, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store.parent ) { throw new Error( @@ -36,10 +36,10 @@ export const MenuSubmenuTriggerItem = forwardRef< accessibleWhenDisabled store={ menuContext.store } render={ - ->( function MenuTriggerButton( { children, disabled = false, ...props }, ref ) { - const menuContext = useContext( MenuContext ); + WordPressComponentProps< TriggerButtonProps, 'button', false > +>( function TriggerButton( { children, disabled = false, ...props }, ref ) { + const menuContext = useContext( Context ); if ( ! menuContext?.store ) { throw new Error( diff --git a/packages/components/src/menu/types.ts b/packages/components/src/menu/types.ts index f9bb0782529d1f..4532d97fb13dd9 100644 --- a/packages/components/src/menu/types.ts +++ b/packages/components/src/menu/types.ts @@ -3,7 +3,7 @@ */ import type * as Ariakit from '@ariakit/react'; -export interface MenuContext { +export interface ContextProps { /** * The ariakit store shared across all Menu subcomponents. */ @@ -14,7 +14,7 @@ export interface MenuContext { variant?: 'toolbar'; } -export interface MenuProps { +export interface Props { /** * The elements, which should include one instance of the `Menu.TriggerButton` * component and one instance of the `Menu.Popover` component. @@ -50,7 +50,7 @@ export interface MenuProps { placement?: Ariakit.MenuProviderProps[ 'placement' ]; } -export interface MenuPopoverProps { +export interface PopoverProps { /** * The contents of the menu popover, which should include instances of the * `Menu.Item`, `Menu.CheckboxItem`, `Menu.RadioItem`, `Menu.Group`, and @@ -98,7 +98,7 @@ export interface MenuPopoverProps { hideOnEscape?: Ariakit.MenuProps[ 'hideOnEscape' ]; } -export interface MenuTriggerButtonProps { +export interface TriggerButtonProps { /** * The contents of the menu trigger button. */ @@ -139,7 +139,7 @@ export interface MenuTriggerButtonProps { accessibleWhenDisabled?: Ariakit.MenuButtonProps[ 'accessibleWhenDisabled' ]; } -export interface MenuGroupProps { +export interface GroupProps { /** * The contents of the menu group, which should include one instance of the * `Menu.GroupLabel` component and one or more instances of `Menu.Item`, @@ -148,7 +148,7 @@ export interface MenuGroupProps { children: Ariakit.MenuGroupProps[ 'children' ]; } -export interface MenuGroupLabelProps { +export interface GroupLabelProps { /** * The contents of the menu group label, which should provide an accessible * label for the menu group. @@ -156,7 +156,7 @@ export interface MenuGroupLabelProps { children: Ariakit.MenuGroupLabelProps[ 'children' ]; } -export interface MenuItemProps { +export interface ItemProps { /** * The contents of the menu item, which could include one instance of the * `Menu.ItemLabel` component and/or one instance of the `Menu.ItemHelpText` @@ -203,7 +203,7 @@ export interface MenuItemProps { store?: Ariakit.MenuItemProps[ 'store' ]; } -export interface MenuCheckboxItemProps { +export interface CheckboxItemProps { /** * The contents of the menu item, which could include one instance of the * `Menu.ItemLabel` component and/or one instance of the `Menu.ItemHelpText` @@ -267,7 +267,7 @@ export interface MenuCheckboxItemProps { onChange?: Ariakit.MenuItemCheckboxProps[ 'onChange' ]; } -export interface MenuRadioItemProps { +export interface RadioItemProps { /** * The contents of the menu item, which could include one instance of the * `Menu.ItemLabel` component and/or one instance of the `Menu.ItemHelpText` @@ -330,4 +330,4 @@ export interface MenuRadioItemProps { onChange?: Ariakit.MenuItemRadioProps[ 'onChange' ]; } -export interface MenuSeparatorProps {} +export interface SeparatorProps {}