Demo
Usage
Import the Menu
and MenuItem
components. Note that the Menu component is rendered in a React Portal, so you can set the Menu button's width from its outer container.
import { Menu, MenuItem, View } from '@aws-amplify/ui-react';
export const BasicExample = () => {
return (
<View width="4rem">
<Menu>
<MenuItem>Option 1</MenuItem>
<MenuItem>Option 2</MenuItem>
<MenuItem>Option 3</MenuItem>
</Menu>
</View>
);
};
Menu items
Use the MenuItem
component to configure Menu options. The example below demonstrates how to add interactivity to the MenuItem
's via the onClick
handler, as well as how to use the Divider
component and isDisabled
prop.
import { Menu, MenuItem, View, Divider } from '@aws-amplify/ui-react';
export const MenuItemsExample = () => {
return (
<View width="4rem">
<Menu>
<MenuItem onClick={() => alert('Download')}>Download</MenuItem>
<MenuItem onClick={() => alert('Create a Copy')}>
Create a Copy
</MenuItem>
<Divider />
<MenuItem isDisabled onClick={() => alert('Delete')}>
Delete
</MenuItem>
</Menu>
</View>
);
};
Customize Menu button
The default Menu button can be customized by importing the MenuButton
component and passing it to the Menu
's trigger
prop. MenuButton
can take all the same props as Button.
import { Menu, MenuItem, MenuButton } from '@aws-amplify/ui-react';
export const MenuExample = () => (
<Menu
trigger={
<MenuButton variation="primary" size="large" width="40%">
Custom trigger button 🚀
</MenuButton>
}
>
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
);
Menu alignment
To control the alignment of the Menu with the Menu button, use the menuAlign
prop. Available options are start
(default), center
, and end
.
import { Flex, Menu, MenuItem } from '@aws-amplify/ui-react';
export const MenuAlignExample = () => {
return (
<Flex direction="column" width="4rem">
<Menu>
<MenuItem>Align start (default)</MenuItem>
</Menu>
<Menu menuAlign="center">
<MenuItem>Align center</MenuItem>
</Menu>
<Menu menuAlign="end">
<MenuItem>Align end</MenuItem>
</Menu>
</Flex>
);
};
Size
Control the size of the Menu button and items using the size
prop. Available options are small
, none (default), and large
.
import { Menu, MenuItem, Flex } from '@aws-amplify/ui-react';
export const SizeExample = () => {
return (
<Flex direction="column" width="4rem">
<Menu size="small">
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
</Menu>
<Menu>
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
</Menu>
<Menu size="large">
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
</Menu>
</Flex>
);
};
Controlled Menu
Create a controlled Menu
using the isOpen
and onOpenChange
props.
import * as React from 'react';
import { Menu, MenuItem, View } from '@aws-amplify/ui-react';
export const ControlledExample = () => {
const [isOpen, setIsOpen] = React.useState(false);
const handleOpenChange = (open) => {
setIsOpen(open);
// Do something else
};
const closeMenu = () => setIsOpen(false);
return (
<View width="4rem">
<Menu
isOpen={isOpen}
onOpenChange={handleOpenChange}
width="3rem"
maxWidth="4rem"
>
<MenuItem
onClick={() => {
closeMenu();
alert('Download');
}}
>
Download
</MenuItem>
<MenuItem
onClick={() => {
closeMenu();
alert('Create a Copy');
}}
>
Create a Copy
</MenuItem>
<MenuItem
onClick={() => {
closeMenu();
alert('Mark as Draft');
}}
>
Mark as Draft
</MenuItem>
</Menu>
</View>
);
};
Styling
Theme
You can customize the appearance of all Menu components in your application with a Theme.
Menu Theme Source
import { Menu, MenuItem, ThemeProvider, Theme } from '@aws-amplify/ui-react';
const theme: Theme = {
name: 'menu-theme',
tokens: {
components: {
menu: {
backgroundColor: { value: '{colors.blue.20}' },
borderRadius: { value: '0' },
item: {
minHeight: { value: '5rem' },
},
},
},
},
};
export const MenuThemeExample = () => {
return (
<ThemeProvider theme={theme} colorMode="light">
<Menu>
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
</ThemeProvider>
);
};
Icons
import { Menu, MenuItem, IconsProvider } from '@aws-amplify/ui-react';
import { FiMoreHorizontal } from 'react-icons/fi';
export const MenuIconExample = () => (
<IconsProvider
icons={{
menu: {
menu: <FiMoreHorizontal />,
},
}}
>
<Menu>
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
</IconsProvider>
);
Target classes
Class | Description |
---|---|
amplify-menu__content | Menu content container (Flex) |
amplify-menu__wrapper | Menu content wrapper |
amplify-menu__content__item | Menu item button (MenuButton, wrapped in amplify-menu-content class) |
amplify-menu__trigger | Menu trigger button (MenuButton, not wrapped in amplify-menu-content class) |
--amplify-components-menu-background-color
--amplify-components-menu-border-color
--amplify-components-menu-border-radius
--amplify-components-menu-border-style
--amplify-components-menu-border-width
--amplify-components-menu-box-shadow
--amplify-components-menu-flex-direction
--amplify-components-menu-gap
--amplify-components-menu-item-min-height
--amplify-components-menu-item-padding-inline-end
--amplify-components-menu-item-padding-inline-start
--amplify-components-menu-large-height
--amplify-components-menu-large-width
--amplify-components-menu-max-width
--amplify-components-menu-min-width
--amplify-components-menu-small-height
--amplify-components-menu-small-width
Global styling
To override styling on all Menus, you can set the Amplify CSS variables with the built-in classes.
/* styles.css */
.amplify-menu-content {
--amplify-components-button-color: var(--amplify-colors-secondary-90);
}
.amplify-menu-trigger {
--amplify-components-button-border-color: var(
--amplify-colors-secondary-90
);
--amplify-components-button-color: var(--amplify-colors-secondary-90);
}
import { Menu, MenuItem } from '@aws-amplify/ui-react';
import '@aws-amplify/ui-react/styles.css';
import './styles.css';
export const GlobalStylingExample = () => (
<Menu>
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
);
Local styling
To override styling on a specific Menu, you can use (in order of increasing specificity): a class selector, data attributes, or style props.
Using a class selector:
Note: The classname
prop is applied to the Menu dropdown content. Use the triggerClassName
prop to apply a class to the menu trigger button.
/* styles.css */
.my-menu-trigger.amplify-menu-trigger {
border-color: var(--amplify-colors-secondary-90);
color: var(--amplify-colors-secondary-90);
}
.my-menu-content .amplify-menu-content__item {
color: var(--amplify-colors-secondary-90);
}
.my-menu-content .amplify-menu-content__item:hover {
background-color: var(--amplify-colors-secondary-90);
}
import { Menu, MenuItem } from '@aws-amplify/ui-react';
import '@aws-amplify/ui-react/styles.css';
import './styles.css';
export const ClassNameExample = () => (
<Menu className="my-menu-content" triggerClassName="my-menu-trigger">
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
);
Using data attributes:
/* styles.css */
.amplify-menu-content__item[data-size='large'] {
font-size: var(--amplify-font-sizes-xxxxl);
}
import { Menu, MenuItem } from '@aws-amplify/ui-react';
import '@aws-amplify/ui-react/styles.css';
import './styles.css';
export const DataAttributesExample = () => (
<Menu size="large">
<MenuItem>Download</MenuItem>
<MenuItem>Create a Copy</MenuItem>
<MenuItem>Mark as Draft</MenuItem>
</Menu>
);
Using style props:
import { Menu, MenuItem, View, useTheme } from '@aws-amplify/ui-react';
export const StylePropsExample = () => {
const { tokens } = useTheme();
return (
<View width="4rem">
<Menu direction="row">
<MenuItem>Download</MenuItem>
<MenuItem fontStyle="italic">Create a Copy</MenuItem>
<MenuItem backgroundColor={tokens.colors.red[40]}>Delete</MenuItem>
</Menu>
</View>
);
};