Skip to content

Commit

Permalink
refactor: Add new dropdown to non-generic pages (#2568)
Browse files Browse the repository at this point in the history
* refactor: Add product panel to tutorials pages

- Move `left` alignment of dropdowns exclusively into desktop dropdown pane
- Add `NavBarListContainer` to tutorials dropdown wrapping to satisfy Radix

* chore: More-reasonable wrapping setup

* chore: Change menu on tutorials library

* Revert "chore: Change menu on tutorials library"

This reverts commit 393b625.

* fix: add left padding on product pages

* Reapply "chore: Change menu on tutorials library"

This reverts commit 46a6c5d.

* fix: Padding on mobile for sidebars

* add mobile menu to profile page

* add product panel to products pages main menu

* fix: Sticky auth controls on sidebar-sidecar layout

* fix padding

* fix: Restore resources in product sidebars

* fix padding and margin

* fix desktop padding

* chore(SidebarNavList): Use NativeDivElement type for props

Co-authored-by: Heat Hamilton <[email protected]>

* fix: Mobile menu cutoff

* fix: Only apply that height change on mobile

* chore: Use inline JSX.IntrinsicElements['div'] type over explicit className type

---------

Co-authored-by: Leah Bush <[email protected]>
Co-authored-by: Heat Hamilton <[email protected]>
  • Loading branch information
3 people committed Sep 13, 2024
1 parent 540f84d commit 05ff87c
Show file tree
Hide file tree
Showing 14 changed files with 141 additions and 49 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
z-index: 2;
@media (--dev-dot-show-mobile-menu) {
top: auto;
height: calc(100% - var(--sticky-bars-height));
}
@media (--dev-dot-hide-mobile-menu) {
top: var(--sticky-bars-height);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,6 @@
box-shadow: var(--token-elevation-higher-box-shadow);
min-width: max-content;
position: absolute;
left: -216px;
}

.dropdownContainerInner {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,3 +29,7 @@
}
}
}

.homepageDropdownPane {
left: -216px;
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ const HomePageHeaderContent = () => {
<NavBarListContainer>
<li>
<NavigationHeaderDropdownMenu
dropdownClassName={s.homepageDropdownPane}
productPanelData={{
navigationData,
navPromo,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import { IconHashicorp24 } from '@hashicorp/flight-icons/svg-react/hashicorp-24'

// Global imports
import { useCurrentProduct } from 'contexts'
import * as NavigationMenu from '@radix-ui/react-navigation-menu'

// Local imports
import {
Expand All @@ -18,6 +19,7 @@ import {
} from '..'
import { ProductIconTextLink } from './components'
import { getNavItems, getProductsDropdownItems, NavItem } from './utils'
import { navigationData, navPromo, sidePanelContent } from 'lib/products'
import s from './product-page-content.module.css'

const ProductPageHeaderContent = () => {
Expand All @@ -28,14 +30,21 @@ const ProductPageHeaderContent = () => {
return (
<>
<div className={s.productsDropdown}>
<NavigationHeaderDropdownMenu
ariaLabel="Main menu"
buttonClassName={s.productsDropdownButton}
dropdownClassName={s.productsDropdownPane}
itemGroups={allProductsItems}
leadingIcon={<IconHashicorp24 className={s.productsDropdownIcon} />}
/>
<NavigationMenu.Root className={s.mobileMenuNavList}>
<NavigationHeaderDropdownMenu
ariaLabel="Main menu"
buttonClassName={s.productsDropdownButton}
itemGroups={allProductsItems}
leadingIcon={<IconHashicorp24 className={s.productsDropdownIcon} />}
productPanelData={{
navigationData,
navPromo,
sidePanelContent,
}}
/>
</NavigationMenu.Root>
</div>

<div className={s.productLinkAndNav}>
<ProductIconTextLink
name={currentProduct.name}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,11 +26,6 @@
padding-top: 2px;
}

.productsDropdownPane {
border-bottom-left-radius: 0;
left: calc(-1 * var(--header-padding-left-right));
}

/*
* Set up the product logo-ish icon lockup next to product nav items.
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,15 @@
display: flex;
justify-content: space-between;
margin-bottom: 12px;

&.rightAlign {
margin-bottom: 0;
}
}

.rightAlign {
justify-content: flex-end;
padding-right: 16px;
}

.levelUpButton {
Expand Down
10 changes: 8 additions & 2 deletions src/components/sidebar/components/sidebar-nav-list/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,14 @@
*/

import { ReactNode } from 'react'
import classNames from 'classnames'
import s from '../../sidebar.module.css'

export default function SidebarNavList({ children }: { children: ReactNode }) {
return <ul className={s.navList}>{children}</ul>
type NativeDivElement = JSX.IntrinsicElements['div']

export default function SidebarNavList({
className,
children,
}: NativeDivElement & { children: ReactNode }) {
return <ul className={classNames(s.navList, className)}>{children}</ul>
}
34 changes: 32 additions & 2 deletions src/components/sidebar/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
// Third-party imports
import { ReactElement, useMemo, useState } from 'react'
import classNames from 'classnames'
import * as NavigationMenu from '@radix-ui/react-navigation-menu'
import ProductPanel from '@hashicorp/react-components/src/components/nav-panel/product-panel'

// Global imports
import { SIDEBAR_LABEL_ID, SIDEBAR_NAV_ELEMENT_ID } from 'constants/element-ids'
Expand All @@ -19,6 +21,7 @@ import {
SidebarNavMenuItem,
SidebarTitleHeading,
} from 'components/sidebar/components'
import { mobileNavigationData, navPromo, sidePanelContent } from 'lib/products'

// Local imports
import { FilteredNavItem, MenuItem, SidebarProps } from './types'
Expand All @@ -45,7 +48,8 @@ const Sidebar = ({
visuallyHideTitle = false,
isInstallPage,
showResourcesList = true,
}: SidebarProps): ReactElement => {
className,
}: SidebarProps & JSX.IntrinsicElements['div']) => {
const currentProduct = useCurrentProduct()
const { shouldRenderMobileControls } = useSidebarNavData()
const currentPath = useCurrentPath({ excludeHash: true, excludeSearch: true })
Expand All @@ -54,6 +58,7 @@ const Sidebar = ({
() => addNavItemMetaData(currentPath, menuItems),
[currentPath, menuItems]
)
const isProductPanel = shouldRenderMobileControls && title === 'Main Menu'

let backToElement
if (shouldRenderMobileControls && levelButtonProps) {
Expand Down Expand Up @@ -131,6 +136,27 @@ const Sidebar = ({
showFilterInput={false}
/>
)
} else if (isProductPanel) {
sidebarContent = (
<>
<NavigationMenu.Root>
<ProductPanel
productCategories={mobileNavigationData}
promo={navPromo}
sidePanel={sidePanelContent}
/>
</NavigationMenu.Root>
{showResourcesList && (
<SidebarNavList className={s.mainMenuResources}>
{navResourceItems.map((item, index) => (
// eslint-disable-next-line react/no-array-index-key
<SidebarNavMenuItem item={item} key={index} />
))}
</SidebarNavList>
)}
</>
)
visuallyHideTitle = true
} else {
sidebarContent = (
<>
Expand All @@ -145,7 +171,11 @@ const Sidebar = ({
)
}
return (
<div className={s.sidebar}>
<div
className={classNames(className, {
[s.sidebar]: !isProductPanel,
})}
>
{backToElement}
{sidebarFilterInput}
<nav
Expand Down
4 changes: 4 additions & 0 deletions src/components/sidebar/sidebar.module.css
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@
padding: 0;
}

.mainMenuResources {
padding: 0 12px;
}

/*
***
* The values set in the following classes are specific so that Sidebar content
Expand Down
21 changes: 19 additions & 2 deletions src/layouts/sidebar-sidecar/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -93,12 +93,29 @@ const SidebarSidecarLayoutContent = ({
sidebarContent = <Sidebar {...sidebarProps} />
}

const shouldNotHaveSidePadding =
sidebarContent.props.title === 'Main Menu' ||
(AlternateSidebar && !sidebarProps?.menuItems)

return (
<div className={classNames(s.root, s[`mainWidth-${mainWidth}`])}>
<MobileMenuContainer className={s.sidebarContainer} ref={sidebarRef}>
<div className={s.sidebarContentWrapper}>
<MobileAuthenticationControls />
{sidebarContent}
<MobileAuthenticationControls
className={classNames(
s.mobileAuthControlsContainer,
s.sidePadding,
{ [s.noMargin]: AlternateSidebar && !sidebarProps?.menuItems }
)}
/>
<div
className={classNames({
[s.sidePadding]:
!shouldNotHaveSidePadding || !isMobileMenuRendered,
})}
>
{sidebarContent}
</div>
</div>
</MobileMenuContainer>
<div className={s.contentWrapper} ref={contentRef}>
Expand Down
21 changes: 17 additions & 4 deletions src/layouts/sidebar-sidecar/sidebar-sidecar-layout.module.css
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,19 @@ for further details.
flex-shrink: 1;
flex-grow: 1;
overflow-y: auto;
padding-bottom: 48px;
padding-left: 16px;
padding-right: 16px;
padding-top: 24px;
position: relative;

@media (--dev-dot-hide-mobile-menu) {
padding-top: 24px;
}
}

.mobileAuthControlsContainer {
padding-top: 24px;

&.noMargin {
margin-bottom: 0;
}
}

/**
Expand Down Expand Up @@ -191,3 +199,8 @@ for further details.
.editOnGithubLink {
margin-top: 64px;
}

.sidePadding {
padding-left: 16px;
padding-right: 16px;
}
24 changes: 14 additions & 10 deletions src/pages/tutorials/library.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ import algoliasearch from 'algoliasearch/lite'
import { InstantSearch } from 'react-instantsearch'
import { history } from 'instantsearch.js/es/lib/routers'
import { useRouter } from 'next/router'
import ProductPanel from '@hashicorp/react-components/src/components/nav-panel/product-panel'
import * as NavigationMenu from '@radix-ui/react-navigation-menu'

import SidebarSidecarLayout, {
SidebarSidecarLayoutProps,
Expand All @@ -19,8 +21,11 @@ import {
searchStateToRouteState,
} from 'views/tutorial-library/utils/router-state'
import SidebarNavList from 'components/sidebar/components/sidebar-nav-list'
import { SidebarNavMenuItem } from 'components/sidebar/components'
import { generateTopLevelSubNavItems } from 'lib/generate-top-level-sub-nav-items'
import {
mobileNavigationData as productPanelMobileNavigationData,
navPromo as productPanelNavPromo,
sidePanelContent as productPanelSidePanelContent,
} from 'lib/products'
import { getTutorials } from 'lib/learn-client/api/tutorial'
import { Tutorial } from 'lib/learn-client/types'
import { stripUndefinedProperties } from 'lib/strip-undefined-props'
Expand Down Expand Up @@ -55,14 +60,13 @@ function TutorialLibrarySidebar() {
</div>
<div className="g-show-with-mobile-menu">
<SidebarNavList>
{/* copied from: src/layouts/base-new/index.tsx */}
<SidebarNavMenuItem item={{ heading: 'Main Menu' }} />
{generateTopLevelSubNavItems().map(
(item: $TSFixMe, index: number) => (
// eslint-disable-next-line react/no-array-index-key
<SidebarNavMenuItem item={item} key={index} />
)
)}
<NavigationMenu.Root>
<ProductPanel
productCategories={productPanelMobileNavigationData}
promo={productPanelNavPromo}
sidePanel={productPanelSidePanelContent}
/>
</NavigationMenu.Root>
</SidebarNavList>
</div>
</>
Expand Down
36 changes: 20 additions & 16 deletions src/views/profile/sidebar/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,37 +3,38 @@
* SPDX-License-Identifier: MPL-2.0
*/

import { generateTopLevelSubNavItems } from 'lib/generate-top-level-sub-nav-items'
import { SidebarNavMenuItem } from 'components/sidebar/components'
import Sidebar from 'components/sidebar'
import { IconSignOut16 } from '@hashicorp/flight-icons/svg-react/sign-out-16'
import { IconUser16 } from '@hashicorp/flight-icons/svg-react/user-16'
import { IconBookmark16 } from '@hashicorp/flight-icons/svg-react/bookmark-16'
import { SidebarNavMenuButton } from 'components/sidebar/components/sidebar-nav-menu-item'
import useAuthentication from 'hooks/use-authentication'
import { useDeviceSize } from 'contexts'
import SidebarNavList from 'components/sidebar/components/sidebar-nav-list'
import { useRouter } from 'next/router'
import ProductPanel from '@hashicorp/react-components/src/components/nav-panel/product-panel'
import { mobileNavigationData, navPromo, sidePanelContent } from 'lib/products'
import * as NavigationMenu from '@radix-ui/react-navigation-menu'

/**
* shared left side bar for /profile pages
*/
export function ProfileSidebar() {
const { signOut } = useAuthentication()
const { isDesktop } = useDeviceSize()
const { asPath } = useRouter()

const isActive = (path: string) => {
return asPath === path
}

return (
<Sidebar
title={isDesktop ? 'Profile' : 'Main Menu'}
showFilterInput={false}
>
<SidebarNavList>
{isDesktop ? (
<>
<Sidebar
title="Profile"
showFilterInput={false}
className="g-hide-with-mobile-menu"
>
<SidebarNavList>
<>
<SidebarNavMenuItem
item={{
Expand Down Expand Up @@ -61,12 +62,15 @@ export function ProfileSidebar() {
/>
</li>
</>
) : (
generateTopLevelSubNavItems().map((item, index) => (
<SidebarNavMenuItem item={item} key={index} />
))
)}
</SidebarNavList>
</Sidebar>
</SidebarNavList>
</Sidebar>
<NavigationMenu.Root className="g-show-with-mobile-menu">
<ProductPanel
productCategories={mobileNavigationData}
promo={navPromo}
sidePanel={sidePanelContent}
/>
</NavigationMenu.Root>
</>
)
}

0 comments on commit 05ff87c

Please sign in to comment.