docs: added show/hide sidebar button (#4150)

* docs: added show/hide sidebar button

* added check for browser

* fix build error

* solve build errors
This commit is contained in:
Shahed Nasser
2023-05-22 19:44:50 +03:00
committed by GitHub
parent 0476f52519
commit 87444488b5
29 changed files with 589 additions and 188 deletions
+3 -3
View File
@@ -19,7 +19,7 @@ export default function AnnouncementBar(): JSX.Element | null {
<div
className={clsx(
"tw-relative tw-flex tw-items-center tw-h-auto tw-bg-medusa-bg-subtle dark:tw-bg-medusa-bg-base-dark tw-p-[12px]",
"tw-border tw-border-solid tw-border-medusa-border-base dark:tw-border-medusa-border-base-dark tw-rounded tw-mx-1.5 tw-mb-1",
"tw-rounded tw-mx-1.5 tw-mb-1 tw-shadow-card-rest dark:tw-shadow-card-rest-dark",
"tw-transition-all tw-duration-200 tw-ease-ease",
"hover:tw-bg-medusa-bg-subtle-hover dark:hover:tw-bg-medusa-bg-base-hover-dark",
"print:tw-hidden"
@@ -29,10 +29,10 @@ export default function AnnouncementBar(): JSX.Element | null {
<div
className={clsx(
"tw-p-[6px] tw-flex tw-justify-center tw-items-center",
"tw-bg-announcement-bg tw-bg-cover tw-rounded-sm"
"tw-rounded-sm tw-bg-medusa-bg-component dark:tw-bg-medusa-bg-component-dark"
)}
>
<IconBell iconColorClassName="tw-fill-medusa-icon-on-color dark:tw-fill-medusa-icon-on-color-dark" />
<IconBell iconColorClassName="tw-fill-medusa-icon-subtle dark:tw-fill-medusa-icon-subtle-dark" />
</div>
</Bordered>
<AnnouncementBarContent className={clsx("tw-flex-1")} />
+22 -59
View File
@@ -8,16 +8,17 @@ import {
import isInternalUrl from "@docusaurus/isInternalUrl"
import { translate } from "@docusaurus/Translate"
import BorderedIcon from "@site/src/components/BorderedIcon"
import Badge, { BadgeProps } from "@site/src/components/Badge"
import Badge from "@site/src/components/Badge"
import Icons from "@site/src/theme/Icon"
import {
ModifiedPropSidebarItemCategory,
ModifiedPropSidebarItemLink,
ModifiedDocCard,
ModifiedDocCardItemCategory,
ModifiedDocCardItemLink,
ModifiedSidebarItem,
} from "@medusajs/docs"
type ModifiedProps = {
item: ModifiedSidebarItem
item: ModifiedDocCard
}
function CardContainer({
@@ -36,9 +37,9 @@ function CardContainer({
className={clsx(
"card",
"tw-bg-medusa-bg-subtle dark:tw-bg-medusa-bg-base-dark",
"tw-rounded tw-border tw-border-solid tw-border-medusa-bg-subtle-hover dark:tw-border-medusa-bg-base-hover-dark",
"tw-shadow-none tw-transition-all tw-duration-200 tw-ease-ease",
"tw-flex tw-p-1 tw-h-full",
"tw-rounded tw-shadow-card-rest dark:tw-shadow-card-rest-dark",
"tw-transition-all tw-duration-200 tw-ease-ease",
"tw-flex tw-p-1 !tw-pb-1.5 tw-h-full",
className
)}
>
@@ -57,16 +58,7 @@ function CardLayout({
containerClassName,
isSoon = false,
badge,
}: {
href: string
icon: ReactNode
title: string
description?: string
html?: string
containerClassName?: string
isSoon?: boolean
badge?: BadgeProps
}): JSX.Element {
}: ModifiedDocCard): JSX.Element {
const isHighlighted = containerClassName?.includes("card-highlighted")
return (
<CardContainer
@@ -77,7 +69,9 @@ function CardLayout({
"hover:tw-bg-medusa-bg-subtle-hover dark:hover:tw-bg-medusa-bg-base-hover-dark",
isSoon && "tw-pointer-events-none",
isHighlighted &&
"md:before:tw-content-[''] md:before:tw-absolute md:before:tw-top-0 before:tw-right-0 md:before:tw-w-1/2 md:before:tw-h-full md:before:tw-bg-no-repeat md:before:tw-bg-cover md:before:tw-bg-card-highlighted dark:md:before:tw-bg-card-highlighted-dark"
"md:before:tw-content-[''] md:before:tw-absolute md:before:tw-top-0 before:tw-right-0 md:before:tw-w-1/2 md:before:tw-h-full md:before:tw-bg-no-repeat md:before:tw-bg-cover md:before:tw-bg-card-highlighted dark:md:before:tw-bg-card-highlighted-dark",
!isSoon &&
"hover:tw-shadow-card-hover dark:hover:tw-shadow-card-hover-dark"
)}
>
<div
@@ -91,7 +85,7 @@ function CardLayout({
<span
className={clsx(
"tw-text-label-regular-plus tw-text-medusa-text-base dark:tw-text-medusa-text-base-dark",
"tw-mb-0.5 tw-block",
"tw-mb-[4px] tw-block",
"tw-transition-all tw-duration-200 tw-ease-ease",
isSoon &&
"group-hover:tw-text-medusa-text-disabled dark:group-hover:tw-text-medusa-text-disabled-dark"
@@ -103,7 +97,7 @@ function CardLayout({
{description && (
<p
className={clsx(
"tw-text-label-regular tw-text-medusa-text-subtle dark:tw-text-medusa-text-subtle-dark",
"tw-text-body-regular tw-text-medusa-text-subtle dark:tw-text-medusa-text-subtle-dark",
"tw-transition-all tw-duration-200 tw-ease-ease",
isSoon &&
"group-hover:tw-text-medusa-text-disabled dark:group-hover:tw-text-medusa-text-disabled-dark",
@@ -141,14 +135,7 @@ function getCardIcon(item: ModifiedSidebarItem): JSX.Element {
light: item.customProps.themedImage.light,
dark: item.customProps.themedImage.dark,
}}
wrapperClassName={
clsx()
// "card-icon-wrapper",
}
iconWrapperClassName={clsx(
item.customProps?.className?.includes("card-highlighted") &&
"tw-p-[6px]"
)}
iconWrapperClassName={clsx("tw-p-[6px]")}
iconClassName={clsx("tw-h-[20px] tw-w-[20px]")}
/>
)
@@ -158,14 +145,7 @@ function getCardIcon(item: ModifiedSidebarItem): JSX.Element {
icon={{
light: item.customProps.image,
}}
wrapperClassName={
clsx()
// "card-icon-wrapper",
}
iconWrapperClassName={clsx(
item.customProps?.className?.includes("card-highlighted") &&
"tw-p-[6px]"
)}
iconWrapperClassName={clsx("tw-p-[6px]")}
iconClassName={clsx("tw-h-[20px] tw-w-[20px]")}
/>
)
@@ -173,14 +153,7 @@ function getCardIcon(item: ModifiedSidebarItem): JSX.Element {
return (
<BorderedIcon
IconComponent={item.customProps.icon}
wrapperClassName={
clsx()
// "card-icon-wrapper",
}
iconWrapperClassName={clsx(
item.customProps?.className?.includes("card-highlighted") &&
"tw-p-[6px]"
)}
iconWrapperClassName={clsx("tw-p-[6px]")}
iconClassName={clsx("tw-h-[20px] tw-w-[20px]")}
/>
)
@@ -191,14 +164,7 @@ function getCardIcon(item: ModifiedSidebarItem): JSX.Element {
return (
<BorderedIcon
IconComponent={Icons[item.customProps?.iconName]}
wrapperClassName={
clsx()
// "card-icon-wrapper",
}
iconWrapperClassName={clsx(
item.customProps?.className?.includes("card-highlighted") &&
"tw-p-[6px]"
)}
iconWrapperClassName={clsx("tw-p-[6px]")}
iconClassName={clsx("tw-h-[20px] tw-w-[20px]")}
/>
)
@@ -223,7 +189,7 @@ function getCardIcon(item: ModifiedSidebarItem): JSX.Element {
function CardCategory({
item,
}: {
item: ModifiedPropSidebarItemCategory
item: ModifiedDocCardItemCategory
}): JSX.Element | null {
const href = findFirstCategoryLink(item)
const icon = getCardIcon(item)
@@ -233,6 +199,7 @@ function CardCategory({
}
return (
<CardLayout
{...item}
href={href}
icon={icon}
title={item.label}
@@ -253,17 +220,13 @@ function CardCategory({
)
}
function CardLink({
item,
}: {
item: ModifiedPropSidebarItemLink
}): JSX.Element {
function CardLink({ item }: { item: ModifiedDocCardItemLink }): JSX.Element {
const icon = getCardIcon(item)
const doc = useDocById(item.docId ?? undefined)
return (
<CardLayout
href={item.href}
{...item}
icon={icon}
title={item.label}
description={item.customProps?.description || doc?.description}
+6 -3
View File
@@ -1,4 +1,4 @@
import React from "react"
import React, { useContext } from "react"
import clsx from "clsx"
import { useWindowSize } from "@docusaurus/theme-common"
import { useDoc } from "@docusaurus/theme-common/internal"
@@ -12,6 +12,7 @@ import DocItemContent from "@theme/DocItem/Content"
import DocBreadcrumbs from "@theme/DocBreadcrumbs"
import type { Props } from "@theme/DocItem/Layout"
import Footer from "@theme/Footer"
import { SidebarContext } from "@site/src/context/sidebar"
/**
* Decide if the toc should be rendered, on mobile or desktop viewports
@@ -39,13 +40,15 @@ function useDocTOC() {
export default function DocItemLayout({ children }: Props): JSX.Element {
const docTOC = useDocTOC()
const sidebarContext = useContext(SidebarContext)
return (
<div className="row tw-m-0">
<div
className={clsx(
"col",
"tw-my-0 tw-mx-auto tw-max-w-main-content tw-w-full tw-ml-auto lg:tw-py-0 lg:tw-px-4 tw-py-0 tw-px-1",
!docTOC.hidden && "xxl:tw-w-10/12 tw-w-9/12"
"tw-my-0 tw-mx-auto tw-max-w-main-content tw-w-full tw-ml-auto lg:tw-py-0 tw-py-0 tw-px-1",
!docTOC.hidden && "tw-w-9/12",
!sidebarContext?.hiddenSidebarContainer && "!tw-max-w-[720px]"
)}
>
<DocVersionBanner />
@@ -1,24 +1,27 @@
import React from "react"
import React, { useContext } from "react"
import clsx from "clsx"
import { useDocsSidebar } from "@docusaurus/theme-common/internal"
import type { Props } from "@theme/DocPage/Layout/Main"
import { SidebarContext } from "@site/src/context/sidebar"
export default function DocPageLayoutMain({
hiddenSidebarContainer,
children,
}: Props): JSX.Element {
export default function DocPageLayoutMain({ children }: Props): JSX.Element {
const sidebar = useDocsSidebar()
const sidebarContext = useContext(SidebarContext)
return (
<main
className={clsx(
"tw-flex tw-flex-col tw-w-full lg:tw-flex-grow lg:tw-max-w-[calc(100%-320px)]",
(hiddenSidebarContainer || !sidebar) && "lg:tw-max-w-[calc(100%-30px)]"
"tw-flex tw-flex-col tw-w-full lg:tw-flex-grow",
(sidebarContext?.hiddenSidebarContainer || !sidebar) &&
"lg:tw-max-w-[calc(100%-30px)]",
!sidebarContext?.hiddenSidebarContainer &&
"xxl:tw-max-w-[1119px] lg:tw-max-w-[calc(100%-321px)]"
)}
>
<div
className={clsx(
"container padding-top--md tw-px-0",
hiddenSidebarContainer && "lg:tw-max-w-main-content-hidden-sidebar"
sidebarContext?.hiddenSidebarContainer &&
"lg:tw-max-w-main-content-hidden-sidebar"
)}
>
{children}
@@ -1,12 +1,12 @@
import React, { type ReactNode, useState, useCallback, useRef } from "react"
import React, { type ReactNode, useRef, useContext } from "react"
import clsx from "clsx"
import { ThemeClassNames } from "@docusaurus/theme-common"
import { useDocsSidebar } from "@docusaurus/theme-common/internal"
import { useLocation } from "@docusaurus/router"
import DocSidebar from "@theme/DocSidebar"
import ExpandButton from "@theme/DocPage/Layout/Sidebar/ExpandButton"
import type { Props } from "@theme/DocPage/Layout/Sidebar"
import { SwitchTransition, CSSTransition } from "react-transition-group"
import { SidebarContext } from "@site/src/context/sidebar"
// Reset sidebar state when sidebar changes
// Use React key to unmount/remount the children
@@ -23,18 +23,9 @@ function ResetOnSidebarChange({ children }: { children: ReactNode }) {
export default function DocPageLayoutSidebar({
sidebar,
hiddenSidebarContainer,
setHiddenSidebarContainer,
}: Props): JSX.Element {
const { pathname } = useLocation()
const [hiddenSidebar, setHiddenSidebar] = useState(false)
const toggleSidebar = useCallback(() => {
if (hiddenSidebar) {
setHiddenSidebar(false)
}
setHiddenSidebarContainer((value) => !value)
}, [setHiddenSidebarContainer, hiddenSidebar])
const sidebarContext = useContext(SidebarContext)
const { name } = useDocsSidebar()
const sidebarRef = useRef(null)
@@ -42,8 +33,13 @@ export default function DocPageLayoutSidebar({
<aside
className={clsx(
ThemeClassNames.docs.docSidebarContainer,
"lg:tw-block lg:tw-w-sidebar lg:tw-will-change-[width] lg:tw-transition-[width] lg:tw-ease-ease tw-clip tw-hidden tw-duration-200",
hiddenSidebarContainer && "lg:tw-w-sidebar-hidden lg:tw-cursor-pointer"
"lg:tw-block lg:tw-w-sidebar lg:tw-transition-[left] lg:tw-ease-ease lg:tw-duration-200 lg:tw-left-0 tw-hidden",
!hiddenSidebarContainer && "clip",
hiddenSidebarContainer &&
"lg:tw-fixed lg:tw-left-[-100%] lg:tw-rounded lg:tw-border-0 lg:tw-border-medusa-border-strong lg:dark:tw-border-medusa-border-strong-dark",
hiddenSidebarContainer &&
sidebarContext?.floatingSidebar &&
"lg:!tw-left-0.5 lg:tw-top-[65px] lg:tw-z-20 lg:tw-bg-docs-bg lg:dark:tw-bg-docs-bg-dark lg:tw-shadow-flyout lg:dark:tw-shadow-flyout-dark"
)}
onTransitionEnd={(e) => {
if (
@@ -55,7 +51,24 @@ export default function DocPageLayoutSidebar({
}
if (hiddenSidebarContainer) {
setHiddenSidebar(true)
sidebarContext?.setHiddenSidebar(true)
}
}}
onMouseLeave={() => {
setTimeout(() => {
if (!document.querySelector(".sidebar-toggler:hover")) {
sidebarContext?.setFloatingSidebar(false)
}
}, 100)
}}
onMouseUp={(e) => {
const target = e.target as Element
console.log("here", target.classList)
if (
target.classList.contains("menu__list-item") ||
target.parentElement.classList.contains("menu__list-item")
) {
sidebarContext?.setFloatingSidebar(false)
}
}}
>
@@ -80,12 +93,9 @@ export default function DocPageLayoutSidebar({
<DocSidebar
sidebar={sidebar}
path={pathname}
onCollapse={toggleSidebar}
isHidden={hiddenSidebar}
onCollapse={sidebarContext?.onCollapse}
isHidden={sidebarContext?.hiddenSidebar}
/>
{hiddenSidebar && (
<ExpandButton toggleSidebar={toggleSidebar} />
)}
</div>
</ResetOnSidebarChange>
</div>
@@ -0,0 +1,35 @@
import React, { useContext } from "react"
import { useDocsSidebar } from "@docusaurus/theme-common/internal"
import Layout from "@theme/Layout"
import BackToTopButton from "@theme/BackToTopButton"
import DocPageLayoutSidebar from "@theme/DocPage/Layout/Sidebar"
import DocPageLayoutMain from "@theme/DocPage/Layout/Main"
import type { Props } from "@theme/DocPage/Layout"
import { SidebarContext } from "@site/src/context/sidebar"
import clsx from "clsx"
export default function DocPageLayout({ children }: Props): JSX.Element {
const sidebar = useDocsSidebar()
const sidebarContext = useContext(SidebarContext)
return (
<Layout wrapperClassName={clsx("tw-flex tw-flex-[1_0_auto]")}>
<BackToTopButton />
<div className={clsx("tw-flex tw-w-full tw-flex-[1_0]")}>
{sidebar && (
<DocPageLayoutSidebar
sidebar={sidebar.items}
hiddenSidebarContainer={sidebarContext?.hiddenSidebarContainer}
setHiddenSidebarContainer={
sidebarContext?.setHiddenSidebarContainer
}
/>
)}
<DocPageLayoutMain
hiddenSidebarContainer={sidebarContext?.hiddenSidebarContainer}
>
{children}
</DocPageLayoutMain>
</div>
</Layout>
)
}
+62 -2
View File
@@ -1,9 +1,10 @@
import React from "react"
import React, { useCallback, useEffect, useState } from "react"
import clsx from "clsx"
import {
HtmlClassNameProvider,
ThemeClassNames,
PageMetadata,
prefersReducedMotion,
} from "@docusaurus/theme-common"
import {
docVersionSearchTag,
@@ -15,6 +16,7 @@ import DocPageLayout from "@theme/DocPage/Layout"
import NotFound from "@theme/NotFound"
import SearchMetadata from "@theme/SearchMetadata"
import type { Props } from "@theme/DocPage"
import { SidebarContext } from "@site/src/context/sidebar"
function DocPageMetadata(props: Props): JSX.Element {
const { versionMetadata } = props
@@ -43,6 +45,52 @@ export default function DocPage(props: Props): JSX.Element {
return <NotFound />
}
const { docElement, sidebarName, sidebarItems } = currentDocRouteMetadata
const [hiddenSidebar, setHiddenSidebar] = useState(false)
const [hiddenSidebarContainer, setHiddenSidebarContainer] = useState(false)
const [floatingSidebar, setFloatingSidebar] = useState(false)
const toggleSidebar = useCallback(() => {
if (hiddenSidebar) {
setHiddenSidebar(false)
}
// onTransitionEnd won't fire when sidebar animation is disabled
// fixes https://github.com/facebook/docusaurus/issues/8918
if (!hiddenSidebar && prefersReducedMotion()) {
setHiddenSidebar(true)
}
setHiddenSidebarContainer((value) => !value)
}, [setHiddenSidebarContainer, hiddenSidebar])
useEffect(() => {
function isEditingContent(event: KeyboardEvent) {
const element = event.target as HTMLElement
const tagName = element.tagName
return (
element.isContentEditable ||
tagName === "INPUT" ||
tagName === "SELECT" ||
tagName === "TEXTAREA"
)
}
function sidebarShortcut(e: KeyboardEvent) {
if (
(e.metaKey || e.ctrlKey) &&
e.key.toLowerCase() === "i" &&
!isEditingContent(e)
) {
e.preventDefault()
toggleSidebar()
}
}
window.addEventListener("keydown", sidebarShortcut)
return () => {
window.removeEventListener("keydown", sidebarShortcut)
}
})
return (
<>
<DocPageMetadata {...props} />
@@ -57,7 +105,19 @@ export default function DocPage(props: Props): JSX.Element {
>
<DocsVersionProvider version={versionMetadata}>
<DocsSidebarProvider name={sidebarName} items={sidebarItems}>
<DocPageLayout>{docElement}</DocPageLayout>
<SidebarContext.Provider
value={{
hiddenSidebar,
setHiddenSidebar,
hiddenSidebarContainer,
setHiddenSidebarContainer,
floatingSidebar,
setFloatingSidebar,
onCollapse: toggleSidebar,
}}
>
<DocPageLayout>{docElement}</DocPageLayout>
</SidebarContext.Provider>
</DocsSidebarProvider>
</DocsVersionProvider>
</HtmlClassNameProvider>
@@ -1,19 +1,15 @@
import React, { useEffect, useRef } from "react"
import clsx from "clsx"
import { useThemeConfig } from "@docusaurus/theme-common"
import CollapseButton from "@theme/DocSidebar/Desktop/CollapseButton"
import Content from "@theme/DocSidebar/Desktop/Content"
import type { Props } from "@theme/DocSidebar/Desktop"
import useIsBrowser from "@docusaurus/useIsBrowser"
import { useLocation } from "@docusaurus/router"
import AnnouncementBar from "../../AnnouncementBar/index"
function DocSidebarDesktop({ path, sidebar, onCollapse, isHidden }: Props) {
function DocSidebarDesktop({ path, sidebar, isHidden }: Props) {
const {
navbar: { hideOnScroll },
docs: {
sidebar: { hideable },
},
} = useThemeConfig()
const isBrowser = useIsBrowser()
const sidebarRef = useRef(null)
@@ -82,9 +78,7 @@ function DocSidebarDesktop({ path, sidebar, onCollapse, isHidden }: Props) {
className={clsx(
"lg:tw-flex lg:tw-flex-col lg:tw-max-h-screen lg:tw-h-full lg:tw-sticky lg:tw-top-0 lg:tw-transition-opacity lg:tw-duration-[50ms] lg:tw-ease-ease lg:tw-pt-1.5",
"sidebar-desktop",
hideOnScroll && "lg:tw-pt-0",
isHidden &&
"lg:tw-opacity-0 lg:tw-h-0 lg:tw-overflow-hidden lg:tw-invisible"
hideOnScroll && "lg:tw-pt-0"
)}
ref={sidebarRef}
>
@@ -97,7 +91,6 @@ function DocSidebarDesktop({ path, sidebar, onCollapse, isHidden }: Props) {
"!tw-mt-0 !tw-pt-0 !tw-px-1.5 !tw-pb-4"
)}
/>
{hideable && <CollapseButton onClick={onCollapse} />}
</div>
)
}
@@ -165,7 +165,7 @@ export default function DocSidebarItemCategory({
"[&_.sidebar-item-icon]:tw-w-[20px] [&_.sidebar-item-icon]:tw-h-[20px]",
!customProps?.sidebar_is_title &&
!customProps?.sidebar_is_back_link &&
"[&_.sidebar-item-icon]:tw-mr-1"
"[&_.sidebar-item-icon]:tw-mr-[12px]"
)}
>
<div
@@ -36,7 +36,7 @@ export default function DocSidebarItemHtml({
"[&_.sidebar-item-icon]:tw-w-[20px] [&_.sidebar-item-icon]:tw-h-[20px]",
!customProps?.sidebar_is_title &&
!customProps?.sidebar_is_back_link &&
"[&_.sidebar-item-icon]:tw-mr-1"
"[&_.sidebar-item-icon]:tw-mr-[12px]"
)}
key={index}
>
@@ -42,7 +42,7 @@ export default function DocSidebarItemLink({
"[&_.sidebar-item-icon]:tw-w-[20px] [&_.sidebar-item-icon]:tw-h-[20px]",
!customProps?.sidebar_is_title &&
!customProps?.sidebar_is_back_link &&
"[&_.sidebar-item-icon]:tw-mr-1"
"[&_.sidebar-item-icon]:tw-mr-[12px]"
)}
key={label}
>
@@ -0,0 +1,31 @@
import React from "react"
import { IconProps } from ".."
const IconBarsThree: React.FC<IconProps> = ({
iconColorClassName,
...props
}) => {
return (
<svg
width={props.width || 20}
height={props.height || 20}
viewBox="0 0 20 20"
fill="none"
xmlns="http://www.w3.org/2000/svg"
{...props}
>
<path
d="M3.125 5.00006H16.875M3.125 10H16.875M3.125 15.0001H16.875"
className={
iconColorClassName ||
"tw-stroke-medusa-icon-secondary dark:tw-stroke-medusa-icon-secondary"
}
strokeWidth="1.5"
strokeLinecap="round"
strokeLinejoin="round"
/>
</svg>
)
}
export default IconBarsThree
@@ -0,0 +1,30 @@
import React from "react"
import { IconProps } from ".."
const IconChevronDoubleLeftMiniSolid: React.FC<IconProps> = ({
iconColorClassName,
...props
}) => {
return (
<svg
width={props.width || 20}
height={props.height || 20}
viewBox="0 0 20 20"
fill="none"
xmlns="http://www.w3.org/2000/svg"
{...props}
>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M15.79 14.77C15.6521 14.9131 15.4629 14.9957 15.2641 14.9994C15.0654 15.0032 14.8733 14.9278 14.73 14.79L10.23 10.54C10.1574 10.47 10.0997 10.3862 10.0602 10.2934C10.0208 10.2006 10.0005 10.1008 10.0005 10C10.0005 9.89919 10.0208 9.79941 10.0602 9.70663C10.0997 9.61385 10.1574 9.52997 10.23 9.46001L14.73 5.21001C14.8002 5.13826 14.8841 5.08133 14.9767 5.0426C15.0693 5.00386 15.1687 4.98411 15.2691 4.9845C15.3695 4.9849 15.4687 5.00544 15.561 5.04491C15.6533 5.08437 15.7367 5.14196 15.8064 5.21427C15.876 5.28657 15.9304 5.37211 15.9663 5.46582C16.0023 5.55953 16.0191 5.65951 16.0157 5.75982C16.0123 5.86014 15.9888 5.95875 15.9466 6.04983C15.9044 6.1409 15.8444 6.22257 15.77 6.29001L11.832 10L15.77 13.71C15.9131 13.848 15.9957 14.0371 15.9994 14.2359C16.0032 14.4346 15.9278 14.6267 15.79 14.77ZM9.79001 14.77C9.65205 14.9131 9.46291 14.9957 9.26415 14.9994C9.06539 15.0032 8.87327 14.9278 8.73001 14.79L4.23001 10.54C4.15742 10.47 4.09968 10.3862 4.06025 10.2934C4.02081 10.2006 4.00049 10.1008 4.00049 10C4.00049 9.89919 4.02081 9.79941 4.06025 9.70663C4.09968 9.61385 4.15742 9.52997 4.23001 9.46001L8.73001 5.21001C8.8002 5.13826 8.88408 5.08133 8.97668 5.0426C9.06928 5.00386 9.16871 4.98411 9.26908 4.9845C9.36945 4.9849 9.46873 5.00544 9.56102 5.04491C9.6533 5.08437 9.73673 5.14196 9.80635 5.21427C9.87598 5.28657 9.93038 5.37211 9.96634 5.46582C10.0023 5.55953 10.0191 5.65951 10.0157 5.75982C10.0123 5.86014 9.98881 5.95875 9.9466 6.04983C9.9044 6.1409 9.84435 6.22257 9.77001 6.29001L5.83201 10L9.77001 13.71C9.91314 13.848 9.99565 14.0371 9.9994 14.2359C10.0032 14.4346 9.92784 14.6267 9.79001 14.77Z"
className={
iconColorClassName ||
"tw-fill-medusa-icon-secondary dark:tw-fill-medusa-icon-secondary-dark"
}
/>
</svg>
)
}
export default IconChevronDoubleLeftMiniSolid
+4
View File
@@ -3,6 +3,7 @@ import IconAdjustments from "./Adjustments"
import IconAlert from "./Alert"
import IconArrowDownTray from "./ArrowDownTray"
import IconBackArrow from "./BackArrow"
import IconBarsThree from "./BarsThree"
import IconBell from "./Bell"
import IconBellAlertSolid from "./BellAlertSolid"
import IconBolt from "./Bolt"
@@ -18,6 +19,7 @@ import IconCashSolid from "./CashSolid"
import IconChannels from "./Channels"
import IconChannelsSolid from "./ChannelsSolid"
import IconCheckCircleSolid from "./CheckCircleSolid"
import IconChevronDoubleLeftMiniSolid from "./ChevronDoubleLeftMiniSolid"
import IconCircleStack from "./CircleStack"
import IconCircleStackSolid from "./CircleStackSolid"
import IconClockSolidMini from "./ClockSolidMini"
@@ -95,6 +97,7 @@ export default {
alert: IconAlert,
"arrow-down-tray": IconArrowDownTray,
"back-arrow": IconBackArrow,
"bars-three": IconBarsThree,
bell: IconBell,
"bell-alert-solid": IconBellAlertSolid,
bolt: IconBolt,
@@ -110,6 +113,7 @@ export default {
"channels-solid": IconChannelsSolid,
channels: IconChannels,
"check-circle-solid": IconCheckCircleSolid,
"chevron-double-left-mini-solid": IconChevronDoubleLeftMiniSolid,
"circle-stack": IconCircleStack,
"circle-stack-solid": IconCircleStackSolid,
"clock-solid-mini": IconClockSolidMini,
@@ -0,0 +1,26 @@
import React from "react"
import { useColorMode, useThemeConfig } from "@docusaurus/theme-common"
import ColorModeToggle from "@theme/ColorModeToggle"
import type { Props } from "@theme/Navbar/ColorModeToggle"
export default function NavbarColorModeToggle({
className,
}: Props): JSX.Element | null {
const disabled = useThemeConfig().colorMode.disableSwitch
const { colorMode, setColorMode } = useColorMode()
if (disabled) {
return null
}
return (
<ColorModeToggle
className={className}
buttonClassName={
"hover:!tw-bg-medusa-button-neutral-hover dark:hover:!tw-bg-medusa-button-neutral-hover-dark"
}
value={colorMode}
onChange={setColorMode}
/>
)
}
+75 -5
View File
@@ -1,4 +1,4 @@
import React, { type ReactNode } from "react"
import React, { useContext, type ReactNode } from "react"
import { useThemeConfig } from "@docusaurus/theme-common"
import {
splitNavbarItems,
@@ -11,7 +11,9 @@ import NavbarLogo from "@theme/Navbar/Logo"
import NavbarActions from "@site/src/components/Navbar/Actions"
import Tooltip from "@site/src/components/Tooltip"
import { ThemeConfig } from "@medusajs/docs"
import useIsBrowser from "@docusaurus/useIsBrowser"
import clsx from "clsx"
import { SidebarContext } from "@site/src/context/sidebar"
function useNavbarItems() {
// TODO temporary casting until ThemeConfig type is improved
@@ -62,7 +64,18 @@ export default function NavbarContent(): JSX.Element {
const items = useNavbarItems()
const [leftItems, rightItems] = splitNavbarItems(items)
const { navbarActions } = useThemeConfig() as ThemeConfig
const {
navbarActions,
docs: {
sidebar: { hideable },
},
} = useThemeConfig() as ThemeConfig
const sidebarContext = useContext(SidebarContext)
const isBrowser = useIsBrowser()
const isApple = isBrowser
? navigator.userAgent.toLowerCase().indexOf("mac") !== 0
: true
return (
<NavbarContentLayout
@@ -71,6 +84,65 @@ export default function NavbarContent(): JSX.Element {
<>
{!mobileSidebar.disabled && <NavbarMobileSidebarToggle />}
<NavbarLogo />
{hideable && (
<NavbarActions
items={[
{
type: "button",
html: !sidebarContext?.hiddenSidebarContainer
? `<span class="tw-text-label-x-small-plus">Close sidebar <kbd class="${clsx(
"tw-bg-medusa-tag-neutral-bg dark:tw-bg-medusa-tag-neutral-bg-dark",
"tw-border tw-border-solid tw-rounded tw-border-medusa-tag-neutral-border dark:tw-border-medusa-tag-neutral-border-dark",
"tw-text-medusa-tag-neutral-text dark:tw-text-medusa-tag-neutral-text tw-font-base tw-text-label-x-small-plus",
"tw-inline-flex tw-w-[22px] tw-h-[22px] !tw-p-0 tw-justify-center tw-items-center tw-shadow-none tw-ml-0.5"
)}">${isApple ? "⌘" : "Ctrl"}</kbd>
<kbd class="${clsx(
"tw-bg-medusa-tag-neutral-bg dark:tw-bg-medusa-tag-neutral-bg-dark",
"tw-border tw-border-solid tw-rounded tw-border-medusa-tag-neutral-border dark:tw-border-medusa-tag-neutral-border-dark",
"tw-text-medusa-tag-neutral-text dark:tw-text-medusa-tag-neutral-text tw-font-base tw-text-label-x-small-plus",
"tw-inline-flex tw-w-[22px] tw-h-[22px] !tw-p-0 tw-justify-center tw-items-center tw-shadow-none"
)}">I</kbd></span>`
: `<span class="tw-text-label-x-small-plus">Lock sidebar open <kbd class="${clsx(
"tw-bg-medusa-tag-neutral-bg dark:tw-bg-medusa-tag-neutral-bg-dark",
"tw-border tw-border-solid tw-rounded tw-border-medusa-tag-neutral-border dark:tw-border-medusa-tag-neutral-border-dark",
"tw-text-medusa-tag-neutral-text dark:tw-text-medusa-tag-neutral-text tw-font-base tw-text-label-x-small-plus",
"tw-inline-flex tw-w-[22px] tw-h-[22px] !tw-p-0 tw-justify-center tw-items-center tw-shadow-none tw-ml-0.5"
)}">${isApple ? "⌘" : "Ctrl"}</kbd>
<kbd class="${clsx(
"tw-bg-medusa-tag-neutral-bg dark:tw-bg-medusa-tag-neutral-bg-dark",
"tw-border tw-border-solid tw-rounded tw-border-medusa-tag-neutral-border dark:tw-border-medusa-tag-neutral-border-dark",
"tw-text-medusa-tag-neutral-text dark:tw-text-medusa-tag-neutral-text tw-font-base tw-text-label-x-small-plus",
"tw-inline-flex tw-w-[22px] tw-h-[22px] !tw-p-0 tw-justify-center tw-items-center tw-shadow-none"
)}">I</kbd></span>`,
events: {
onClick: sidebarContext?.onCollapse,
onMouseEnter: () => {
if (!sidebarContext?.hiddenSidebarContainer) {
sidebarContext?.setFloatingSidebar(false)
} else {
sidebarContext?.setFloatingSidebar(true)
}
},
onMouseLeave: () => {
setTimeout(() => {
if (
!document.querySelector(
".theme-doc-sidebar-container:hover"
)
) {
sidebarContext?.setFloatingSidebar(false)
}
}, 100)
},
},
icon: !sidebarContext?.hiddenSidebarContainer
? "bars-three"
: "chevron-double-left-mini-solid",
},
]}
className="tw-mr-0.5 sidebar-toggler"
/>
)}
<NavbarItems items={leftItems} />
</>
}
@@ -88,9 +160,7 @@ export default function NavbarContent(): JSX.Element {
<NavbarColorModeToggle
className={clsx(
"lg:tw-block tw-hidden",
"tw-bg-medusa-button-secondary dark:tw-bg-medusa-button-secondary-dark",
"tw-border tw-border-solid tw-border-medusa-border-base dark:tw-border-medusa-border-base-dark",
"tw-rounded !tw-w-2 !tw-h-2 tw-ml-1 tw-mr-[12px] [&>button]:!tw-rounded"
"navbar-action-icon-item !tw-w-2 !tw-h-2 tw-ml-1 tw-mr-[12px] [&>button]:!tw-rounded"
)}
/>
</Tooltip>