agroptima-design-system 0.14.0 → 0.14.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/atoms/Menu/Menu.scss +27 -58
- package/src/atoms/Menu/Menu.tsx +1 -5
- package/src/atoms/Menu/MenuDropdown.tsx +42 -0
- package/src/atoms/Menu/MenuLink.tsx +39 -0
- package/src/atoms/Menu/index.ts +3 -2
- package/src/stories/Changelog.stories.mdx +4 -0
- package/src/stories/Menu.stories.js +23 -107
- package/tests/Menu.spec.tsx +23 -25
- package/src/atoms/Menu/MenuOption.tsx +0 -79
package/package.json
CHANGED
package/src/atoms/Menu/Menu.scss
CHANGED
|
@@ -4,15 +4,19 @@
|
|
|
4
4
|
@use '../../settings/depth';
|
|
5
5
|
|
|
6
6
|
.menu {
|
|
7
|
+
@include typography.body-regular-primary;
|
|
7
8
|
list-style-type: none;
|
|
8
9
|
display: flex;
|
|
9
10
|
flex-direction: column;
|
|
10
11
|
padding: 0;
|
|
11
12
|
|
|
12
|
-
|
|
13
|
+
&-item {
|
|
13
14
|
display: flex;
|
|
14
|
-
flex-direction: column;
|
|
15
15
|
gap: config.$space-2x;
|
|
16
|
+
padding: config.$space-3x;
|
|
17
|
+
text-decoration: none;
|
|
18
|
+
color: inherit;
|
|
19
|
+
align-items: center;
|
|
16
20
|
cursor: default;
|
|
17
21
|
|
|
18
22
|
.icon {
|
|
@@ -24,46 +28,10 @@
|
|
|
24
28
|
}
|
|
25
29
|
}
|
|
26
30
|
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
> .container .right .icon {
|
|
30
|
-
transform: rotate(180deg);
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
&:has(> .dropdown) {
|
|
34
|
-
> .container .right {
|
|
35
|
-
display: inline-block;
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
> .dropdown {
|
|
39
|
-
> .menu-option details .container {
|
|
40
|
-
padding-left: config.$space-8x;
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
.container {
|
|
46
|
-
display: flex;
|
|
47
|
-
padding: config.$space-3x;
|
|
48
|
-
|
|
49
|
-
.left {
|
|
50
|
-
display: flex;
|
|
51
|
-
width: 100%;
|
|
52
|
-
gap: config.$space-2x;
|
|
53
|
-
justify-content: flex-start;
|
|
54
|
-
align-items: baseline;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
.right {
|
|
58
|
-
display: none;
|
|
59
|
-
margin-top: auto;
|
|
60
|
-
margin-bottom: auto;
|
|
61
|
-
}
|
|
62
|
-
}
|
|
31
|
+
.title {
|
|
32
|
+
flex: 1;
|
|
63
33
|
}
|
|
64
34
|
|
|
65
|
-
@include typography.body-regular-primary;
|
|
66
|
-
|
|
67
35
|
&.primary {
|
|
68
36
|
color: color_alias.$neutral-white;
|
|
69
37
|
background: color_alias.$neutral-color-900;
|
|
@@ -81,29 +49,30 @@
|
|
|
81
49
|
background: color_alias.$primary-color-600;
|
|
82
50
|
}
|
|
83
51
|
|
|
84
|
-
&.
|
|
52
|
+
&.active {
|
|
85
53
|
background: color_alias.$primary-color-600;
|
|
86
54
|
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
87
57
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
}
|
|
58
|
+
details[open] {
|
|
59
|
+
.arrow {
|
|
60
|
+
transform: rotate(180deg);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
.menu-dropdown .menu {
|
|
64
|
+
.menu-item {
|
|
65
|
+
padding-left: config.$space-8x;
|
|
66
|
+
background: color_alias.$neutral-color-100;
|
|
67
|
+
color: color_alias.$neutral-color-1000;
|
|
99
68
|
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
box-shadow: inset -3px 0px 0px 0px color_alias.$primary-color-600;
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
}
|
|
69
|
+
&:hover {
|
|
70
|
+
background: color_alias.$primary-color-100;
|
|
106
71
|
}
|
|
107
72
|
}
|
|
73
|
+
.active {
|
|
74
|
+
background: color_alias.$primary-color-100;
|
|
75
|
+
box-shadow: inset -3px 0px 0px 0px color_alias.$primary-color-600;
|
|
76
|
+
}
|
|
108
77
|
}
|
|
109
78
|
}
|
package/src/atoms/Menu/Menu.tsx
CHANGED
|
@@ -6,19 +6,15 @@ export type Variant = 'primary'
|
|
|
6
6
|
|
|
7
7
|
export interface MenuProps extends React.ComponentPropsWithoutRef<'ul'> {
|
|
8
8
|
variant?: Variant
|
|
9
|
-
isDropdown?: boolean
|
|
10
9
|
}
|
|
11
10
|
|
|
12
11
|
export function Menu({
|
|
13
12
|
variant = 'primary',
|
|
14
13
|
className,
|
|
15
|
-
isDropdown = false,
|
|
16
14
|
children,
|
|
17
15
|
...props
|
|
18
16
|
}: MenuProps): React.JSX.Element {
|
|
19
|
-
const cssClasses = classNames('menu', variant, className
|
|
20
|
-
dropdown: isDropdown,
|
|
21
|
-
})
|
|
17
|
+
const cssClasses = classNames('menu', variant, className)
|
|
22
18
|
|
|
23
19
|
return (
|
|
24
20
|
<ul className={cssClasses} role="menu" {...props}>
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { classNames } from '../../utils/classNames'
|
|
2
|
+
import { Icon, IconType } from '../Icon'
|
|
3
|
+
import './Menu.scss'
|
|
4
|
+
|
|
5
|
+
export type Variant = 'primary'
|
|
6
|
+
|
|
7
|
+
export interface MenuDropdownProps
|
|
8
|
+
extends React.ComponentPropsWithoutRef<'li'> {
|
|
9
|
+
title: string
|
|
10
|
+
variant?: Variant
|
|
11
|
+
icon?: IconType
|
|
12
|
+
isOpen?: boolean
|
|
13
|
+
name?: string
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export function MenuDropdown({
|
|
17
|
+
variant = 'primary',
|
|
18
|
+
className,
|
|
19
|
+
icon,
|
|
20
|
+
title,
|
|
21
|
+
children,
|
|
22
|
+
isOpen,
|
|
23
|
+
name,
|
|
24
|
+
...props
|
|
25
|
+
}: MenuDropdownProps): React.JSX.Element {
|
|
26
|
+
const cssClasses = classNames('menu-item', variant, className)
|
|
27
|
+
|
|
28
|
+
return (
|
|
29
|
+
<li tabIndex={0} role="menuitem" className="menu-dropdown" {...props}>
|
|
30
|
+
<details open={isOpen} name={name}>
|
|
31
|
+
<summary className={cssClasses}>
|
|
32
|
+
{icon && <Icon name={icon} />}
|
|
33
|
+
<span className="title">{title}</span>
|
|
34
|
+
<Icon className="arrow" name="AngleDown" />
|
|
35
|
+
</summary>
|
|
36
|
+
<ul className="menu" role="menu">
|
|
37
|
+
{children}
|
|
38
|
+
</ul>
|
|
39
|
+
</details>
|
|
40
|
+
</li>
|
|
41
|
+
)
|
|
42
|
+
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import './Menu.scss'
|
|
2
|
+
import React from 'react'
|
|
3
|
+
import { Icon, IconType } from '../Icon'
|
|
4
|
+
import { classNames } from '../../utils/classNames'
|
|
5
|
+
import Link from 'next/link'
|
|
6
|
+
|
|
7
|
+
export type Variant = 'primary'
|
|
8
|
+
|
|
9
|
+
export interface MenuLinkProps
|
|
10
|
+
extends React.AnchorHTMLAttributes<HTMLAnchorElement> {
|
|
11
|
+
title: string
|
|
12
|
+
variant?: Variant
|
|
13
|
+
icon?: IconType
|
|
14
|
+
isActive?: boolean
|
|
15
|
+
href: string
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export function MenuLink({
|
|
19
|
+
variant = 'primary',
|
|
20
|
+
isActive = false,
|
|
21
|
+
className,
|
|
22
|
+
icon,
|
|
23
|
+
title,
|
|
24
|
+
href,
|
|
25
|
+
...props
|
|
26
|
+
}: MenuLinkProps): React.JSX.Element {
|
|
27
|
+
const cssClasses = classNames('menu-item', variant, className, {
|
|
28
|
+
active: isActive,
|
|
29
|
+
})
|
|
30
|
+
|
|
31
|
+
return (
|
|
32
|
+
<li tabIndex={0} role="menuitem">
|
|
33
|
+
<Link href={href} {...props} className={cssClasses}>
|
|
34
|
+
{icon && <Icon name={icon} />}
|
|
35
|
+
<span className="title">{title}</span>
|
|
36
|
+
</Link>
|
|
37
|
+
</li>
|
|
38
|
+
)
|
|
39
|
+
}
|
package/src/atoms/Menu/index.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import React from 'react'
|
|
2
2
|
|
|
3
|
-
import { Menu,
|
|
3
|
+
import { Menu, MenuLink, MenuDropdown } from '../atoms/Menu'
|
|
4
4
|
|
|
5
5
|
const figmaPrimaryDesign = {
|
|
6
6
|
design: {
|
|
@@ -23,11 +23,14 @@ const meta = {
|
|
|
23
23
|
title: {
|
|
24
24
|
description: 'Component title text',
|
|
25
25
|
},
|
|
26
|
-
|
|
27
|
-
description: 'Is the element
|
|
26
|
+
isActive: {
|
|
27
|
+
description: 'Is the element active?',
|
|
28
28
|
},
|
|
29
|
-
|
|
30
|
-
description: '
|
|
29
|
+
href: {
|
|
30
|
+
description: 'link to the page',
|
|
31
|
+
},
|
|
32
|
+
isOpen: {
|
|
33
|
+
description: 'Is the dropdown open?',
|
|
31
34
|
},
|
|
32
35
|
},
|
|
33
36
|
parameters: figmaPrimaryDesign,
|
|
@@ -35,116 +38,29 @@ const meta = {
|
|
|
35
38
|
|
|
36
39
|
export default meta
|
|
37
40
|
|
|
38
|
-
export const
|
|
39
|
-
render: () => (
|
|
40
|
-
<Menu>
|
|
41
|
-
<MenuOption title="Tekken 8" icon="Edit">
|
|
42
|
-
<Menu isDropdown>
|
|
43
|
-
<MenuOption title="Walkthrough" onClick={() => alert('click')} />
|
|
44
|
-
<MenuOption title="Characters" onClick={() => alert('click')} />
|
|
45
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
46
|
-
</Menu>
|
|
47
|
-
</MenuOption>
|
|
48
|
-
<MenuOption
|
|
49
|
-
title="The Legend of Zelda: Tears of the Kingdom"
|
|
50
|
-
icon="Delete"
|
|
51
|
-
onClick={() => alert('click')}
|
|
52
|
-
/>
|
|
53
|
-
<MenuOption
|
|
54
|
-
title="Metal Gear Solid 5: Ground Zeroes + The Phantom Pain"
|
|
55
|
-
icon="Show"
|
|
56
|
-
>
|
|
57
|
-
<Menu isDropdown>
|
|
58
|
-
<MenuOption title="Walkthrough" onClick={() => alert('click')} />
|
|
59
|
-
<MenuOption title="Characters" onClick={() => alert('click')} />
|
|
60
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
61
|
-
</Menu>
|
|
62
|
-
</MenuOption>
|
|
63
|
-
<MenuOption title="Stray" icon="Info" onClick={() => alert('click')} />
|
|
64
|
-
</Menu>
|
|
65
|
-
),
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
export const FirstLevelMenu = {
|
|
69
|
-
render: () => (
|
|
70
|
-
<Menu>
|
|
71
|
-
<MenuOption title="Tekken 8" icon="Edit" onClick={() => alert('click')} />
|
|
72
|
-
<MenuOption
|
|
73
|
-
title="The Legend of Zelda: Tears of the Kingdom"
|
|
74
|
-
icon="Delete"
|
|
75
|
-
onClick={() => alert('click')}
|
|
76
|
-
/>
|
|
77
|
-
<MenuOption
|
|
78
|
-
title="Metal Gear Solid 5: Ground Zeroes + The Phantom Pain"
|
|
79
|
-
icon="Show"
|
|
80
|
-
onClick={() => alert('click')}
|
|
81
|
-
/>
|
|
82
|
-
<MenuOption title="Stray" icon="Info" onClick={() => alert('click')} />
|
|
83
|
-
</Menu>
|
|
84
|
-
),
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
export const MenuWithSecondLevelPreselectedOption = {
|
|
41
|
+
export const MenuWithLinks = {
|
|
88
42
|
render: () => (
|
|
89
43
|
<Menu>
|
|
90
|
-
<
|
|
91
|
-
|
|
92
|
-
<MenuOption title="Walkthrough" onClick={() => alert('click')} />
|
|
93
|
-
<MenuOption
|
|
94
|
-
isSelected
|
|
95
|
-
title="Characters"
|
|
96
|
-
onClick={() => alert('click')}
|
|
97
|
-
/>
|
|
98
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
99
|
-
</Menu>
|
|
100
|
-
</MenuOption>
|
|
101
|
-
<MenuOption
|
|
44
|
+
<MenuLink title="Tekken 8" href="some-link" />
|
|
45
|
+
<MenuLink
|
|
102
46
|
title="The Legend of Zelda: Tears of the Kingdom"
|
|
103
47
|
icon="Delete"
|
|
104
|
-
|
|
48
|
+
href="some-link"
|
|
49
|
+
isActive
|
|
105
50
|
/>
|
|
106
|
-
<
|
|
51
|
+
<MenuLink
|
|
107
52
|
title="Metal Gear Solid 5: Ground Zeroes + The Phantom Pain"
|
|
108
53
|
icon="Show"
|
|
109
|
-
|
|
110
|
-
<Menu isDropdown>
|
|
111
|
-
<MenuOption title="Walkthrough" onClick={() => alert('click')} />
|
|
112
|
-
<MenuOption title="Characters" onClick={() => alert('click')} />
|
|
113
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
114
|
-
</Menu>
|
|
115
|
-
</MenuOption>
|
|
116
|
-
<MenuOption title="Stray" icon="Info" onClick={() => alert('click')} />
|
|
117
|
-
</Menu>
|
|
118
|
-
),
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
export const MenuWithFirstLevelPreselectedOption = {
|
|
122
|
-
render: () => (
|
|
123
|
-
<Menu>
|
|
124
|
-
<MenuOption title="Tekken 8" icon="Edit">
|
|
125
|
-
<Menu isDropdown>
|
|
126
|
-
<MenuOption title="Walkthrough" onClick={() => alert('click')} />
|
|
127
|
-
<MenuOption title="Characters" onClick={() => alert('click')} />
|
|
128
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
129
|
-
</Menu>
|
|
130
|
-
</MenuOption>
|
|
131
|
-
<MenuOption
|
|
132
|
-
isSelected
|
|
133
|
-
title="The Legend of Zelda: Tears of the Kingdom"
|
|
134
|
-
icon="Delete"
|
|
135
|
-
onClick={() => alert('click')}
|
|
54
|
+
href="some-link"
|
|
136
55
|
/>
|
|
137
|
-
<
|
|
138
|
-
title="
|
|
139
|
-
|
|
140
|
-
>
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
</Menu>
|
|
146
|
-
</MenuOption>
|
|
147
|
-
<MenuOption title="Stray" icon="Info" onClick={() => alert('click')} />
|
|
56
|
+
<MenuDropdown title="Open" icon="AddCircle" name="menu" isOpen>
|
|
57
|
+
<MenuLink title="Stray" href="some-link" isActive />
|
|
58
|
+
<MenuLink title="Fallout 3" href="some-link" />
|
|
59
|
+
</MenuDropdown>
|
|
60
|
+
<MenuDropdown title="Close" name="menu">
|
|
61
|
+
<MenuLink title="Dark souls" href="some-link" />
|
|
62
|
+
<MenuLink title="Elder ring" href="some-link" />
|
|
63
|
+
</MenuDropdown>
|
|
148
64
|
</Menu>
|
|
149
65
|
),
|
|
150
66
|
}
|
package/tests/Menu.spec.tsx
CHANGED
|
@@ -1,59 +1,57 @@
|
|
|
1
1
|
import React from 'react'
|
|
2
2
|
import { render } from '@testing-library/react'
|
|
3
3
|
import { Menu } from '@/atoms/Menu/Menu'
|
|
4
|
-
import {
|
|
4
|
+
import { MenuDropdown, MenuLink } from '@/atoms/Menu'
|
|
5
5
|
|
|
6
6
|
describe('Menu', () => {
|
|
7
7
|
it('renders first-level menu', () => {
|
|
8
|
-
const { getByRole, getByText
|
|
8
|
+
const { getByRole, getByText } = render(
|
|
9
9
|
<Menu>
|
|
10
|
-
<
|
|
11
|
-
<
|
|
12
|
-
|
|
10
|
+
<MenuLink title="Tekken 8" icon="Edit" href="#" />
|
|
11
|
+
<MenuLink
|
|
12
|
+
isActive
|
|
13
13
|
title="The Legend of Zelda: Tears of the Kingdom"
|
|
14
14
|
icon="Delete"
|
|
15
|
+
href="#"
|
|
15
16
|
/>
|
|
16
17
|
</Menu>,
|
|
17
18
|
)
|
|
18
19
|
|
|
19
20
|
expect(getByRole('menu')).toHaveClass(`menu primary`)
|
|
20
|
-
expect(
|
|
21
|
+
expect(
|
|
22
|
+
getByRole('link', { name: 'The Legend of Zelda: Tears of the Kingdom' }),
|
|
23
|
+
).toHaveClass(`active`)
|
|
21
24
|
expect(getByText(/Tekken/i)).toBeInTheDocument()
|
|
22
25
|
expect(getByText(/Zelda/i)).toBeInTheDocument()
|
|
23
|
-
expect(
|
|
24
|
-
expect(
|
|
26
|
+
expect(getByRole('img', { name: 'Edit' })).toBeInTheDocument()
|
|
27
|
+
expect(getByRole('img', { name: 'Delete' })).toBeInTheDocument()
|
|
25
28
|
})
|
|
26
29
|
|
|
27
30
|
it('renders second-level menu', () => {
|
|
28
|
-
const { getByText, getAllByRole } = render(
|
|
31
|
+
const { getByText, getAllByRole, getByRole } = render(
|
|
29
32
|
<Menu>
|
|
30
|
-
<
|
|
31
|
-
<
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
onClick={() => alert('click')}
|
|
37
|
-
/>
|
|
38
|
-
<MenuOption title="Story" onClick={() => alert('click')} />
|
|
39
|
-
</Menu>
|
|
40
|
-
</MenuOption>
|
|
41
|
-
<MenuOption
|
|
33
|
+
<MenuDropdown title="Tekken 8" icon="Edit">
|
|
34
|
+
<MenuLink title="Walkthrough" href="#" />
|
|
35
|
+
<MenuLink isActive title="Characters" href="#" />
|
|
36
|
+
<MenuLink title="Story" href="#" />
|
|
37
|
+
</MenuDropdown>
|
|
38
|
+
<MenuLink
|
|
42
39
|
title="The Legend of Zelda: Tears of the Kingdom"
|
|
43
40
|
icon="Delete"
|
|
41
|
+
href="#"
|
|
44
42
|
/>
|
|
45
43
|
</Menu>,
|
|
46
44
|
)
|
|
47
45
|
|
|
48
46
|
expect(getAllByRole('menu').length).toBe(2)
|
|
49
|
-
expect(
|
|
47
|
+
expect(getByRole('link', { name: 'Characters' })).toHaveClass(`active`)
|
|
50
48
|
expect(getByText(/Tekken/i)).toBeInTheDocument()
|
|
51
49
|
expect(getByText(/Walkthrough/i)).toBeInTheDocument()
|
|
52
50
|
expect(getByText(/Characters/i)).toBeInTheDocument()
|
|
53
51
|
expect(getByText(/Story/i)).toBeInTheDocument()
|
|
54
52
|
expect(getByText(/Zelda/i)).toBeInTheDocument()
|
|
55
|
-
expect(
|
|
56
|
-
expect(
|
|
57
|
-
expect(
|
|
53
|
+
expect(getByRole('img', { name: 'Edit' })).toBeInTheDocument()
|
|
54
|
+
expect(getByRole('img', { name: 'AngleDown' })).toBeInTheDocument()
|
|
55
|
+
expect(getByRole('img', { name: 'Delete' })).toBeInTheDocument()
|
|
58
56
|
})
|
|
59
57
|
})
|
|
@@ -1,79 +0,0 @@
|
|
|
1
|
-
import './Menu.scss'
|
|
2
|
-
import React from 'react'
|
|
3
|
-
import { Icon, IconType } from '../Icon'
|
|
4
|
-
import { classNames } from '../../utils/classNames'
|
|
5
|
-
|
|
6
|
-
export type Variant = 'primary'
|
|
7
|
-
|
|
8
|
-
export interface MenuOptionProps extends React.ComponentPropsWithoutRef<'li'> {
|
|
9
|
-
variant?: Variant
|
|
10
|
-
icon?: IconType
|
|
11
|
-
title: string
|
|
12
|
-
isSelected?: boolean
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
export function MenuOption({
|
|
16
|
-
variant = 'primary',
|
|
17
|
-
className,
|
|
18
|
-
isSelected = false,
|
|
19
|
-
icon,
|
|
20
|
-
title,
|
|
21
|
-
children,
|
|
22
|
-
onClick,
|
|
23
|
-
...props
|
|
24
|
-
}: MenuOptionProps): React.JSX.Element {
|
|
25
|
-
const cssClasses = classNames('menu-option', variant, className, {
|
|
26
|
-
selected: isSelected,
|
|
27
|
-
})
|
|
28
|
-
|
|
29
|
-
function closePreviousSelectedDropdown(currentTarget: HTMLLIElement) {
|
|
30
|
-
document.querySelectorAll('details[open]').forEach((detailElement) => {
|
|
31
|
-
const firstLevelMenuOption = detailElement?.closest('li')
|
|
32
|
-
const currentFirstLevelMenuOption = currentTarget
|
|
33
|
-
?.closest('details')
|
|
34
|
-
?.closest('li')
|
|
35
|
-
|
|
36
|
-
if (firstLevelMenuOption !== currentFirstLevelMenuOption)
|
|
37
|
-
detailElement.removeAttribute('open')
|
|
38
|
-
})
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
function unselectPreviousOption() {
|
|
42
|
-
document
|
|
43
|
-
.querySelectorAll('.selected')
|
|
44
|
-
.forEach((option) => option.classList.remove('selected'))
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
function setOptionSelected(event: React.MouseEvent<HTMLLIElement>) {
|
|
48
|
-
event.stopPropagation()
|
|
49
|
-
|
|
50
|
-
closePreviousSelectedDropdown(event.currentTarget)
|
|
51
|
-
unselectPreviousOption()
|
|
52
|
-
|
|
53
|
-
event.currentTarget.classList.add('selected')
|
|
54
|
-
if (onClick) onClick(event)
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
return (
|
|
58
|
-
<li
|
|
59
|
-
className={cssClasses}
|
|
60
|
-
tabIndex={0}
|
|
61
|
-
role="menuitem"
|
|
62
|
-
onClick={setOptionSelected}
|
|
63
|
-
{...props}
|
|
64
|
-
>
|
|
65
|
-
<details open={isSelected}>
|
|
66
|
-
<summary className="container">
|
|
67
|
-
<div className="left">
|
|
68
|
-
{icon && <Icon name={icon} />}
|
|
69
|
-
<span className="title">{title}</span>
|
|
70
|
-
</div>
|
|
71
|
-
<div className="right">
|
|
72
|
-
<Icon name="AngleDown" />
|
|
73
|
-
</div>
|
|
74
|
-
</summary>
|
|
75
|
-
{children}
|
|
76
|
-
</details>
|
|
77
|
-
</li>
|
|
78
|
-
)
|
|
79
|
-
}
|