From 29c843343b7be82393ec84a09d4a8b238c9efc0d Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Tue, 21 Jun 2022 15:02:29 -0400 Subject: [PATCH 1/8] convert menu to TS --- .../src/components/Menu/examples/Menu.md | 1303 +---------------- .../components/Menu/examples/MenuBasic.tsx | 51 + .../examples/MenuDrilldownBreadcrumbs.tsx | 346 +++++ .../examples/MenuFilteringWithTextInput.tsx | 52 + .../Menu/examples/MenuOptionMultiSelect.tsx | 29 + .../Menu/examples/MenuOptionSingleSelect.tsx | 27 + .../Menu/examples/MenuScrollable.tsx | 48 + .../MenuScrollableCustomMenuHeight.tsx | 48 + .../Menu/examples/MenuWithActions.tsx | 74 + .../Menu/examples/MenuWithCheckbox.tsx | 4 +- .../Menu/examples/MenuWithDescription.tsx | 35 + .../Menu/examples/MenuWithFavorites.tsx | 105 ++ .../Menu/examples/MenuWithFooter.tsx | 39 + .../Menu/examples/MenuWithIcons.tsx | 33 + .../Menu/examples/MenuWithLinks.tsx | 30 + .../Menu/examples/MenuWithSeparators.tsx | 25 + .../Menu/examples/MenuWithTitledGroups.tsx | 46 + .../Menu/examples/MenuWithViewMore.tsx | 118 ++ 18 files changed, 1124 insertions(+), 1289 deletions(-) create mode 100644 packages/react-core/src/components/Menu/examples/MenuBasic.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuOptionSingleSelect.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuScrollable.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuScrollableCustomMenuHeight.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithActions.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx create mode 100644 packages/react-core/src/components/Menu/examples/MenuWithViewMore.tsx diff --git a/packages/react-core/src/components/Menu/examples/Menu.md b/packages/react-core/src/components/Menu/examples/Menu.md index 31b87730634..2be8fefd63a 100644 --- a/packages/react-core/src/components/Menu/examples/Menu.md +++ b/packages/react-core/src/components/Menu/examples/Menu.md @@ -20,112 +20,12 @@ import AngleLeftIcon from '@patternfly/react-icons/dist/esm/icons/angle-left-ico ### Basic -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem, Checkbox } from '@patternfly/react-core'; - -class MenuBasicList extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - isPlain: false - }; - this.onSelect = (event, itemId) => { - console.log(`clicked ${itemId}`); - this.setState({ - activeItem: itemId - }); - }; - this.togglePlain = checked => { - this.setState({ - isPlain: checked - }); - }; - } - - render() { - const { activeItem, isPlain } = this.state; - return ( - - - - - Action - event.preventDefault()} - > - Link - - Disabled action - - Disabled link - - - - -
- -
-
- ); - } -} +```ts file="MenuBasic.tsx" ``` ### With icons -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; -import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; -import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; -import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; - -class MenuIconsList extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - } itemId={0}> - From git - - } itemId={1}> - Container image - - } itemId={2}> - Docker file - - - - - ); - } -} +```ts file="MenuWithIcons.tsx" ``` ### With checkbox @@ -135,552 +35,47 @@ class MenuIconsList extends React.Component { ### Filtering with text input -```js -import React from 'react'; -import { Menu, MenuList, MenuItem, MenuContent, MenuInput, TextInput, Divider } from '@patternfly/react-core'; - -class MenuWithFiltering extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - input: '' - }; - - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - - this.handleTextInputChange = (value, field) => { - this.setState({ [field]: value }); - }; - } - - render() { - const { activeItem, input } = this.state; - const menuListItemsText = ['Action 1', 'Action 2', 'Action 3']; - - const menuListItems = menuListItemsText - .filter(item => !input || item.toLowerCase().includes(input.toString().toLowerCase())) - .map((currentValue, index) => ( - - {currentValue} - - )); - if (input && menuListItems.length === 0) { - menuListItems.push( - - No results found - - ); - } - - return ( - - - this.handleTextInputChange(value, 'input')} - /> - - - - {menuListItems} - - - ); - } -} +```ts file="MenuFilteringWithTextInput.tsx" ``` ### With links -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; - -class MenuWithLinks extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - - Link 1 - - - Link 2 - - - Link 3 - - - - - ); - } -} +```ts file="MenuWithLinks.tsx" ``` ### With separator(s) -```js -import React from 'react'; -import { Divider, Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; - -class MenuWithSeparators extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - Action 1 - Action 2 - - Action 3 - - - - ); - } -} +```ts file="MenuWithSeparators.tsx" ``` ### With titled groups -```js -import React from 'react'; -import { Menu, MenuContent, MenuGroup, MenuList, MenuItem, Divider } from '@patternfly/react-core'; - -class MenuWithTitledGroups extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - - - Link not in group - - - - - - - - Link 1 - - Link 2 - - - - - - - Link 1 - - - Link 2 - - - - - - ); - } -} +```ts file="MenuWithTitledGroups.tsx" ``` ### With description -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; -import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; - -class MenuWithDescription extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - } description="Description" itemId={0}> - Action 1 - - } description="Description" itemId={1}> - Action 2 disabled - - } - description="Nunc non ornare ex, et pretium dui. Duis nec augue at urna elementum blandit tincidunt eget metus. Aenean sed metus id urna dignissim interdum. Aenean vel nisl vitae arcu vehicula pulvinar eget nec turpis. Cras sit amet est est." - itemId={2} - > - Action 3 - - - - - ); - } -} +```ts file="MenuWithDescription.tsx" ``` ### With actions -```js -import React from 'react'; -import { Menu, MenuContent, MenuGroup, MenuList, MenuItem, MenuItemAction } from '@patternfly/react-core'; -import BarsIcon from '@patternfly/react-icons/dist/esm/icons/bars-icon'; -import ClipboardIcon from '@patternfly/react-icons/dist/esm/icons/clipboard-icon'; -import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; -import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; - -class MenuWithActions extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - isActionMenuOpen: false, - selectedItems: [0, 2, 3] - }; - - this.onSelect = (event, itemId) => { - if (this.state.selectedItems.indexOf(itemId) !== -1) { - this.setState({ - selectedItems: this.state.selectedItems.filter(id => id !== itemId) - }); - } else { - this.setState({ - selectedItems: [...this.state.selectedItems, itemId] - }); - } - }; - } - - render() { - const { activeItem, selectedItems } = this.state; - - return ( - console.log(`clicked on ${itemId} - ${actionId}`)} - activeItemId={activeItem} - > - - - - } - actionId="code" - onClick={() => console.log('clicked on code icon')} - aria-label="Code" - /> - } - description="This is a description" - itemId={0} - > - Item 1 - - } actionId="alert" aria-label="Alert" />} - description="This is a description" - itemId={1} - > - Item 2 - - } actionId="copy" aria-label="Copy" />} - itemId={2} - > - Item 3 - - } actionId="expand" aria-label="Expand" />} - description="This is a description" - itemId={3} - > - Item 4 - - - - - - ); - } -} +```ts file="MenuWithActions.tsx" ``` ### With favorites -```js -import React from 'react'; -import { Menu, MenuContent, MenuItem, MenuItemAction, MenuGroup, MenuList, Divider } from '@patternfly/react-core'; -import BarsIcon from '@patternfly/react-icons/dist/esm/icons/bars-icon'; -import ClipboardIcon from '@patternfly/react-icons/dist/esm/icons/clipboard-icon'; -import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; - -class MenuWithFavorites extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - favorites: [] - }; - - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId - }); - }; - this.onFavorite = (event, itemId, actionId) => { - console.log(`clicked ${itemId} - ${actionId}`); - if (actionId === 'fav') { - const isFavorite = this.state.favorites.includes(itemId); - if (isFavorite) { - this.setState({ - favorites: this.state.favorites.filter(fav => fav !== itemId) - }); - } else { - this.setState({ - favorites: [...this.state.favorites, itemId] - }); - } - } - }; - } - - render() { - const { activeItem, favorites } = this.state; - - const items = [ - { - text: 'Item 1', - description: 'Description 1', - itemId: 'item-1', - action: , - actionId: 'bars' - }, - { - text: 'Item 2', - description: 'Description 2', - itemId: 'item-2', - action: , - actionId: 'clipboard' - }, - { - text: 'Item 3', - description: 'Description 3', - itemId: 'item-3', - action: , - actionId: 'bell' - } - ]; - - return ( - - - {favorites.length > 0 && ( - - - - {items - // map the items into the favorites group that have been favorited - .filter(item => favorites.includes(item.itemId)) - .map(item => { - const { text, description, itemId, action, actionId } = item; - return ( - } - > - {text} - - ); - })} - - - - - )} - - - {items.map(item => { - const { text, description, itemId, action, actionId } = item; - const isFavorited = favorites.includes(item.itemId); - return ( - } - > - {text} - - ); - })} - - - - - ); - } -} +```ts file="MenuWithFavorites.tsx" ``` ### Option single select -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; -import TableIcon from '@patternfly/react-icons/dist/esm/icons/table-icon'; - -class MenuOptionSingleSelect extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - selectedItem: 0 - }; - - this.onSelect = (event, itemId) => { - this.setState({ - activeItem: itemId, - selectedItem: itemId - }); - }; - } - - render() { - const { activeItem, selectedItem } = this.state; - return ( - - - - Option 1 - Option 2 - } itemId={2}> - Option 3 - - - - - ); - } -} +```ts file="MenuOptionSingleSelect.tsx" ``` ### Option multi select -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; -import TableIcon from '@patternfly/react-icons/dist/esm/icons/table-icon'; - -class MenuOptionMultiSelect extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - selectedItems: [] - }; - this.onSelect = (event, itemId) => { - if (this.state.selectedItems.indexOf(itemId) !== -1) { - this.setState({ - selectedItems: this.state.selectedItems.filter(id => id !== itemId) - }); - } else { - this.setState({ - selectedItems: [...this.state.selectedItems, itemId] - }); - } - }; - } - - render() { - const { activeItem, selectedItems } = this.state; - return ( - - - - Option 1 - Option 2 - } itemId={2}> - Option 3 - - - - - ); - } -} +```ts file="MenuOptionMultiSelect.tsx" ``` ### With drilldown @@ -702,691 +97,25 @@ To render an initially drilled in menu, the `menuDrilledIn`, `drilldownPath`, an ### With drilldown breadcrumbs -```js isBeta -import React from 'react'; -import { - Menu, - MenuContent, - MenuList, - MenuItem, - Divider, - DrilldownMenu, - Breadcrumb, - BreadcrumbItem, - BreadcrumbHeading, - MenuBreadcrumb, - Dropdown, - DropdownItem, - BadgeToggle, - Checkbox -} from '@patternfly/react-core'; -import StorageDomainIcon from '@patternfly/react-icons/dist/esm/icons/storage-domain-icon'; -import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; -import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; -import AngleLeftIcon from '@patternfly/react-icons/dist/esm/icons/angle-left-icon'; -import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; - -class MenuWithDrilldownBreadcrumbs extends React.Component { - constructor(props) { - super(props); - this.state = { - menuDrilledIn: [], - drilldownPath: [], - menuHeights: {}, - activeMenu: 'breadcrumbs-rootMenu', - breadcrumb: undefined, - withMaxMenuHeight: false - }; - - this.onToggle = (isOpen, key) => { - switch (key) { - case 'app': - this.setState({ - breadcrumb: this.appGroupingBreadcrumb(isOpen) - }); - break; - case 'label': - this.setState({ - breadcrumb: this.labelsBreadcrumb(isOpen) - }); - break; - default: - break; - } - }; - - this.onToggleMaxMenuHeight = checked => { - this.setState({ - withMaxMenuHeight: checked - }); - }; - - this.drillOut = (toMenuId, fromPathId, breadcrumb) => { - const indexOfMenuId = this.state.menuDrilledIn.indexOf(toMenuId); - const menuDrilledInSansLast = this.state.menuDrilledIn.slice(0, indexOfMenuId); - const indexOfMenuIdPath = this.state.drilldownPath.indexOf(fromPathId); - const pathSansLast = this.state.drilldownPath.slice(0, indexOfMenuIdPath); - this.setState({ - menuDrilledIn: menuDrilledInSansLast, - drilldownPath: pathSansLast, - activeMenu: toMenuId, - breadcrumb - }); - }; - this.setHeight = (menuId, height) => { - if (!this.state.menuHeights[menuId]) { - this.setState({ - menuHeights: { - ...this.state.menuHeights, - [menuId]: height - } - }); - } - }; - this.drillIn = (fromMenuId, toMenuId, pathId) => { - this.setState({ - menuDrilledIn: [...this.state.menuDrilledIn, fromMenuId], - drilldownPath: [...this.state.drilldownPath, pathId], - activeMenu: toMenuId - }); - }; - - this.startRolloutBreadcrumb = ( - - this.drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> - Root - - Start rollout - - ); - - this.appGroupingBreadcrumb = isOpen => { - return ( - - this.drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> - Root - - - this.onToggle(open, 'app')}> - 1 - - } - isOpen={isOpen} - dropdownItems={[ - } - onClick={() => - this.drillOut('breadcrumbs-drilldownMenuStart', 'group:app_grouping_start', this.startRolloutBreadcrumb) - } - > - Start rollout - - ]} - /> - - Application Grouping - - ); - }; - - this.labelsBreadcrumb = isOpen => ( - - this.drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> - Root - - - this.onToggle(open, 'label')}> - 1 - - } - isOpen={isOpen} - dropdownItems={[ - } - onClick={() => this.drillOut('breadcrumbs-drilldownMenuStart', 'group:labels_start', this.startRolloutBreadcrumb)} - > - Start rollout - - ]} - /> - - Labels - - ); - - this.pauseRolloutsBreadcrumb = ( - - this.drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> - Root - - Pause rollouts - - ); - - this.pauseRolloutsAppGrpBreadcrumb = ( - - this.drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> - Root - - this.drillOut('breadcrumbs-drilldownMenuPause', 'group:app_grouping', this.pauseRolloutsBreadcrumb)} - > - Pause rollouts - - Application Grouping - - ); - - this.pauseRolloutsLabelsBreadcrumb = ( - - this.drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> - Root - - this.drillOut('breadcrumbs-drilldownMenuPause', 'group:labels', this.pauseRolloutsBreadcrumb)} - > - Pause rollouts - - Labels - - ); - - this.addStorageBreadcrumb = ( - - this.drillOut('breadcrumbs-rootMenu', 'group:storage', null)}> - Root - - Add storage - - ); - } - - render() { - const { menuDrilledIn, drilldownPath, activeMenu, menuHeights, breadcrumb, withMaxMenuHeight } = this.state; - - return ( - <> - -
- - {breadcrumb && ( - <> - {breadcrumb} - - - )} - - - this.setState({ breadcrumb: this.startRolloutBreadcrumb })} - drilldownMenu={ - - this.setState({ breadcrumb: this.appGroupingBreadcrumb(false) })} - drilldownMenu={ - - Group A - Group B - Group C - Group D - Group E - Group F - Group G - - } - > - Application grouping - - Count - this.setState({ breadcrumb: this.labelsBreadcrumb(false) })} - drilldownMenu={ - - Label 1 - Label 2 - Label 3 - - } - > - Labels - - Annotations - - } - > - Start rollout - - this.setState({ breadcrumb: this.pauseRolloutsBreadcrumb })} - drilldownMenu={ - - this.setState({ breadcrumb: this.pauseRolloutsAppGrpBreadcrumb })} - drilldownMenu={ - - Group A - Group B - Group C - - } - > - Application grouping - - Count - this.setState({ breadcrumb: this.pauseRolloutsLabelsBreadcrumb })} - drilldownMenu={ - - Label 1 - Label 2 - Label 3 - - } - > - Labels - - Annotations - - } - > - Pause rollouts - - } - direction="down" - onClick={() => this.setState({ breadcrumb: this.addStorageBreadcrumb })} - drilldownMenu={ - - } itemId="git"> - From git - - } itemId="container"> - Container image - - } itemId="docker"> - Docker file - - - } - > - Add storage - - Edit - Delete deployment config - - - - - ); - } -} +```ts file="MenuDrilldownBreadcrumbs.tsx" isBeta ``` ### Scrollable -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; - -class MenuBasicList extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - console.log(`clicked ${itemId}`); - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - Action 1 - Action 2 - Action 3 - Action 4 - Action 5 - Action 6 - Action 7 - Action 8 - Action 9 - Action 10 - Action 11 - Action 12 - Action 13 - Action 14 - Action 15 - event.preventDefault()} - > - Link - - Disabled action - - Disabled link - - - - - ); - } -} +```ts file="MenuScrollable.tsx" ``` ### Scrollable with custom menu height -```js -import React from 'react'; -import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; - -class MenuBasicList extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - console.log(`clicked ${itemId}`); - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - Action 1 - Action 2 - Action 3 - Action 4 - Action 5 - Action 6 - Action 7 - Action 8 - Action 9 - Action 10 - Action 11 - Action 12 - Action 13 - Action 14 - Action 15 - event.preventDefault()} - > - Link - - Disabled action - - Disabled link - - - - - ); - } -} +```ts file="MenuScrollableCustomMenuHeight.tsx" ``` ### With footer -```js -import React from 'react'; -import { Menu, MenuList, MenuItem, MenuContent, MenuFooter, Button } from '@patternfly/react-core'; - -class FooterMenu extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0 - }; - this.onSelect = (event, itemId) => { - console.log(`clicked ${itemId}`); - this.setState({ - activeItem: itemId - }); - }; - } - - render() { - const { activeItem } = this.state; - return ( - - - - Action - event.preventDefault()} - > - Link - - Disabled action - - Disabled link - - - - - - - - ); - } -} +```ts file="MenuWithFooter.tsx" ``` ### With view more -```js -import React from 'react'; -import { Menu, MenuList, MenuItem, MenuContent, MenuFooter, Spinner } from '@patternfly/react-core'; - -class ViewMoreMenu extends React.Component { - constructor(props) { - super(props); - this.state = { - activeItem: 0, - isLoading: false, - numOptions: 3 - }; - this.activeItemRef = React.createRef(); - this.viewMoreRef = React.createRef(); - - this.menuOptions = [ - - Action - , - event.preventDefault()} - > - Link - , - - Disabled action - , - - Disabled link - , - - Action 2 - , - - Action 3 - , - - Action 4 - , - - Action 5 - , - - Final option - - ]; - - this.onSelect = (event, itemId) => { - console.log(`clicked ${itemId}`); - this.setState({ - activeItem: itemId - }); - }; - - this.simulateNetworkCall = networkCallback => { - setTimeout(networkCallback, 2000); - }; - - this.getNextValidItem = (startingIndex, maxLength) => { - let validItem; - for (let i = startingIndex; i < maxLength; i++) { - if (this.menuOptions[i].props.isDisabled) { - continue; - } else { - validItem = this.menuOptions[i]; - break; - } - } - return validItem; - }; - - this.loadMoreOptions = stateCallback => { - const newLength = - this.state.numOptions + 3 <= this.menuOptions.length ? this.state.numOptions + 3 : this.menuOptions.length; - const prevPosition = this.state.numOptions; - const nextValidItem = this.getNextValidItem(prevPosition, newLength); - - this.setState({ numOptions: newLength, isLoading: false, activeItem: nextValidItem.props.itemId }, stateCallback); - }; - - this.onViewMoreClick = event => { - this.setState({ isLoading: true }); - this.simulateNetworkCall(() => { - this.loadMoreOptions(() => { - this.activeItemRef.current.focus(); - }); - }); - }; - - this.onViewMoreKeyDown = event => { - if (!(event.key === ' ' || event.key === 'Enter')) { - return; - } - event.stopPropagation(); - event.preventDefault(); - - this.setState({ isLoading: true }); - this.simulateNetworkCall(() => { - this.loadMoreOptions(() => { - if (this.viewMoreRef.current) { - this.viewMoreRef.current.tabIndex = -1; - } - const firstMenuItem = this.activeItemRef.current.closest('ul').firstChild; - firstMenuItem.querySelector('button, a').tabIndex = -1; - this.activeItemRef.current.tabIndex = 0; - this.activeItemRef.current.focus(); - }); - }); - }; - } - - render() { - const { activeItem, isLoading, numOptions } = this.state; - return ( - - - - {this.menuOptions.slice(0, numOptions).map(option => { - const props = option.props; - - return ( - - ); - })} - {numOptions !== this.menuOptions.length && ( - - {isLoading ? : 'View more'} - - )} - - - - ); - } -} +```ts file="MenuWithViewMore.tsx" ``` diff --git a/packages/react-core/src/components/Menu/examples/MenuBasic.tsx b/packages/react-core/src/components/Menu/examples/MenuBasic.tsx new file mode 100644 index 00000000000..ec4ffa65fbd --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuBasic.tsx @@ -0,0 +1,51 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem, Checkbox } from '@patternfly/react-core'; + +export const MenuBasic: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + const [isPlain, setIsPlain] = React.useState(false); + + const onSelect = (event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + const togglePlain = (checked: boolean) => { + setIsPlain(checked); + }; + + return ( + + + + + Action + event.preventDefault()} + > + Link + + Disabled action + + Disabled link + + + + +
+ +
+
+ ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx b/packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx new file mode 100644 index 00000000000..81f15cb69c8 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx @@ -0,0 +1,346 @@ +import React from 'react'; +import { + Menu, + MenuContent, + MenuList, + MenuItem, + Divider, + DrilldownMenu, + Breadcrumb, + BreadcrumbItem, + BreadcrumbHeading, + MenuBreadcrumb, + Dropdown, + DropdownItem, + BadgeToggle, + Checkbox +} from '@patternfly/react-core'; +import StorageDomainIcon from '@patternfly/react-icons/dist/esm/icons/storage-domain-icon'; +import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; +import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; +import AngleLeftIcon from '@patternfly/react-icons/dist/esm/icons/angle-left-icon'; +import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; + +export const MenuDrilldownBreadcrumbs: React.FunctionComponent = () => { + const [menuDrilledIn, setMenuDrilledIn] = React.useState([]); + const [drilldownPath, setDrilldownPath] = React.useState([]); + const [menuHeights, setMenuHeights] = React.useState({}); + const [activeMenu, setActiveMenu] = React.useState('rootMenu'); + const [breadcrumb, setBreadcrumb] = React.useState(); + const [withMaxMenuHeight, setWithMaxMenuHeight] = React.useState(false); + + const onToggle = (isOpen: boolean, key: string) => { + switch (key) { + case 'app': + setBreadcrumb(appGroupingBreadcrumb(isOpen)); + break; + case 'label': + setBreadcrumb(labelsBreadcrumb(isOpen)); + break; + default: + break; + } + }; + + const onToggleMaxMenuHeight = (checked: boolean) => { + setWithMaxMenuHeight(checked); + }; + + const drillOut = (toMenuId: string, fromPathId: string, _breadcrumb: JSX.Element | null) => { + const indexOfMenuId = menuDrilledIn.indexOf(toMenuId); + const menuDrilledInSansLast = menuDrilledIn.slice(0, indexOfMenuId); + const indexOfMenuIdPath = drilldownPath.indexOf(fromPathId); + const pathSansLast = drilldownPath.slice(0, indexOfMenuIdPath); + setMenuDrilledIn(menuDrilledInSansLast); + setDrilldownPath(pathSansLast); + setActiveMenu(toMenuId); + // this.setState({ + // menuDrilledIn: menuDrilledInSansLast, + // drilldownPath: pathSansLast, + // activeMenu: toMenuId, + // breadcrumb + // }); + }; + const setHeight = (menuId: string, height: number) => { + if (menuHeights[menuId]) { + setMenuHeights({ ...menuHeights, [menuId]: height }); + // this.setState({ + // menuHeights: { + // ...this.state.menuHeights, + // [menuId]: height + // } + // }); + } + }; + const drillIn = (fromMenuId: string, toMenuId: string, pathId: string) => { + setMenuDrilledIn([...menuDrilledIn, fromMenuId]); + setDrilldownPath([...drilldownPath, pathId]); + setActiveMenu(toMenuId); + // this.setState({ + // menuDrilledIn: [...this.state.menuDrilledIn, fromMenuId], + // drilldownPath: [...this.state.drilldownPath, pathId], + // activeMenu: toMenuId + // }); + }; + + const startRolloutBreadcrumb = ( + + drillOut('rootMenu', 'group:start_rollout', null)}> + Root + + Start rollout + + ); + + const appGroupingBreadcrumb = (isOpen: boolean) => ( + + drillOut('rootMenu', 'group:start_rollout', null)}> + Root + + + onToggle(open, 'app')}> + 1 + + } + isOpen={isOpen} + dropdownItems={[ + } + onClick={() => drillOut('drilldownMenuStart', 'group:app_grouping_start', startRolloutBreadcrumb)} + > + Start rollout + + ]} + /> + + Application Grouping + + ); + + const labelsBreadcrumb = (isOpen: boolean) => ( + + drillOut('rootMenu', 'group:start_rollout', null)}> + Root + + + onToggle(open, 'label')}> + 1 + + } + isOpen={isOpen} + dropdownItems={[ + } + onClick={() => drillOut('drilldownMenuStart', 'group:labels_start', startRolloutBreadcrumb)} + > + Start rollout + + ]} + /> + + Labels + + ); + + const pauseRolloutsBreadcrumb = ( + + drillOut('rootMenu', 'group:pause_rollout', null)}> + Root + + Pause rollouts + + ); + + const pauseRolloutsAppGrpBreadcrumb = ( + + drillOut('rootMenu', 'group:pause_rollout', null)}> + Root + + drillOut('drilldownMenuPause', 'group:app_grouping', pauseRolloutsBreadcrumb)} + > + Pause rollouts + + Application Grouping + + ); + + const pauseRolloutsLabelsBreadcrumb = ( + + drillOut('rootMenu', 'group:pause_rollout', null)}> + Root + + drillOut('drilldownMenuPause', 'group:labels', pauseRolloutsBreadcrumb)} + > + Pause rollouts + + Labels + + ); + + const addStorageBreadcrumb = ( + + drillOut('rootMenu', 'group:storage', null)}> + Root + + Add storage + + ); + + return ( + <> + +
+ drillOut} + onGetMenuHeight={setHeight} + > + {breadcrumb && ( + <> + {breadcrumb} + + + )} + + + setBreadcrumb(startRolloutBreadcrumb)} + drilldownMenu={ + + setBreadcrumb(appGroupingBreadcrumb(false))} + drilldownMenu={ + + Group A + Group B + Group C + Group D + Group E + Group F + Group G + + } + > + Application grouping + + Count + setBreadcrumb(labelsBreadcrumb(false))} + drilldownMenu={ + + Label 1 + Label 2 + Label 3 + + } + > + Labels + + Annotations + + } + > + Start rollout + + setBreadcrumb(pauseRolloutsBreadcrumb)} + drilldownMenu={ + + setBreadcrumb(pauseRolloutsAppGrpBreadcrumb)} + drilldownMenu={ + + Group A + Group B + Group C + + } + > + Application grouping + + Count + setBreadcrumb(pauseRolloutsLabelsBreadcrumb)} + drilldownMenu={ + + Label 1 + Label 2 + Label 3 + + } + > + Labels + + Annotations + + } + > + Pause rollouts + + } + direction="down" + onClick={() => setBreadcrumb(addStorageBreadcrumb)} + drilldownMenu={ + + } itemId="git"> + From git + + } itemId="container"> + Container image + + } itemId="docker"> + Docker file + + + } + > + Add storage + + Edit + Delete deployment config + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx b/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx new file mode 100644 index 00000000000..19a7f854bb2 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx @@ -0,0 +1,52 @@ +import React from 'react'; +import { Menu, MenuList, MenuItem, MenuContent, MenuInput, TextInput, Divider } from '@patternfly/react-core'; + +export const MenuFilteringWithTextInput: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + const [input, setInput] = React.useState(''); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + const handleTextInputChange = (value: string) => { + setInput(value); + }; + + const menuListItemsText = ['Action 1', 'Action 2', 'Action 3']; + + const menuListItems = menuListItemsText + .filter(item => !input || item.toLowerCase().includes(input.toString().toLowerCase())) + .map((currentValue, index) => ( + + {currentValue} + + )); + if (input && menuListItems.length === 0) { + menuListItems.push( + + No results found + + ); + } + + return ( + + + handleTextInputChange(value)} + /> + + + + {menuListItems} + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx b/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx new file mode 100644 index 00000000000..18a9d137ca9 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx @@ -0,0 +1,29 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; +import TableIcon from '@patternfly/react-icons/dist/esm/icons/table-icon'; + +export const MenuOptionMultiSelect: React.FunctionComponent = () => { + const [selectedItems, setSelectedItems] = React.useState([]); + + const onSelect = (_event, itemId) => { + if (selectedItems.indexOf(itemId) !== -1) { + setSelectedItems(selectedItems.filter(id => id !== itemId)); + } else { + setSelectedItems([...selectedItems, itemId]); + } + }; + + return ( + + + + Option 1 + Option 2 + } itemId={2}> + Option 3 + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuOptionSingleSelect.tsx b/packages/react-core/src/components/Menu/examples/MenuOptionSingleSelect.tsx new file mode 100644 index 00000000000..57e21bcbd99 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuOptionSingleSelect.tsx @@ -0,0 +1,27 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; +import TableIcon from '@patternfly/react-icons/dist/esm/icons/table-icon'; + +export const MenuOptionSingleSelect: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + const [selectedItem, setSelectedItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + setActiveItem(itemId); + setSelectedItem(itemId); + }; + + return ( + + + + Option 1 + Option 2 + } itemId={2}> + Option 3 + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuScrollable.tsx b/packages/react-core/src/components/Menu/examples/MenuScrollable.tsx new file mode 100644 index 00000000000..e4909ec1dfc --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuScrollable.tsx @@ -0,0 +1,48 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; + +export const MenuScrollable: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + Action 1 + Action 2 + Action 3 + Action 4 + Action 5 + Action 6 + Action 7 + Action 8 + Action 9 + Action 10 + Action 11 + Action 12 + Action 13 + Action 14 + Action 15 + event.preventDefault()} + > + Link + + Disabled action + + Disabled link + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuScrollableCustomMenuHeight.tsx b/packages/react-core/src/components/Menu/examples/MenuScrollableCustomMenuHeight.tsx new file mode 100644 index 00000000000..f1891efae60 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuScrollableCustomMenuHeight.tsx @@ -0,0 +1,48 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; + +export const MenuScrollableCustomMenuHeight: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + Action 1 + Action 2 + Action 3 + Action 4 + Action 5 + Action 6 + Action 7 + Action 8 + Action 9 + Action 10 + Action 11 + Action 12 + Action 13 + Action 14 + Action 15 + event.preventDefault()} + > + Link + + Disabled action + + Disabled link + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx new file mode 100644 index 00000000000..daa87e90dc7 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx @@ -0,0 +1,74 @@ +import React from 'react'; +import { Menu, MenuContent, MenuGroup, MenuList, MenuItem, MenuItemAction } from '@patternfly/react-core'; +import BarsIcon from '@patternfly/react-icons/dist/esm/icons/bars-icon'; +import ClipboardIcon from '@patternfly/react-icons/dist/esm/icons/clipboard-icon'; +import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; +import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; + +export const MenuWithActions: React.FunctionComponent = () => { + const [selectedItems, setSelectedItems] = React.useState([0, 2, 3]); + + const onSelect = (_event, itemId) => { + if (selectedItems.indexOf(itemId) !== -1) { + setSelectedItems(selectedItems.filter(id => id !== itemId)); + } else { + setSelectedItems([...selectedItems, itemId]); + } + }; + + return ( + console.log(`clicked on ${itemId} - ${actionId}`)} + activeItemId={0} + > + + + + } + actionId="code" + // eslint-disable-next-line no-console + onClick={() => console.log('clicked on code icon')} + aria-label="Code" + /> + } + description="This is a description" + itemId={0} + > + Item 1 + + } actionId="alert" aria-label="Alert" />} + description="This is a description" + itemId={1} + > + Item 2 + + } actionId="copy" aria-label="Copy" />} + itemId={2} + > + Item 3 + + } actionId="expand" aria-label="Expand" />} + description="This is a description" + itemId={3} + > + Item 4 + + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx b/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx index 2640d18fb7c..2b14100b228 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx @@ -1,11 +1,11 @@ import React from 'react'; import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; -export const MenuCheckboxList: React.FunctionComponent = () => { +export const MenuWithCheckbox: React.FunctionComponent = () => { const [selectedItems, setSelectedItems] = React.useState([]); /* eslint no-unused-vars: ["error", {"args": "after-used"}] */ - const onSelect = (event: React.MouseEvent, itemId: number | string) => { + const onSelect = (event: React.MouseEvent | undefined, itemId: number | string | undefined) => { const item = itemId as number; if (selectedItems.includes(item)) { setSelectedItems(selectedItems.filter(id => id !== item)); diff --git a/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx new file mode 100644 index 00000000000..58798fbbc14 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx @@ -0,0 +1,35 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; +import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; + +export const MenuWithDescription: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + } description="Description" itemId={0}> + Action 1 + + } description="Description" itemId={1}> + Action 2 disabled + + } + description="Nunc non ornare ex, et pretium dui. Duis nec augue at urna elementum blandit tincidunt eget metus. Aenean sed metus id urna dignissim interdum. Aenean vel nisl vitae arcu vehicula pulvinar eget nec turpis. Cras sit amet est est." + itemId={2} + > + Action 3 + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx new file mode 100644 index 00000000000..0d9cdd79faa --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx @@ -0,0 +1,105 @@ +import React from 'react'; +import { Menu, MenuContent, MenuItem, MenuItemAction, MenuGroup, MenuList, Divider } from '@patternfly/react-core'; +import BarsIcon from '@patternfly/react-icons/dist/esm/icons/bars-icon'; +import ClipboardIcon from '@patternfly/react-icons/dist/esm/icons/clipboard-icon'; +import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; + +export const MenuWithFavorites: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + const [favorites, setFavorites] = React.useState([]); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + const onFavorite = (event, itemId: string, actionId: string) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId} - ${actionId}`); + if (actionId === 'fav') { + const isFavorite = favorites.includes(itemId); + if (isFavorite) { + setFavorites(favorites.filter(fav => fav !== itemId)); + } else { + setFavorites([...favorites, itemId]); + } + } + }; + + const items = [ + { + text: 'Item 1', + description: 'Description 1', + itemId: 'item-1', + action: , + actionId: 'bars' + }, + { + text: 'Item 2', + description: 'Description 2', + itemId: 'item-2', + action: , + actionId: 'clipboard' + }, + { + text: 'Item 3', + description: 'Description 3', + itemId: 'item-3', + action: , + actionId: 'bell' + } + ]; + + return ( + + + {favorites.length > 0 && ( + + + + {items + // map the items into the favorites group that have been favorited + .filter(item => favorites.includes(item.itemId)) + .map(item => { + const { text, description, itemId, action, actionId } = item; + return ( + } + > + {text} + + ); + })} + + + + + )} + + + {items.map(item => { + const { text, description, itemId, action, actionId } = item; + const isFavorited = favorites.includes(item.itemId); + return ( + } + > + {text} + + ); + })} + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx new file mode 100644 index 00000000000..a4d086efc12 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx @@ -0,0 +1,39 @@ +import React from 'react'; +import { Menu, MenuList, MenuItem, MenuContent, MenuFooter, Button } from '@patternfly/react-core'; + +export const MenuWithFooter: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + Action + event.preventDefault()} + > + Link + + Disabled action + + Disabled link + + + + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx b/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx new file mode 100644 index 00000000000..1da82814ae7 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx @@ -0,0 +1,33 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; +import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-icon'; +import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; +import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; + +export const MenuWithIcons: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + } itemId={0}> + From git + + } itemId={1}> + Container image + + } itemId={2}> + Docker file + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx b/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx new file mode 100644 index 00000000000..d60b9c156d7 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx @@ -0,0 +1,30 @@ +import React from 'react'; +import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; + +export const MenuWithLinks: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + + Link 1 + + + Link 2 + + + Link 3 + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx b/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx new file mode 100644 index 00000000000..5879217dab0 --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx @@ -0,0 +1,25 @@ +import React from 'react'; +import { Divider, Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; + +export const MenuWithSeparators: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + Action 1 + Action 2 + + Action 3 + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx new file mode 100644 index 00000000000..ea9bf6aa31e --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx @@ -0,0 +1,46 @@ +import React from 'react'; +import { Menu, MenuContent, MenuGroup, MenuList, MenuItem, Divider } from '@patternfly/react-core'; + +export const MenuWithTitledGroups: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + + const onSelect = (_event, itemId) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId); + }; + + return ( + + + + + + Link not in group + + + + + + + + Link 1 + + Link 2 + + + + + + + Link 1 + + + Link 2 + + + + + + ); +}; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithViewMore.tsx b/packages/react-core/src/components/Menu/examples/MenuWithViewMore.tsx new file mode 100644 index 00000000000..9d84e8b56de --- /dev/null +++ b/packages/react-core/src/components/Menu/examples/MenuWithViewMore.tsx @@ -0,0 +1,118 @@ +import React from 'react'; +import { Menu, MenuList, MenuItem, MenuContent, Spinner } from '@patternfly/react-core'; + +export const MenuWithViewMore: React.FunctionComponent = () => { + const [activeItem, setActiveItem] = React.useState(0); + const [isLoading, setIsLoading] = React.useState(false); + const [numOptions, setNumOptions] = React.useState(3); + // eslint-disable-next-line @typescript-eslint/no-unused-vars + const [menuOptions, setMenuOptions] = React.useState([ + + Action + , + event.preventDefault()} + > + Link + , + + Disabled action + , + + Disabled link + , + + Action 2 + , + + Action 3 + , + + Action 4 + , + + Action 5 + , + + Final option + + ]); + const [visibleOptions, setVisibleOptions] = React.useState(menuOptions.slice(0, numOptions)); + + const activeItemRef = React.useRef(null); + const viewMoreRef = React.useRef(null); + + React.useEffect(() => { + activeItemRef.current?.focus(); + }, [visibleOptions]); + + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + // eslint-disable-next-line no-console + console.log(`clicked ${itemId}`); + setActiveItem(itemId as string); + }; + + const simulateNetworkCall = (networkCallback: () => void) => { + setTimeout(networkCallback, 2000); + }; + + const getNextValidItem = (startingIndex: number, maxLength: number) => { + let validItem; + for (let i = startingIndex; i < maxLength; i++) { + if (menuOptions[i].props.isDisabled) { + continue; + } else { + validItem = menuOptions[i]; + break; + } + } + return validItem; + }; + + const loadMoreOptions = () => { + const newLength = numOptions + 3 <= menuOptions.length ? numOptions + 3 : menuOptions.length; + const prevPosition = numOptions; + const nextValidItem = getNextValidItem(prevPosition, newLength); + + setNumOptions(newLength); + setIsLoading(false); + setActiveItem(nextValidItem.props.itemId); + setVisibleOptions(menuOptions.slice(0, newLength)); + }; + + const onViewMoreClick = () => { + setIsLoading(true); + simulateNetworkCall(() => { + loadMoreOptions(); + }); + }; + + return ( + + + + {visibleOptions.map(option => { + const props = option.props; + + return ; + })} + {numOptions !== menuOptions.length && ( + + {isLoading ? : 'View more'} + + )} + + + + ); +}; From ec1295a1ae9008d30a118fabde06f483d9026b8b Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Mon, 27 Jun 2022 15:34:37 -0400 Subject: [PATCH 2/8] update drilldown names --- .../Menu/examples/{MenuDrilldown.tsx => MenuWithDrilldown.tsx} | 2 +- ...rilldownBreadcrumbs.tsx => MenuWithDrilldownBreadcrumbs.tsx} | 2 +- ...lldownInitialState.tsx => MenuWithDrilldownInitialState.tsx} | 0 ...bmenuFunctions.tsx => MenuWithDrilldownSubmenuFunctions.tsx} | 2 +- 4 files changed, 3 insertions(+), 3 deletions(-) rename packages/react-core/src/components/Menu/examples/{MenuDrilldown.tsx => MenuWithDrilldown.tsx} (99%) rename packages/react-core/src/components/Menu/examples/{MenuDrilldownBreadcrumbs.tsx => MenuWithDrilldownBreadcrumbs.tsx} (99%) rename packages/react-core/src/components/Menu/examples/{MenuDrilldownInitialState.tsx => MenuWithDrilldownInitialState.tsx} (100%) rename packages/react-core/src/components/Menu/examples/{MenuDrilldownSubmenuFunctions.tsx => MenuWithDrilldownSubmenuFunctions.tsx} (98%) diff --git a/packages/react-core/src/components/Menu/examples/MenuDrilldown.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldown.tsx similarity index 99% rename from packages/react-core/src/components/Menu/examples/MenuDrilldown.tsx rename to packages/react-core/src/components/Menu/examples/MenuWithDrilldown.tsx index 6798b35f8c9..0918400a12a 100644 --- a/packages/react-core/src/components/Menu/examples/MenuDrilldown.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDrilldown.tsx @@ -5,7 +5,7 @@ import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-i import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; -export const MenuDrilldown: React.FunctionComponent = () => { +export const MenuWithDrilldown: React.FunctionComponent = () => { const [menuDrilledIn, setMenuDrilledIn] = React.useState([]); const [drilldownPath, setDrilldownPath] = React.useState([]); const [menuHeights, setMenuHeights] = React.useState({}); diff --git a/packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx similarity index 99% rename from packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx rename to packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx index 81f15cb69c8..a1ea9328359 100644 --- a/packages/react-core/src/components/Menu/examples/MenuDrilldownBreadcrumbs.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx @@ -21,7 +21,7 @@ import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-i import AngleLeftIcon from '@patternfly/react-icons/dist/esm/icons/angle-left-icon'; import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; -export const MenuDrilldownBreadcrumbs: React.FunctionComponent = () => { +export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const [menuDrilledIn, setMenuDrilledIn] = React.useState([]); const [drilldownPath, setDrilldownPath] = React.useState([]); const [menuHeights, setMenuHeights] = React.useState({}); diff --git a/packages/react-core/src/components/Menu/examples/MenuDrilldownInitialState.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownInitialState.tsx similarity index 100% rename from packages/react-core/src/components/Menu/examples/MenuDrilldownInitialState.tsx rename to packages/react-core/src/components/Menu/examples/MenuWithDrilldownInitialState.tsx diff --git a/packages/react-core/src/components/Menu/examples/MenuDrilldownSubmenuFunctions.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownSubmenuFunctions.tsx similarity index 98% rename from packages/react-core/src/components/Menu/examples/MenuDrilldownSubmenuFunctions.tsx rename to packages/react-core/src/components/Menu/examples/MenuWithDrilldownSubmenuFunctions.tsx index 5568ee484dc..9629b890d2a 100644 --- a/packages/react-core/src/components/Menu/examples/MenuDrilldownSubmenuFunctions.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownSubmenuFunctions.tsx @@ -5,7 +5,7 @@ import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-i import LayerGroupIcon from '@patternfly/react-icons/dist/esm/icons/layer-group-icon'; import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; -export const MenuDrilldownSubmenuFunctions: React.FunctionComponent = () => { +export const MenuWithDrilldownSubmenuFunctions: React.FunctionComponent = () => { const [menuDrilledIn, setMenuDrilledIn] = React.useState([]); const [drilldownPath, setDrilldownPath] = React.useState([]); const [menuHeights, setMenuHeights] = React.useState({}); From 93212536ee498a29dc502577ff41986807826e07 Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Tue, 28 Jun 2022 15:56:52 -0400 Subject: [PATCH 3/8] remove comments --- .../examples/MenuWithDrilldownBreadcrumbs.tsx | 17 ----------------- 1 file changed, 17 deletions(-) diff --git a/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx index a1ea9328359..6d19dc1f424 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx @@ -54,33 +54,16 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { setMenuDrilledIn(menuDrilledInSansLast); setDrilldownPath(pathSansLast); setActiveMenu(toMenuId); - // this.setState({ - // menuDrilledIn: menuDrilledInSansLast, - // drilldownPath: pathSansLast, - // activeMenu: toMenuId, - // breadcrumb - // }); }; const setHeight = (menuId: string, height: number) => { if (menuHeights[menuId]) { setMenuHeights({ ...menuHeights, [menuId]: height }); - // this.setState({ - // menuHeights: { - // ...this.state.menuHeights, - // [menuId]: height - // } - // }); } }; const drillIn = (fromMenuId: string, toMenuId: string, pathId: string) => { setMenuDrilledIn([...menuDrilledIn, fromMenuId]); setDrilldownPath([...drilldownPath, pathId]); setActiveMenu(toMenuId); - // this.setState({ - // menuDrilledIn: [...this.state.menuDrilledIn, fromMenuId], - // drilldownPath: [...this.state.drilldownPath, pathId], - // activeMenu: toMenuId - // }); }; const startRolloutBreadcrumb = ( From d180a133add6fd7b3ed92ae9f598a5fdc410169d Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Tue, 28 Jun 2022 15:58:07 -0400 Subject: [PATCH 4/8] fix file names --- packages/react-core/src/components/Menu/examples/Menu.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/packages/react-core/src/components/Menu/examples/Menu.md b/packages/react-core/src/components/Menu/examples/Menu.md index 2be8fefd63a..de09eeb021e 100644 --- a/packages/react-core/src/components/Menu/examples/Menu.md +++ b/packages/react-core/src/components/Menu/examples/Menu.md @@ -80,24 +80,24 @@ import AngleLeftIcon from '@patternfly/react-icons/dist/esm/icons/angle-left-ico ### With drilldown -```ts file="./MenuDrilldown.tsx" isBeta +```ts file="./MenuWithDrilldown.tsx" isBeta ``` ### With drilldown - initial drill in state To render an initially drilled in menu, the `menuDrilledIn`, `drilldownPath`, and `activeMenu` states must be set to an initial state. The `menuHeights` state must also be set, defining the height of the root menu. The `setHeight` function passed into the `onGetMenuHeight` property must also account for updating heights, other than the root menu, as menus drill in and out of view. -```ts file="./MenuDrilldownInitialState.tsx" isBeta +```ts file="./MenuWithDrilldownInitialState.tsx" isBeta ``` ### With drilldown - submenu functions -```ts file="./MenuDrilldownSubmenuFunctions.tsx" isBeta +```ts file="./MenuWithDrilldownSubmenuFunctions.tsx" isBeta ``` ### With drilldown breadcrumbs -```ts file="MenuDrilldownBreadcrumbs.tsx" isBeta +```ts file="MenuWithDrilldownBreadcrumbs.tsx" isBeta ``` ### Scrollable From 6294fe730b20885609cc9d7f9fc035ee42d8d8e2 Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Thu, 7 Jul 2022 15:13:21 -0400 Subject: [PATCH 5/8] PR feedback from Eric --- .../src/components/Menu/examples/MenuBasic.tsx | 6 +++--- .../Menu/examples/MenuFilteringWithTextInput.tsx | 6 +++--- .../components/Menu/examples/MenuOptionMultiSelect.tsx | 9 +++++---- .../src/components/Menu/examples/MenuWithActions.tsx | 9 +++++---- .../src/components/Menu/examples/MenuWithDescription.tsx | 8 ++++---- .../Menu/examples/MenuWithDrilldownBreadcrumbs.tsx | 2 +- .../src/components/Menu/examples/MenuWithFavorites.tsx | 8 ++++---- .../src/components/Menu/examples/MenuWithFooter.tsx | 7 ++++--- .../src/components/Menu/examples/MenuWithIcons.tsx | 8 ++++---- .../src/components/Menu/examples/MenuWithLinks.tsx | 8 ++++---- .../src/components/Menu/examples/MenuWithSeparators.tsx | 7 ++++--- .../components/Menu/examples/MenuWithTitledGroups.tsx | 8 ++++---- packages/react-core/tsconfig.json | 1 + 13 files changed, 46 insertions(+), 41 deletions(-) diff --git a/packages/react-core/src/components/Menu/examples/MenuBasic.tsx b/packages/react-core/src/components/Menu/examples/MenuBasic.tsx index ec4ffa65fbd..98280db25ab 100644 --- a/packages/react-core/src/components/Menu/examples/MenuBasic.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuBasic.tsx @@ -5,10 +5,10 @@ export const MenuBasic: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); const [isPlain, setIsPlain] = React.useState(false); - const onSelect = (event, itemId) => { - // eslint-disable-next-line no-console + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console console.log(`clicked ${itemId}`); - setActiveItem(itemId); + setActiveItem(item); }; const togglePlain = (checked: boolean) => { diff --git a/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx b/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx index 19a7f854bb2..4e8f32e2453 100644 --- a/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuFilteringWithTextInput.tsx @@ -5,10 +5,10 @@ export const MenuFilteringWithTextInput: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); const [input, setInput] = React.useState(''); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console console.log(`clicked ${itemId}`); - setActiveItem(itemId); + setActiveItem(item); }; const handleTextInputChange = (value: string) => { diff --git a/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx b/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx index 18a9d137ca9..d8c333699e6 100644 --- a/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuOptionMultiSelect.tsx @@ -5,11 +5,12 @@ import TableIcon from '@patternfly/react-icons/dist/esm/icons/table-icon'; export const MenuOptionMultiSelect: React.FunctionComponent = () => { const [selectedItems, setSelectedItems] = React.useState([]); - const onSelect = (_event, itemId) => { - if (selectedItems.indexOf(itemId) !== -1) { - setSelectedItems(selectedItems.filter(id => id !== itemId)); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; + if (selectedItems.indexOf(item) !== -1) { + setSelectedItems(selectedItems.filter(id => id !== item)); } else { - setSelectedItems([...selectedItems, itemId]); + setSelectedItems([...selectedItems, item]); } }; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx index daa87e90dc7..3d3b9002cfb 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx @@ -8,11 +8,12 @@ import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; export const MenuWithActions: React.FunctionComponent = () => { const [selectedItems, setSelectedItems] = React.useState([0, 2, 3]); - const onSelect = (_event, itemId) => { - if (selectedItems.indexOf(itemId) !== -1) { - setSelectedItems(selectedItems.filter(id => id !== itemId)); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; + if (selectedItems.indexOf(item) !== -1) { + setSelectedItems(selectedItems.filter(id => id !== item)); } else { - setSelectedItems([...selectedItems, itemId]); + setSelectedItems([...selectedItems, item]); } }; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx index 58798fbbc14..f6b3cc77ea5 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDescription.tsx @@ -5,10 +5,10 @@ import CodeBranchIcon from '@patternfly/react-icons/dist/esm/icons/code-branch-i export const MenuWithDescription: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx index 6d19dc1f424..2e7ed5d94cb 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithDrilldownBreadcrumbs.tsx @@ -56,7 +56,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { setActiveMenu(toMenuId); }; const setHeight = (menuId: string, height: number) => { - if (menuHeights[menuId]) { + if (!menuHeights[menuId]) { setMenuHeights({ ...menuHeights, [menuId]: height }); } }; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx index 0d9cdd79faa..150a0da9270 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx @@ -8,10 +8,10 @@ export const MenuWithFavorites: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); const [favorites, setFavorites] = React.useState([]); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console + console.log(`clicked ${item}`); + setActiveItem(item); }; const onFavorite = (event, itemId: string, actionId: string) => { diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx index a4d086efc12..eb6f09f059b 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithFooter.tsx @@ -4,10 +4,11 @@ import { Menu, MenuList, MenuItem, MenuContent, MenuFooter, Button } from '@patt export const MenuWithFooter: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (event, itemId) => { + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx b/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx index 1da82814ae7..d8b65ceb977 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithIcons.tsx @@ -7,10 +7,10 @@ import CubeIcon from '@patternfly/react-icons/dist/esm/icons/cube-icon'; export const MenuWithIcons: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx b/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx index d60b9c156d7..07d4fc5eb0f 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithLinks.tsx @@ -4,10 +4,10 @@ import { Menu, MenuContent, MenuList, MenuItem } from '@patternfly/react-core'; export const MenuWithLinks: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx b/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx index 5879217dab0..6c1980def14 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithSeparators.tsx @@ -4,10 +4,11 @@ import { Divider, Menu, MenuContent, MenuList, MenuItem } from '@patternfly/reac export const MenuWithSeparators: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (_event, itemId) => { + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx index ea9bf6aa31e..ae375304f7d 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx @@ -4,10 +4,10 @@ import { Menu, MenuContent, MenuGroup, MenuList, MenuItem, Divider } from '@patt export const MenuWithTitledGroups: React.FunctionComponent = () => { const [activeItem, setActiveItem] = React.useState(0); - const onSelect = (_event, itemId) => { - // eslint-disable-next-line no-console - console.log(`clicked ${itemId}`); - setActiveItem(itemId); + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const item = itemId as number; // eslint-disable-next-line no-console + console.log(`clicked ${item}`); + setActiveItem(item); }; return ( diff --git a/packages/react-core/tsconfig.json b/packages/react-core/tsconfig.json index 15945ac6cfa..f3062d0890f 100644 --- a/packages/react-core/tsconfig.json +++ b/packages/react-core/tsconfig.json @@ -1,6 +1,7 @@ { "extends": "../tsconfig.base.json", "compilerOptions": { + "jsx": "react", "rootDir": "./src", "outDir": "./dist/esm", "tsBuildInfoFile": "dist/esm.tsbuildinfo" From 0c308d4fe7a688008c33ab2737f05e918b2fad82 Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Thu, 7 Jul 2022 15:15:10 -0400 Subject: [PATCH 6/8] prefix event param --- .../src/components/Menu/examples/MenuWithCheckbox.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx b/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx index 2b14100b228..0980d539388 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithCheckbox.tsx @@ -5,7 +5,7 @@ export const MenuWithCheckbox: React.FunctionComponent = () => { const [selectedItems, setSelectedItems] = React.useState([]); /* eslint no-unused-vars: ["error", {"args": "after-used"}] */ - const onSelect = (event: React.MouseEvent | undefined, itemId: number | string | undefined) => { + const onSelect = (_event: React.MouseEvent | undefined, itemId: number | string | undefined) => { const item = itemId as number; if (selectedItems.includes(item)) { setSelectedItems(selectedItems.filter(id => id !== item)); From c8ad813064e87bd5c5320b6aa57582da89dc0602 Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Thu, 7 Jul 2022 15:16:32 -0400 Subject: [PATCH 7/8] remove comment --- .../src/components/Menu/examples/MenuWithFavorites.tsx | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx index 150a0da9270..2aacebade10 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx @@ -59,7 +59,6 @@ export const MenuWithFavorites: React.FunctionComponent = () => { {items - // map the items into the favorites group that have been favorited .filter(item => favorites.includes(item.itemId)) .map(item => { const { text, description, itemId, action, actionId } = item; From 8dfce33f3ee227f2ae31ae143ddd17858548df04 Mon Sep 17 00:00:00 2001 From: jenny-s51 Date: Tue, 26 Jul 2022 13:48:02 -0400 Subject: [PATCH 8/8] fix conflicts --- .../Menu/examples/MenuWithActions.tsx | 2 +- .../examples/MenuWithDrilldownBreadcrumbs.tsx | 42 ++++++++++--------- .../Menu/examples/MenuWithFavorites.tsx | 4 +- .../Menu/examples/MenuWithTitledGroups.tsx | 4 +- 4 files changed, 27 insertions(+), 25 deletions(-) diff --git a/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx index 3d3b9002cfb..13ff5017510 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithActions.tsx @@ -25,7 +25,7 @@ export const MenuWithActions: React.FunctionComponent = () => { activeItemId={0} > - + { const [menuDrilledIn, setMenuDrilledIn] = React.useState([]); const [drilldownPath, setDrilldownPath] = React.useState([]); const [menuHeights, setMenuHeights] = React.useState({}); - const [activeMenu, setActiveMenu] = React.useState('rootMenu'); + const [activeMenu, setActiveMenu] = React.useState('breadcrumbs-rootMenu'); const [breadcrumb, setBreadcrumb] = React.useState(); const [withMaxMenuHeight, setWithMaxMenuHeight] = React.useState(false); @@ -68,7 +68,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const startRolloutBreadcrumb = ( - drillOut('rootMenu', 'group:start_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> Root Start rollout @@ -77,7 +77,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const appGroupingBreadcrumb = (isOpen: boolean) => ( - drillOut('rootMenu', 'group:start_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> Root @@ -93,7 +93,9 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { key="dropdown-start" component="button" icon={} - onClick={() => drillOut('drilldownMenuStart', 'group:app_grouping_start', startRolloutBreadcrumb)} + onClick={() => + drillOut('breadcrumbs-drilldownMenuStart', 'group:app_grouping_start', startRolloutBreadcrumb) + } > Start rollout @@ -106,7 +108,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const labelsBreadcrumb = (isOpen: boolean) => ( - drillOut('rootMenu', 'group:start_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:start_rollout', null)}> Root @@ -122,7 +124,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { key="dropdown-start" component="button" icon={} - onClick={() => drillOut('drilldownMenuStart', 'group:labels_start', startRolloutBreadcrumb)} + onClick={() => drillOut('breadcrumbs-drilldownMenuStart', 'group:labels_start', startRolloutBreadcrumb)} > Start rollout @@ -135,7 +137,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const pauseRolloutsBreadcrumb = ( - drillOut('rootMenu', 'group:pause_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> Root Pause rollouts @@ -144,12 +146,12 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const pauseRolloutsAppGrpBreadcrumb = ( - drillOut('rootMenu', 'group:pause_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> Root drillOut('drilldownMenuPause', 'group:app_grouping', pauseRolloutsBreadcrumb)} + onClick={() => drillOut('breadcrumbs-drilldownMenuPause', 'group:app_grouping', pauseRolloutsBreadcrumb)} > Pause rollouts @@ -159,12 +161,12 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const pauseRolloutsLabelsBreadcrumb = ( - drillOut('rootMenu', 'group:pause_rollout', null)}> + drillOut('breadcrumbs-rootMenu', 'group:pause_rollout', null)}> Root drillOut('drilldownMenuPause', 'group:labels', pauseRolloutsBreadcrumb)} + onClick={() => drillOut('breadcrumbs-drilldownMenuPause', 'group:labels', pauseRolloutsBreadcrumb)} > Pause rollouts @@ -174,7 +176,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { const addStorageBreadcrumb = ( - drillOut('rootMenu', 'group:storage', null)}> + drillOut('breadcrumbs-rootMenu', 'group:storage', null)}> Root Add storage @@ -193,7 +195,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { />
{ direction="down" onClick={() => setBreadcrumb(startRolloutBreadcrumb)} drilldownMenu={ - + setBreadcrumb(appGroupingBreadcrumb(false))} drilldownMenu={ - + Group A Group B Group C @@ -241,7 +243,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { direction="down" onClick={() => setBreadcrumb(labelsBreadcrumb(false))} drilldownMenu={ - + Label 1 Label 2 Label 3 @@ -261,14 +263,14 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { direction="down" onClick={() => setBreadcrumb(pauseRolloutsBreadcrumb)} drilldownMenu={ - + setBreadcrumb(pauseRolloutsAppGrpBreadcrumb)} drilldownMenu={ - + Group A Group B Group C @@ -283,7 +285,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { direction="down" onClick={() => setBreadcrumb(pauseRolloutsLabelsBreadcrumb)} drilldownMenu={ - + Label 1 Label 2 Label 3 @@ -304,7 +306,7 @@ export const MenuWithDrilldownBreadcrumbs: React.FunctionComponent = () => { direction="down" onClick={() => setBreadcrumb(addStorageBreadcrumb)} drilldownMenu={ - + } itemId="git"> From git diff --git a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx index 2aacebade10..2e778d95533 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithFavorites.tsx @@ -56,7 +56,7 @@ export const MenuWithFavorites: React.FunctionComponent = () => { {favorites.length > 0 && ( - + {items .filter(item => favorites.includes(item.itemId)) @@ -79,7 +79,7 @@ export const MenuWithFavorites: React.FunctionComponent = () => { )} - + {items.map(item => { const { text, description, itemId, action, actionId } = item; diff --git a/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx index ae375304f7d..6318fbaaf04 100644 --- a/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx +++ b/packages/react-core/src/components/Menu/examples/MenuWithTitledGroups.tsx @@ -21,7 +21,7 @@ export const MenuWithTitledGroups: React.FunctionComponent = () => { - + Link 1 @@ -30,7 +30,7 @@ export const MenuWithTitledGroups: React.FunctionComponent = () => { - + Link 1