Skip to content

Commit

Permalink
🐛💄Menu: implement [popover] (#3583)
Browse files Browse the repository at this point in the history
* Autocomplete: add missing existence checks

* Autocomplete option: fix "in menu" issue

* menu: implement [popover]

* menu.section: added missing role

* Update Autocomplete.test.tsx.snap
  • Loading branch information
oddvernes authored Aug 13, 2024
1 parent 33dc1a1 commit 9365916
Show file tree
Hide file tree
Showing 7 changed files with 95 additions and 45 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -714,7 +714,6 @@ function AutocompleteInner<T>(
selectedItem: null,
stateReducer: (state, actionAndChanges) => {
const { changes, type } = actionAndChanges

switch (type) {
case useCombobox.stateChangeTypes.InputClick:
return {
Expand Down Expand Up @@ -834,9 +833,9 @@ function AutocompleteInner<T>(
// MARK: popover toggle
useIsomorphicLayoutEffect(() => {
if (isOpen) {
refs.floating.current.showPopover()
refs.floating.current?.showPopover()
} else {
refs.floating.current.hidePopover()
refs.floating.current?.hidePopover()
}
}, [isOpen, refs.floating])

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ const StyledListItem = styled.li<StyledListItemType>(
user-select: none;
overflow: hidden;
touch-action: manipulation;
z-index: 3;
cursor: ${$highlighted === 'true' ? 'pointer' : 'default'};
${typographyTemplate(theme.typography)}
${spacingsTemplate(theme.spacings)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ exports[`Autocomplete Matches snapshot 1`] = `
user-select: none;
overflow: hidden;
touch-action: manipulation;
z-index: 3;
cursor: default;
margin: 0;
color: var(--eds_text__static_icons__default, rgba(61, 61, 61, 1));
Expand Down
6 changes: 3 additions & 3 deletions packages/eds-core-react/src/components/Menu/Menu.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,23 +18,23 @@ describe('Menu', () => {
it('Matches snapshot', async () => {
render(
<StyledMenu open>
<div>some random content</div>
<Menu.Item>Item 1</Menu.Item>
</StyledMenu>,
)

const menuContainer = await screen.findByRole('menu', { hidden: true })

expect(menuContainer).toMatchSnapshot()
})
it('Should pass a11y test', async () => {
it('Should not pass a11y test with div as child', async () => {
const { container } = render(
<TestMenu open>
<div>some random content</div>
</TestMenu>,
)
await act(async () => {
const results = await axe(container)
expect(results).toHaveNoViolations()
expect(results).not.toHaveNoViolations()
})
})
it('Should pass a11y test with Item', async () => {
Expand Down
68 changes: 34 additions & 34 deletions packages/eds-core-react/src/components/Menu/Menu.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { useEffect, HTMLAttributes, forwardRef, useMemo } from 'react'
import styled, { css, ThemeProvider } from 'styled-components'
import styled, { ThemeProvider } from 'styled-components'
import { useMenu, MenuProvider } from './Menu.context'
import { Paper } from '../Paper'
import { MenuList } from './MenuList'
Expand All @@ -9,7 +9,6 @@ import {
useToken,
bordersTemplate,
useIsomorphicLayoutEffect,
useIsInDialog,
} from '@equinor/eds-utils'
import { menu as tokens } from './Menu.tokens'
import { useEds } from '../EdsProvider'
Expand All @@ -22,25 +21,31 @@ import {
useFloating,
useInteractions,
useDismiss,
FloatingPortal,
size,
Middleware,
MiddlewareState,
} from '@floating-ui/react'

type MenuPaperProps = {
open: boolean
}

const { border } = tokens

const MenuPaper = styled(Paper)<MenuPaperProps>`
position: absolute;
z-index: 1400;
width: fit-content;
const MenuPaper = styled(Paper)`
width: 100%;
min-width: fit-content;
${bordersTemplate(border)};
${({ open }) => css({ display: open ? 'block' : 'none' })};
`

const StyledPopover = styled('div').withConfig({
shouldForwardProp: () => true, //workaround to avoid warning until popover gets added to react types
})<{ popover: string }>`
inset: unset;
border: 0;
padding: 0;
margin: 0;
overflow: visible;
background-color: transparent;
&::backdrop {
background-color: transparent;
}
`

const MenuContainer = forwardRef<HTMLDivElement, MenuProps>(
Expand Down Expand Up @@ -191,12 +196,19 @@ export const Menu = forwardRef<HTMLDivElement, MenuProps>(function Menu(
}
}, [refs.reference, refs.floating, update, open])

useIsomorphicLayoutEffect(() => {
if (open) {
refs.floating.current?.showPopover()
} else {
refs.floating.current?.hidePopover()
}
}, [open, refs.floating])

const { getFloatingProps } = useInteractions([
useDismiss(context, { escapeKey: false }),
])

const props = {
open,
className,
}

Expand All @@ -207,14 +219,10 @@ export const Menu = forwardRef<HTMLDivElement, MenuProps>(function Menu(
open,
}

//temporary fix when inside dialog. Should be replaced by popover api when it is ready
const inDialog = useIsInDialog(anchorEl)

const menuElement = (
return (
<ThemeProvider theme={token}>
<MenuPaper
elevation="raised"
{...props}
<StyledPopover
popover="manual"
{...getFloatingProps({
ref: popoverRef,
style: {
Expand All @@ -225,20 +233,12 @@ export const Menu = forwardRef<HTMLDivElement, MenuProps>(function Menu(
},
})}
>
<MenuProvider>
<MenuContainer {...menuProps} ref={ref} />
</MenuProvider>
</MenuPaper>
<MenuPaper elevation="raised" {...props}>
<MenuProvider>
<MenuContainer {...menuProps} ref={ref} />
</MenuProvider>
</MenuPaper>
</StyledPopover>
</ThemeProvider>
)

return (
<>
{inDialog ? (
menuElement
) : (
<FloatingPortal id="eds-menu-container">{menuElement}</FloatingPortal>
)}
</>
)
})
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ export const MenuSection = memo(function MenuSection(props: MenuSectionProps) {
</div>
)}
{title && (
<Header>
<Header role="group">
<Typography group="navigation" variant="label">
{title}
</Typography>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,42 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`Menu Matches snapshot 1`] = `
.c1 {
border: 0;
background-color: transparent;
width: auto;
position: relative;
z-index: 2;
text-decoration: none;
margin: 0;
color: var(--eds_text__static_icons__default, rgba(61, 61, 61, 1));
font-family: Equinor;
font-size: 1.000rem;
font-weight: 400;
line-height: 1.000em;
letter-spacing: 0.013em;
text-align: left;
padding-left: 24px;
padding-top: 16px;
padding-right: 24px;
padding-bottom: 16px;
}
.c1:focus-visible {
z-index: 3;
outline: 2px dashed var(--eds_interactive__focus, rgba(0, 112, 121, 1));
outline-offset: 2px;
}
.c2 {
width: auto;
display: grid;
grid-gap: 16px;
grid-auto-flow: column;
grid-auto-columns: max-content auto max-content;
align-items: center;
}
.c0 {
position: relative;
list-style: none;
Expand All @@ -17,14 +53,27 @@ exports[`Menu Matches snapshot 1`] = `
z-index: 3;
}
@media (hover:hover) and (pointer:fine) {
.c1:hover {
cursor: pointer;
background: var(--eds_interactive_table__header__fill_hover, rgba(220, 220, 220, 1));
}
}
<div
class="c0"
role="menu"
>
<div
index="0"
<button
class="c1"
role="menuitem"
tabindex="0"
>
some random content
</div>
<div
class="c2"
>
Item 1
</div>
</button>
</div>
`;

0 comments on commit 9365916

Please sign in to comment.