@hashicorp/react-components 0.0.0-nightly.48bfabb → 0.0.0-nightly.52c0d39

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.
Files changed (76) hide show
  1. package/package.json +4 -3
  2. package/src/components/actions/index.tsx +5 -5
  3. package/src/components/call-to-action/index.tsx +7 -7
  4. package/src/components/card/index.test.tsx +1 -1
  5. package/src/components/card/newsroom-card/index.test.tsx +1 -1
  6. package/src/components/card/partner-card/index.tsx +3 -3
  7. package/src/components/card/person-card/index.tsx +1 -1
  8. package/src/components/card/primitives.tsx +16 -15
  9. package/src/components/card/resource-card/index.test.tsx +1 -1
  10. package/src/components/card/resource-card/index.tsx +3 -0
  11. package/src/components/card/types.ts +2 -2
  12. package/src/components/card/unified-card/index.spec.tsx +40 -0
  13. package/src/components/card/unified-card/index.tsx +5 -11
  14. package/src/components/marketo-form/contexts/FormMetadata.ts +2 -0
  15. package/src/components/marketo-form/form/index.tsx +4 -2
  16. package/src/components/marketo-form/partials/fields/checkbox-field/index.tsx +1 -1
  17. package/src/components/marketo-form/partials/fields/email-field/index.tsx +1 -1
  18. package/src/components/marketo-form/partials/fields/form-page-url-field/index.tsx +12 -1
  19. package/src/components/marketo-form/partials/fields/hidden-field/index.tsx +1 -0
  20. package/src/components/marketo-form/partials/fields/radio-buttons-field/index.tsx +1 -1
  21. package/src/components/marketo-form/partials/fields/select-field/index.tsx +1 -1
  22. package/src/components/marketo-form/partials/fields/telephone-field/index.tsx +1 -1
  23. package/src/components/marketo-form/partials/fields/text-field/index.tsx +1 -1
  24. package/src/components/marketo-form/partials/fields/textarea-field/index.tsx +1 -1
  25. package/src/components/marketo-form/types.ts +5 -11
  26. package/src/components/nav-panel/components/link-list/index.tsx +15 -9
  27. package/src/components/nav-panel/components/promo/index.tsx +12 -9
  28. package/src/components/nav-panel/product-panel/index.tsx +12 -7
  29. package/src/components/nav-panel/standard-panel/index.tsx +3 -0
  30. package/src/components/next-steps/index.tsx +3 -2
  31. package/src/components/product-badge/index.tsx +1 -1
  32. package/src/components/subnav/index.tsx +13 -3
  33. package/src/components/subnav/partials/CtaLinks/github-stars-link/style.module.css +8 -12
  34. package/src/components/subnav/partials/CtaLinks/index.tsx +9 -8
  35. package/src/components/subnav/partials/CtaLinks/style.module.css +4 -4
  36. package/src/components/subnav/partials/DropdownTrigger/index.tsx +2 -2
  37. package/src/components/subnav/partials/DropdownTrigger/style.module.css +7 -4
  38. package/src/components/subnav/partials/MenuItemsDefault/index.tsx +30 -8
  39. package/src/components/subnav/partials/MenuItemsDefault/style.module.css +37 -24
  40. package/src/components/subnav/partials/MenuItemsOverflow/index.tsx +20 -4
  41. package/src/components/subnav/partials/MenuItemsOverflow/style.module.css +22 -16
  42. package/src/components/subnav/partials/TitleLink/index.tsx +6 -4
  43. package/src/components/subnav/partials/TitleLink/style.module.css +1 -1
  44. package/src/components/subnav/partials/nav-item-text/style.module.css +2 -4
  45. package/src/components/subnav/style.module.css +4 -6
  46. package/src/lib/get-localized-link-props/index.test.ts +30 -0
  47. package/src/lib/get-localized-link-props/index.ts +46 -0
  48. package/src/lib/parse-url/index.test.ts +40 -1
  49. package/src/lib/parse-url/index.ts +83 -11
  50. package/src/lib/supported-locales/index.ts +1 -0
  51. package/src/lib/v/index.ts +4 -5
  52. package/src/components/consent-manager/README.md +0 -73
  53. package/src/components/consent-manager/components/banner/banner.module.css +0 -23
  54. package/src/components/consent-manager/components/banner/banner.test.tsx +0 -31
  55. package/src/components/consent-manager/components/banner/banner.tsx +0 -73
  56. package/src/components/consent-manager/components/dialog/dialog.module.css +0 -145
  57. package/src/components/consent-manager/components/dialog/dialog.test.tsx +0 -194
  58. package/src/components/consent-manager/components/dialog/dialog.tsx +0 -339
  59. package/src/components/consent-manager/img/icn_close.tsx +0 -19
  60. package/src/components/consent-manager/index.test.tsx +0 -334
  61. package/src/components/consent-manager/index.tsx +0 -186
  62. package/src/components/consent-manager/loader/README.md +0 -29
  63. package/src/components/consent-manager/loader/categories.ts +0 -22
  64. package/src/components/consent-manager/loader/index.tsx +0 -94
  65. package/src/components/consent-manager/loader/presets/enterprise.ts +0 -12
  66. package/src/components/consent-manager/loader/presets/oss.ts +0 -10
  67. package/src/components/consent-manager/loader/services.ts +0 -45
  68. package/src/components/consent-manager/scripts/custom.tsx +0 -59
  69. package/src/components/consent-manager/scripts/segment.tsx +0 -87
  70. package/src/components/consent-manager/style.module.css +0 -9
  71. package/src/components/consent-manager/types.ts +0 -55
  72. package/src/components/consent-manager/util/cookies.test.ts +0 -75
  73. package/src/components/consent-manager/util/cookies.ts +0 -70
  74. package/src/components/consent-manager/util/integrations.test.ts +0 -115
  75. package/src/components/consent-manager/util/integrations.ts +0 -110
  76. package/src/components/subnav/theme.module.css +0 -50
@@ -1,14 +1,15 @@
1
1
  import { useCallback } from 'react'
2
2
  import classNames from 'classnames'
3
- import { v } from '../../../../lib/v'
3
+ import { vercelSplit } from '../../../../lib/v'
4
4
  import Link from 'next/link'
5
- import { parseUrl } from '../../../../lib/parse-url'
5
+ import { getLocalizedLinkProps } from '../../../../lib/get-localized-link-props'
6
6
  import { trackNavClickEvent } from '../../../../lib/track-nav-click-event'
7
- import FlightIcon from '@hashicorp/react-design-system-components/src/components/flight-icon'
7
+ import FlightIcon from '@hashicorp/react-hds/src/components/flight-icon'
8
8
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
9
9
  import s from './style.module.css'
10
10
 
11
11
  export interface PromoProps {
12
+ locale?: string
12
13
  title: string
13
14
  description: string
14
15
  linkUrl: string
@@ -20,6 +21,7 @@ export interface PromoProps {
20
21
  }
21
22
 
22
23
  export default function Promo({
24
+ locale,
23
25
  title,
24
26
  description,
25
27
  linkUrl,
@@ -51,19 +53,19 @@ export default function Promo({
51
53
  {icon && (
52
54
  <div
53
55
  className={classNames(s.icon, {
54
- [s.hashidays]: v(theme) === 'hashidays',
55
- [s.hashiconf]: v(theme) === 'hashiconf',
56
+ [s.hashidays]: vercelSplit(theme) === 'hashidays',
57
+ [s.hashiconf]: vercelSplit(theme) === 'hashiconf',
56
58
  })}
57
59
  >
58
- <FlightIcon name={v(icon)} />
60
+ <FlightIcon name={vercelSplit(icon)} />
59
61
  </div>
60
62
  )}
61
63
  <div className={s.rightContent}>
62
64
  <div>
63
65
  <div
64
66
  className={classNames(s.title, {
65
- [s.hashidays]: v(theme) === 'hashidays',
66
- [s.hashiconf]: v(theme) === 'hashiconf',
67
+ [s.hashidays]: vercelSplit(theme) === 'hashidays',
68
+ [s.hashiconf]: vercelSplit(theme) === 'hashiconf',
67
69
  })}
68
70
  >
69
71
  {title}
@@ -72,7 +74,8 @@ export default function Promo({
72
74
  </div>
73
75
  <NavigationMenu.Link asChild>
74
76
  <Link
75
- href={parseUrl(linkUrl).href}
77
+ locale={locale ? locale : undefined}
78
+ {...getLocalizedLinkProps(linkUrl, locale)}
76
79
  className={s.link}
77
80
  onClickCapture={() => handleClick(title, linkUrl, linkTitle, slug)}
78
81
  >
@@ -2,10 +2,10 @@ import classNames from 'classnames'
2
2
  import Link from 'next/link'
3
3
  import * as NavPanel from '../components/panel'
4
4
  import Promo, { type PromoProps } from '../components/promo'
5
+ import { getLocalizedLinkProps } from '../../../lib/get-localized-link-props'
5
6
  import { Products } from '@hashicorp/platform-product-meta'
6
- import FlightIcon from '@hashicorp/react-design-system-components/src/components/flight-icon'
7
- import { TextPlus } from '@hashicorp/react-design-system-components/src/components/text'
8
- import { parseUrl } from '../../../lib/parse-url'
7
+ import FlightIcon from '@hashicorp/react-hds/src/components/flight-icon'
8
+ import { TextPlus } from '@hashicorp/react-hds/src/components/text'
9
9
  import { trackNavClickEvent } from '../../../lib/track-nav-click-event'
10
10
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
11
11
  import s from './style.module.css'
@@ -30,6 +30,7 @@ const PRODUCT_LOGO_EXCEPTION_CLASSNAMES = {
30
30
  }
31
31
 
32
32
  export interface ProductsPanelProps {
33
+ locale: string
33
34
  productCategories: any
34
35
  promo?: PromoProps
35
36
  sidePanel?: {
@@ -44,6 +45,7 @@ export interface ProductsPanelProps {
44
45
  }
45
46
 
46
47
  const ProductPanel = ({
48
+ locale,
47
49
  productCategories,
48
50
  promo,
49
51
  sidePanel,
@@ -67,7 +69,7 @@ const ProductPanel = ({
67
69
  {products.map((product) => {
68
70
  return (
69
71
  <li key={product.url}>
70
- <NavProduct {...product} />
72
+ <NavProduct locale={locale} {...product} />
71
73
  </li>
72
74
  )
73
75
  })}
@@ -97,7 +99,8 @@ const ProductPanel = ({
97
99
  <li key={title}>
98
100
  <Link
99
101
  aria-label={`${title} - ${description}`}
100
- href={parseUrl(url).href}
102
+ {...getLocalizedLinkProps(url, locale)}
103
+ locale={locale ? locale : undefined}
101
104
  className={classNames(s.sidePanelItem, s.focusIndicator)}
102
105
  >
103
106
  <div className={s.iconBackground}>
@@ -125,17 +128,19 @@ const ProductPanel = ({
125
128
  }
126
129
 
127
130
  export interface NavProductProps {
131
+ locale?: string
128
132
  url: string
129
133
  product: Products | string
130
134
  description: string
131
135
  }
132
136
 
133
- function NavProduct({ url, product, description }: NavProductProps) {
137
+ function NavProduct({ locale, url, product, description }: NavProductProps) {
134
138
  return (
135
139
  <NavigationMenu.Link asChild>
136
140
  <Link
137
141
  aria-label={`${product} - ${description}`}
138
- href={parseUrl(url).href}
142
+ {...getLocalizedLinkProps(url, locale)}
143
+ locale={locale ? locale : undefined}
139
144
  onClickCapture={() => {
140
145
  trackNavClickEvent(product, url, 'products')
141
146
  }}
@@ -12,12 +12,14 @@ interface StandardPanelProps {
12
12
  navData: NavItem[]
13
13
  promo?: PromoProps
14
14
  sectionName?: string
15
+ locale?: any
15
16
  }
16
17
 
17
18
  const StandardPanel = ({
18
19
  navData,
19
20
  promo,
20
21
  sectionName = '',
22
+ locale,
21
23
  }: StandardPanelProps) => {
22
24
  return (
23
25
  <NavPanel.Root>
@@ -26,6 +28,7 @@ const StandardPanel = ({
26
28
  return (
27
29
  <NavPanel.Column key={stableIdx}>
28
30
  <LinkList
31
+ locale={locale}
29
32
  links={navItems}
30
33
  linkClickHandler={(text, href) => {
31
34
  trackNavClickEvent(text, href, sectionName)
@@ -2,6 +2,7 @@
2
2
  * Copyright (c) HashiCorp, Inc.
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
+ 'use client'
5
6
 
6
7
  import { useState } from 'react'
7
8
  import Badge from '@hashicorp/react-badge'
@@ -10,7 +11,7 @@ import ExpandableArrow from '@hashicorp/react-expandable-arrow'
10
11
  import Intro from '../intro'
11
12
  import Link from 'next/link'
12
13
  import type { NextStepsProps } from './types'
13
- import StandaloneLink from '@hashicorp/react-design-system-components/src/components/standalone-link'
14
+ import { HDSPlusStandaloneLink } from '@hashicorp/react-mds/src/hds-plus/standalone-link'
14
15
  import { IconArrowRight16 } from '@hashicorp/flight-icons/svg-react/arrow-right-16'
15
16
  import useProductMeta from '@hashicorp/platform-product-meta'
16
17
  import s from './style.module.css'
@@ -69,7 +70,7 @@ export default function NextSteps({
69
70
  {cta ? (
70
71
  <div className={s.cta}>
71
72
  <p className={s.ctaCopy}>{cta.copy}</p>
72
- <StandaloneLink
73
+ <HDSPlusStandaloneLink
73
74
  href={cta.href}
74
75
  text={cta.ctaText}
75
76
  icon={
@@ -4,7 +4,7 @@
4
4
  */
5
5
 
6
6
  import type { Products } from '@hashicorp/platform-product-meta'
7
- import Badge from '@hashicorp/react-design-system-components/src/components/badge'
7
+ import Badge from '@hashicorp/react-hds/src/components/badge'
8
8
  import { IconDot16 } from '@hashicorp/flight-icons/svg-react/dot-16'
9
9
  import s from './style.module.css'
10
10
 
@@ -17,7 +17,6 @@ import CtaLinks, { type CtaLinkProps } from './partials/CtaLinks'
17
17
  import traverse, { isObject } from './helpers/traverse'
18
18
  import { areBasePathsMatching } from './helpers/areBasePathsMatching'
19
19
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
20
- import themeStyles from './theme.module.css'
21
20
  import s from './style.module.css'
22
21
 
23
22
  const productAllowList = {
@@ -47,6 +46,7 @@ type SubnavDropdown = {
47
46
  type MenuItem = SubnavLink | SubnavDropdown | 'divider'
48
47
 
49
48
  export interface SubnavInnerProps {
49
+ locale?: string
50
50
  hasOverflow?: boolean
51
51
  titleLink: { text: string; url: string }
52
52
  product?: Products
@@ -62,6 +62,7 @@ export interface SubnavInnerProps {
62
62
  }
63
63
 
64
64
  function SubnavInner({
65
+ locale,
65
66
  hasOverflow,
66
67
  titleLink,
67
68
  product,
@@ -110,17 +111,21 @@ function SubnavInner({
110
111
  >
111
112
  <NavigationMenu.Link asChild>
112
113
  <TitleLink
114
+ locale={locale}
113
115
  text={titleLink.text}
114
116
  url={titleLink.url}
115
117
  product={product}
116
118
  theme={theme}
117
119
  />
118
120
  </NavigationMenu.Link>
121
+
119
122
  {!hasOverflow && (
120
123
  <div className={s.subNavRight}>
121
124
  <MenuItemsDefault
122
125
  menuItems={menuItemsWithActive}
123
126
  activatePanel={activatePanel}
127
+ locale={locale}
128
+ product={product}
124
129
  />
125
130
  {ctaLinks?.length > 0 && (
126
131
  <CtaLinks
@@ -165,6 +170,10 @@ function Subnav({ className, theme = 'light', ...restProps }: SubnavProps) {
165
170
  setActivePanel(panel)
166
171
  }
167
172
 
173
+ const ariaLabel = restProps?.titleLink?.text
174
+ ? `${restProps.titleLink.text} pages`
175
+ : 'Subnav pages'
176
+
168
177
  return (
169
178
  <>
170
179
  {/**
@@ -175,11 +184,12 @@ function Subnav({ className, theme = 'light', ...restProps }: SubnavProps) {
175
184
  <style>{`:root{--subnav-height:${height}px}`}</style>
176
185
  <NavigationMenu.Root
177
186
  ref={wrapperRef}
178
- className={classNames(s.root, themeStyles[theme], className, {
187
+ className={classNames(s.root, className, {
179
188
  [s.isSticky]: isSticky,
180
189
  [s.hasOverflow]: hasOverflow,
190
+ 'hdsplus-dark-mode': theme === 'dark',
181
191
  })}
182
- aria-label={`${product} website navigation`}
192
+ aria-label={ariaLabel}
183
193
  onValueChange={activatePanel}
184
194
  value={activePanel}
185
195
  delayDuration={0}
@@ -3,15 +3,13 @@
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
5
 
6
- /* Note: consumes from theme.module.css, as marked */
7
-
8
6
  .root {
9
- --local-scrim-color: transparent;
10
- --local-divider-color: var(--border-color); /* from theme.module.css */
7
+ --local-scrim-opacity: 0;
8
+ --local-divider-color: var(--token-color-border-primary);
11
9
 
12
10
  position: relative;
13
- color: var(--gh-stars-icon-color); /* from theme.module.css */
14
- border: 1px solid var(--local-divider-color); /* from theme.module.css */
11
+ color: var(--token-color-foreground-primary);
12
+ border: 1px solid var(--local-divider-color);
15
13
  border-radius: 5px;
16
14
  background: none;
17
15
  transition: background 0.2s, border-color 0.2s;
@@ -27,17 +25,15 @@
27
25
  right: -1px;
28
26
  bottom: -1px;
29
27
  border-radius: 5px;
30
- transition: background 0.25s ease;
28
+ transition: opacity 0.25s ease;
29
+ opacity: var(--local-scrim-opacity);
31
30
  z-index: 0;
32
- background-color: var(--local-scrim-color);
31
+ background-color: var(--token-color-foreground-primary);
33
32
  }
34
33
 
35
34
  &:hover,
36
35
  &:active {
37
- --local-divider-color: transparent;
38
- --local-scrim-color: var(
39
- --gh-stars-scrim-color
40
- ); /* from theme.module.css */
36
+ --local-scrim-opacity: 0.12;
41
37
  }
42
38
  }
43
39
 
@@ -3,19 +3,20 @@
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
5
 
6
- import Button, {
7
- type ButtonProps,
8
- } from '@hashicorp/react-design-system-components/src/components/button'
9
- import FlightIcon from '@hashicorp/react-design-system-components/src/components/flight-icon'
6
+ import {
7
+ HDSPlusButton,
8
+ type HDSPlusButtonProps,
9
+ } from '@hashicorp/react-mds/src/hds-plus/button'
10
+ import FlightIcon from '@hashicorp/react-hds/src/components/flight-icon'
10
11
  import type { Products } from '@hashicorp/platform-product-meta'
11
- import type { ToggleButtonProps } from '@hashicorp/react-design-system-components/src/components/dropdown/toggle/button'
12
- import * as Dropdown from '@hashicorp/react-design-system-components/src/components/dropdown'
12
+ import type { ToggleButtonProps } from '@hashicorp/react-hds/src/components/dropdown/toggle/button'
13
+ import * as Dropdown from '@hashicorp/react-hds/src/components/dropdown'
13
14
  import GithubStarsLink from './github-stars-link'
14
15
  import classNames from 'classnames'
15
16
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
16
17
  import s from './style.module.css'
17
18
 
18
- type CtaLink = ButtonProps & { href: string; __typename?: string }
19
+ type CtaLink = HDSPlusButtonProps & { href: string; __typename?: string }
19
20
 
20
21
  type CtaDropdown = {
21
22
  __typename?: string
@@ -83,7 +84,7 @@ function CtaLinks({
83
84
  const isLastButton = stableIdx === links.length - 1
84
85
 
85
86
  return (
86
- <Button
87
+ <HDSPlusButton
87
88
  key={href}
88
89
  text={text}
89
90
  href={href}
@@ -10,26 +10,26 @@
10
10
  list-style: none;
11
11
  padding: 0 0 0 var(--hdsplus-spacing-05);
12
12
  margin: 0;
13
- gap: 0 12px;
13
+ gap: 0 var(--hdsplus-spacing-04);
14
14
  @media (--medium-up) {
15
15
  gap: 0;
16
16
  }
17
17
 
18
18
  & > * + * {
19
19
  /* Spaces consecutive buttons horizontally on desktop */
20
- margin-left: 16px;
20
+ margin-left: var(--hdsplus-spacing-05);
21
21
  }
22
22
 
23
23
  &.isInDropdown {
24
24
  /* Allows consecutive buttons to wrap */
25
25
  flex-wrap: wrap;
26
26
  white-space: wrap;
27
- padding-left: 0;
27
+ padding-inline: var(--hdsplus-spacing-04);
28
28
 
29
29
  & > * {
30
30
  /* Spaces consecutive buttons vertically */
31
31
  margin-left: 0;
32
- margin-top: 16px;
32
+ margin-top: var(--hdsplus-spacing-05);
33
33
 
34
34
  &:last-of-type {
35
35
  margin-bottom: var(--hdsplus-spacing-04);
@@ -3,7 +3,7 @@
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
5
 
6
- import FlightIcon from '@hashicorp/react-design-system-components/src/components/flight-icon'
6
+ import FlightIcon from '@hashicorp/react-hds/src/components/flight-icon'
7
7
  import NavItemText from '../nav-item-text'
8
8
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
9
9
  import s from './style.module.css'
@@ -27,7 +27,7 @@ function DropdownTrigger(props: DropdownTriggerProps) {
27
27
  onMouseDown={(e) => e.preventDefault()}
28
28
  >
29
29
  <NavItemText isActive={isActive} text={text} />
30
- <FlightIcon name="chevron-down" color="var(--menu-item-text-color)" />
30
+ <FlightIcon name="chevron-down" />
31
31
  </NavigationMenu.Trigger>
32
32
  )
33
33
  }
@@ -3,8 +3,6 @@
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
5
 
6
- /* Note: consumes from theme.module.css, as marked */
7
-
8
6
  .root {
9
7
  composes: hds-typography-body-200 from global;
10
8
  composes: hds-font-weight-medium from global;
@@ -26,11 +24,16 @@
26
24
  width: 12px;
27
25
  height: 12px;
28
26
  transition: transform 0.3s;
29
- fill: var(--menu-item-text-color); /* from theme.module.css */
27
+ fill: var(--token-color-foreground-primary);
30
28
  }
31
29
 
32
30
  &:hover {
33
- background-color: var(--menu-item-hover-color);
31
+ background-color: var(--token-color-surface-interactive-hover);
34
32
  border-radius: var(--hdsplus-spacing-01);
35
33
  }
34
+
35
+ &:focus {
36
+ outline: 2px solid var(--token-color-focus-action-internal);
37
+ outline-style: auto;
38
+ }
36
39
  }
@@ -9,22 +9,31 @@ import NavItemText from '../nav-item-text'
9
9
  import DropdownTrigger from '../DropdownTrigger'
10
10
  import * as NavigationMenu from '@radix-ui/react-navigation-menu'
11
11
  import s from './style.module.css'
12
+ import FlightIcon from '@hashicorp/react-hds/src/components/flight-icon'
13
+ import { getLocalizedLinkProps } from '../../../../lib/get-localized-link-props'
12
14
 
13
15
  interface MenuItemsDefaultProps {
14
16
  menuItems: (
15
17
  | {
16
18
  text: string
17
19
  url: string
18
- submenu: { text: string; url: string; _isActiveUrl: string }[]
20
+ submenu: {
21
+ icon: string
22
+ text: string
23
+ url: string
24
+ _isActiveUrl: string
25
+ }[]
19
26
  _isActiveUrl: boolean
20
27
  }
21
28
  | 'divider'
22
29
  )[]
23
30
  activatePanel: (panel: string) => void
31
+ locale?: string
32
+ product?: string
24
33
  }
25
34
 
26
35
  function MenuItemsDefault(props: MenuItemsDefaultProps) {
27
- const { menuItems, activatePanel } = props
36
+ const { menuItems, activatePanel, locale, product } = props
28
37
  return (
29
38
  <NavigationMenu.List className={s.root}>
30
39
  {menuItems.map((menuItem, stableIdx) => {
@@ -41,6 +50,7 @@ function MenuItemsDefault(props: MenuItemsDefaultProps) {
41
50
  text={text}
42
51
  submenu={submenu}
43
52
  activatePanel={activatePanel}
53
+ locale={locale}
44
54
  />
45
55
  ) : (
46
56
  <NavLink
@@ -50,6 +60,8 @@ function MenuItemsDefault(props: MenuItemsDefaultProps) {
50
60
  text={text}
51
61
  url={url}
52
62
  isActive={_isActiveUrl}
63
+ locale={locale}
64
+ product={product}
53
65
  />
54
66
  )
55
67
  })}
@@ -69,14 +81,19 @@ interface NavLinkProps {
69
81
  text: string
70
82
  url: string
71
83
  isActive: boolean
84
+ locale?: string
85
+ product?: string
72
86
  }
73
87
 
74
88
  function NavLink(props: NavLinkProps) {
75
- const { text, url, isActive } = props
89
+ const { text, url, isActive, locale, product } = props
76
90
  return (
77
91
  <NavigationMenu.Item className={s.listItem}>
78
92
  <NavigationMenu.Link asChild>
79
- <Link className={s.navLink} href={url}>
93
+ <Link
94
+ className={s.navLink}
95
+ {...getLocalizedLinkProps(url, locale, Boolean(product))}
96
+ >
80
97
  <NavItemText isActive={isActive} text={text} />
81
98
  </Link>
82
99
  </NavigationMenu.Link>
@@ -86,8 +103,9 @@ function NavLink(props: NavLinkProps) {
86
103
 
87
104
  interface NavLinkWithDropdownProps {
88
105
  text: string
89
- submenu: { text: string; url: string; _isActiveUrl: string }[]
106
+ submenu: { icon: string; text: string; url: string; _isActiveUrl: string }[]
90
107
  activatePanel: (panel: string) => void
108
+ locale?: string
91
109
  }
92
110
 
93
111
  interface NavLinkWithDropdownState {
@@ -99,7 +117,7 @@ class NavLinkWithDropdown extends React.Component<
99
117
  NavLinkWithDropdownState
100
118
  > {
101
119
  render() {
102
- const { text, submenu, activatePanel } = this.props
120
+ const { text, submenu, activatePanel, locale } = this.props
103
121
  const hasActiveChild = submenu.some((s) => s._isActiveUrl)
104
122
 
105
123
  const handleFocusOutside = () => {
@@ -128,12 +146,16 @@ class NavLinkWithDropdown extends React.Component<
128
146
  <NavigationMenu.Sub>
129
147
  <NavigationMenu.List className={s.dropdownList}>
130
148
  {submenu.map((submenuItem, stableIdx) => {
131
- const { text, url } = submenuItem
149
+ const { icon, text, url } = submenuItem
132
150
  return (
133
151
  // eslint-disable-next-line react/no-array-index-key
134
152
  <NavigationMenu.Item key={stableIdx}>
135
153
  <NavigationMenu.Link asChild>
136
- <Link className={s.submenuItem} href={url}>
154
+ <Link
155
+ className={s.submenuItem}
156
+ {...getLocalizedLinkProps(url, locale)}
157
+ >
158
+ {icon ? <FlightIcon name={icon} /> : null}
137
159
  {text}
138
160
  </Link>
139
161
  </NavigationMenu.Link>
@@ -3,8 +3,6 @@
3
3
  * SPDX-License-Identifier: MPL-2.0
4
4
  */
5
5
 
6
- /* Note: consumes from theme.module.css, as marked */
7
-
8
6
  .root {
9
7
  display: flex;
10
8
  padding: 0 0 0 var(--hdsplus-spacing-08);
@@ -16,7 +14,6 @@
16
14
 
17
15
  .listItem {
18
16
  position: relative;
19
- white-space: nowrap;
20
17
  margin: 0;
21
18
  padding: 0;
22
19
  }
@@ -31,7 +28,7 @@
31
28
  white-space: nowrap;
32
29
 
33
30
  &:hover {
34
- background-color: var(--menu-item-hover-color);
31
+ background-color: var(--token-color-surface-interactive-hover);
35
32
  border-radius: var(--hdsplus-spacing-01);
36
33
  }
37
34
 
@@ -42,43 +39,58 @@
42
39
  }
43
40
 
44
41
  .submenuItem {
42
+ --submenu-item-background-color: transparent;
43
+
44
+ position: relative;
45
45
  composes: hds-typography-body-200 from global;
46
46
  composes: hds-font-weight-medium from global;
47
- display: block;
48
- color: var(--menu-item-text-color); /* from theme.module.css */
47
+ color: var(--token-color-foreground-primary);
48
+ display: flex;
49
+ gap: var(--hdsplus-spacing-04);
50
+ padding: var(--hdsplus-spacing-03);
51
+ min-width: 190px;
52
+ align-items: center;
53
+
54
+ &::before {
55
+ content: "";
56
+ position: absolute;
57
+ z-index: -1;
58
+ inset: 2px 0;
59
+ border-radius: var(--hdsplus-spacing-01);
60
+ background-color: var(--submenu-item-background-color);
61
+ }
49
62
 
50
63
  &:hover {
51
- text-decoration: underline;
64
+ --submenu-item-background-color: var(--token-color-surface-interactive-hover);
65
+ }
66
+
67
+ @media (--large) {
68
+ max-width: 416px;
69
+ }
70
+
71
+ &:focus {
72
+ outline: 2px solid var(--token-color-focus-action-internal);
73
+ outline-style: auto;
52
74
  }
53
75
  }
54
76
 
55
77
  .submenuModal {
56
- border-radius: 4px;
57
- box-shadow: var(--token-elevation-high-box-shadow); /* from theme.module.css */
58
- background: var(--dropdown-background-color); /* from theme.module.css */
78
+ border-radius: var(--hdsplus-spacing-03);
79
+ border: 1px solid var(--token-color-border-primary);
80
+ box-shadow: var(--token-elevation-high-box-shadow);
81
+ background: var(--token-color-surface-primary);
59
82
  z-index: 1;
60
- display: block;
61
83
  position: absolute;
62
84
  top: 100%;
63
- margin: 8px 0 0 0;
64
- padding: 24px;
85
+ margin: var(--hdsplus-spacing-03) 0 0 0;
86
+ padding: var(--hdsplus-spacing-04);
65
87
  left: 100%;
66
88
  transform: translateX(-100%);
67
89
  list-style: none;
68
-
69
- & li {
70
- & a:hover .text {
71
- text-decoration: underline;
72
- }
73
-
74
- & + li {
75
- margin-top: 6px;
76
- }
77
- }
78
90
  }
79
91
 
80
92
  .verticalDivider {
81
- background: var(--border-color); /* from theme.module.css */
93
+ background: var(--token-color-border-primary);
82
94
  height: 1.75rem;
83
95
  width: 1px;
84
96
  margin: 0 8px;
@@ -86,6 +98,7 @@
86
98
  }
87
99
 
88
100
  .dropdownList {
101
+ min-width: max-content;
89
102
  list-style: none;
90
103
  padding: 0;
91
104
  }