feat(v2): allow any type of NavbarItem to be passed in a navbar dropdown (#5072)

* Initial work

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* More elegant `eslint-disable`

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Fix typing

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Allow doc links in dropdown

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Allow more dropdowns to use linklike items

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Finalize

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Dogfood

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Disallow nested dropdowns

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Better typing

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Complete type fix

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Use flatmap

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Patch

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Test

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Try fix

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Style change

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Revert (to test)

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Hmmm

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* I know what's wrong

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Does this work?

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Nope

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Wrong class name

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Pass prop to render dropdown item differently

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* This looks better

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Tests passed

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Separate dropdown from default

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Pourquois?

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Better prop typing

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Make code simpler

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* There's some extra className

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Test

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* More test

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* A-ha!

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Test again?

* Add backward compatibility

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Incorporate my type fix

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Resolve conflict

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* minor refactor

* minor refactors

* allow usage of ES2019 in browser code

* revert NavLink rename

Co-authored-by: slorber <lorber.sebastien@gmail.com>
This commit is contained in:
Joshua Chen 2021-07-15 00:19:08 +08:00 committed by GitHub
parent 38c6cb5faa
commit 007e901354
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
13 changed files with 298 additions and 238 deletions

View file

@ -8,7 +8,7 @@
/* eslint-disable camelcase */
declare module '@docusaurus/plugin-content-docs-types' {
import type {VersionBanner} from './types';
type VersionBanner = import('./types').VersionBanner;
export type PropVersionMetadata = {
pluginId: string;

View file

@ -58,7 +58,7 @@ function UnmaintainedVersionLabel({
}
const BannerLabelComponents: Record<
Props['versionMetadata']['banner'],
Exclude<Props['versionMetadata']['banner'], 'none'>,
ComponentType<BannerLabelComponentProps>
> = {
unreleased: UnreleasedVersionLabel,

View file

@ -19,7 +19,7 @@ import {
import useHideableNavbar from '@theme/hooks/useHideableNavbar';
import useLockBodyScroll from '@theme/hooks/useLockBodyScroll';
import useWindowSize from '@theme/hooks/useWindowSize';
import NavbarItem from '@theme/NavbarItem';
import NavbarItem, {Props as NavbarItemConfig} from '@theme/NavbarItem';
import Logo from '@theme/Logo';
import IconMenu from '@theme/IconMenu';
@ -28,9 +28,14 @@ import styles from './styles.module.css';
// retrocompatible with v1
const DefaultNavItemPosition = 'right';
function useNavbarItems() {
// TODO temporary casting until ThemeConfig type is improved
return useThemeConfig().navbar.items as NavbarItemConfig[];
}
// If split links by left/right
// if position is unspecified, fallback to right (as v1)
function splitNavItemsByPosition(items) {
function splitNavItemsByPosition(items: NavbarItemConfig[]) {
const leftItems = items.filter(
(item) => (item.position ?? DefaultNavItemPosition) === 'left',
);
@ -132,9 +137,7 @@ function NavbarMobileSidebar({
toggleSidebar,
}: NavbarMobileSidebarProps) {
useLockBodyScroll(sidebarShown);
const {
navbar: {items},
} = useThemeConfig();
const items = useNavbarItems();
const colorModeToggle = useColorModeToggle();
@ -166,12 +169,7 @@ function NavbarMobileSidebar({
<div className="menu">
<ul className="menu__list">
{items.map((item, i) => (
<NavbarItem
mobile
{...(item as any)} // TODO fix typing
onClick={toggleSidebar}
key={i}
/>
<NavbarItem mobile {...item} onClick={toggleSidebar} key={i} />
))}
</ul>
</div>
@ -196,7 +194,7 @@ function NavbarMobileSidebar({
function Navbar(): JSX.Element {
const {
navbar: {items, hideOnScroll, style},
navbar: {hideOnScroll, style},
} = useThemeConfig();
const mobileSidebar = useMobileSidebar();
@ -204,6 +202,7 @@ function Navbar(): JSX.Element {
const {navbarRef, isNavbarVisible} = useHideableNavbar(hideOnScroll);
const items = useNavbarItems();
const hasSearchNavbarItem = items.some((item) => item.type === 'search');
const {leftItems, rightItems} = splitNavItemsByPosition(items);

View file

@ -5,16 +5,10 @@
* LICENSE file in the root directory of this source tree.
*/
import React, {useState, useRef, useEffect} from 'react';
import React from 'react';
import clsx from 'clsx';
import Link from '@docusaurus/Link';
import useBaseUrl from '@docusaurus/useBaseUrl';
import {useLocation} from '@docusaurus/router';
import {
isSamePath,
useCollapsible,
Collapsible,
} from '@docusaurus/theme-common';
import type {
NavLinkProps,
DesktopOrMobileNavBarItemProps,
@ -25,7 +19,7 @@ import isInternalUrl from '@docusaurus/isInternalUrl';
const dropdownLinkActiveClass = 'dropdown__link--active';
function NavLink({
export function NavLink({
activeBasePath,
activeBaseRegex,
to,
@ -34,7 +28,7 @@ function NavLink({
activeClassName = 'navbar__link--active',
prependBaseUrlToHref,
...props
}: NavLinkProps) {
}: NavLinkProps): JSX.Element {
// TODO all this seems hacky
// {to: 'version'} should probably be forbidden, in favor of {to: '/version'}
const toUrl = useBaseUrl(to);
@ -75,159 +69,36 @@ function NavLink({
);
}
function NavItemDesktop({
items,
position,
function DefaultNavbarItemDesktop({
className,
isDropdownItem = false,
...props
}: DesktopOrMobileNavBarItemProps) {
const dropdownRef = useRef<HTMLDivElement>(null);
const dropdownMenuRef = useRef<HTMLUListElement>(null);
const [showDropdown, setShowDropdown] = useState(false);
useEffect(() => {
const handleClickOutside = (event) => {
if (!dropdownRef.current || dropdownRef.current.contains(event.target)) {
return;
}
setShowDropdown(false);
};
document.addEventListener('mousedown', handleClickOutside);
document.addEventListener('touchstart', handleClickOutside);
return () => {
document.removeEventListener('mousedown', handleClickOutside);
document.removeEventListener('touchstart', handleClickOutside);
};
}, [dropdownRef]);
const navLinkClassNames = (extraClassName?: string, isDropdownItem = false) =>
clsx(
{
'navbar__item navbar__link': !isDropdownItem,
dropdown__link: isDropdownItem,
},
extraClassName,
);
if (!items) {
return <NavLink className={navLinkClassNames(className)} {...props} />;
}
return (
<div
ref={dropdownRef}
className={clsx('navbar__item', 'dropdown', 'dropdown--hoverable', {
'dropdown--left': position === 'left',
'dropdown--right': position === 'right',
'dropdown--show': showDropdown,
})}>
<NavLink
className={navLinkClassNames(className)}
className={clsx(
isDropdownItem ? 'dropdown__link' : 'navbar__item navbar__link',
className,
)}
{...props}
onClick={props.to ? undefined : (e) => e.preventDefault()}
onKeyDown={(e) => {
if (e.key === 'Enter') {
e.preventDefault();
setShowDropdown(!showDropdown);
}
}}>
{props.children ?? props.label}
</NavLink>
<ul ref={dropdownMenuRef} className="dropdown__menu">
{items.map(({className: childItemClassName, ...childItemProps}, i) => (
<li key={i}>
<NavLink
onKeyDown={(e) => {
if (i === items.length - 1 && e.key === 'Tab') {
e.preventDefault();
setShowDropdown(false);
const nextNavbarItem = (dropdownRef.current as HTMLElement)
.nextElementSibling;
if (nextNavbarItem) {
(nextNavbarItem as HTMLElement).focus();
}
}
}}
activeClassName={dropdownLinkActiveClass}
className={navLinkClassNames(childItemClassName, true)}
{...childItemProps}
/>
</li>
))}
</ul>
</div>
);
}
function NavItemMobile({
items,
function DefaultNavbarItemMobile({
className,
position: _position, // Need to destructure position from props so that it doesn't get passed on.
isDropdownItem: _isDropdownItem,
...props
}: DesktopOrMobileNavBarItemProps) {
const {pathname} = useLocation();
const {collapsed, toggleCollapsed} = useCollapsible({
initialState: () =>
!items?.some((item) => isSamePath(item.to, pathname)) ?? true,
});
const navLinkClassNames = (extraClassName?: string, isSubList = false) =>
clsx(
'menu__link',
{
'menu__link--sublist': isSubList,
},
extraClassName,
);
if (!items) {
return (
<li className="menu__list-item">
<NavLink className={navLinkClassNames(className)} {...props} />
</li>
);
}
return (
<li
className={clsx('menu__list-item', {
'menu__list-item--collapsed': collapsed,
})}>
<NavLink
role="button"
className={navLinkClassNames(className, true)}
{...props}
onClick={(e) => {
e.preventDefault();
toggleCollapsed();
}}>
{props.children ?? props.label}
</NavLink>
<Collapsible lazy as="ul" className="menu__list" collapsed={collapsed}>
{items.map(({className: childItemClassName, ...childItemProps}, i) => (
<li className="menu__list-item" key={i}>
<NavLink
activeClassName="menu__link--active"
className={navLinkClassNames(childItemClassName)}
{...childItemProps}
onClick={props.onClick}
/>
</li>
))}
</Collapsible>
<NavLink className={clsx('menu__link', className)} {...props} />
</li>
);
}
function DefaultNavbarItem({mobile = false, ...props}: Props): JSX.Element {
const Comp = mobile ? NavItemMobile : NavItemDesktop;
const Comp = mobile ? DefaultNavbarItemMobile : DefaultNavbarItemDesktop;
return <Comp {...props} />;
}

View file

@ -12,17 +12,10 @@ import clsx from 'clsx';
import type {Props} from '@theme/NavbarItem/DocNavbarItem';
import {useDocsPreferredVersion} from '@docusaurus/theme-common';
import {uniq} from '@docusaurus/utils-common';
import type {
GlobalDataVersion,
GlobalDataDoc,
} from '@docusaurus/plugin-content-docs-types';
import type {GlobalDataVersion} from '@docusaurus/plugin-content-docs-types';
function getDocInVersions(versions: GlobalDataVersion[], docId: string) {
// vanilla-js flatten, TODO replace soon by ES flat() / flatMap()
const allDocs: GlobalDataDoc[] = [].concat(
...versions.map((version) => version.docs),
);
const allDocs = versions.flatMap((version) => version.docs);
const doc = allDocs.find((versionDoc) => versionDoc.id === docId);
if (!doc) {
const docIds = allDocs.map((versionDoc) => versionDoc.id).join('\n- ');

View file

@ -7,6 +7,7 @@
import React from 'react';
import DefaultNavbarItem from '@theme/NavbarItem/DefaultNavbarItem';
import DropdownNavbarItem from '@theme/NavbarItem/DropdownNavbarItem';
import {
useVersions,
useLatestVersion,
@ -52,20 +53,7 @@ export default function DocsVersionDropdownNavbarItem({
};
});
const items = [
...dropdownItemsBefore,
...versionLinks,
...dropdownItemsAfter,
];
// We don't want to render a version dropdown with 0 or 1 item
// If we build the site with a single docs version (onlyIncludeVersions: ['1.0.0'])
// We'd rather render a button instead of a dropdown
if (items.length <= 1) {
return undefined;
}
return items;
return [...dropdownItemsBefore, ...versionLinks, ...dropdownItemsAfter];
}
const items = getItems();
@ -78,8 +66,23 @@ export default function DocsVersionDropdownNavbarItem({
const dropdownTo =
mobile && items ? undefined : getVersionMainDoc(dropdownVersion).path;
// We don't want to render a version dropdown with 0 or 1 item
// If we build the site with a single docs version (onlyIncludeVersions: ['1.0.0'])
// We'd rather render a button instead of a dropdown
if (items.length <= 1) {
return (
<DefaultNavbarItem
{...props}
mobile={mobile}
label={dropdownLabel}
to={dropdownTo}
isActive={dropdownActiveClassDisabled ? () => false : undefined}
/>
);
}
return (
<DropdownNavbarItem
{...props}
mobile={mobile}
label={dropdownLabel}

View file

@ -0,0 +1,147 @@
/**
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
import React, {useState, useRef, useEffect} from 'react';
import clsx from 'clsx';
import {useLocation} from '@docusaurus/router';
import {
isSamePath,
useCollapsible,
Collapsible,
} from '@docusaurus/theme-common';
import type {
DesktopOrMobileNavBarItemProps,
Props,
} from '@theme/NavbarItem/DropdownNavbarItem';
import {NavLink} from '@theme/NavbarItem/DefaultNavbarItem';
import NavbarItem from '@theme/NavbarItem';
const dropdownLinkActiveClass = 'dropdown__link--active';
function DropdownNavbarItemDesktop({
items,
position,
className,
...props
}: DesktopOrMobileNavBarItemProps) {
const dropdownRef = useRef<HTMLDivElement>(null);
const dropdownMenuRef = useRef<HTMLUListElement>(null);
const [showDropdown, setShowDropdown] = useState(false);
useEffect(() => {
const handleClickOutside = (event: MouseEvent | TouchEvent) => {
if (
!dropdownRef.current ||
dropdownRef.current.contains(event.target as Node)
) {
return;
}
setShowDropdown(false);
};
document.addEventListener('mousedown', handleClickOutside);
document.addEventListener('touchstart', handleClickOutside);
return () => {
document.removeEventListener('mousedown', handleClickOutside);
document.removeEventListener('touchstart', handleClickOutside);
};
}, [dropdownRef]);
return (
<div
ref={dropdownRef}
className={clsx('navbar__item', 'dropdown', 'dropdown--hoverable', {
'dropdown--left': position === 'left',
'dropdown--right': position === 'right',
'dropdown--show': showDropdown,
})}>
<NavLink
className={clsx('navbar__item navbar__link', className)}
{...props}
onClick={props.to ? undefined : (e) => e.preventDefault()}
onKeyDown={(e) => {
if (e.key === 'Enter') {
e.preventDefault();
setShowDropdown(!showDropdown);
}
}}>
{props.children ?? props.label}
</NavLink>
<ul ref={dropdownMenuRef} className="dropdown__menu">
{items.map((childItemProps, i) => (
<NavbarItem
isDropdownItem
onKeyDown={(e) => {
if (i === items.length - 1 && e.key === 'Tab') {
e.preventDefault();
setShowDropdown(false);
const nextNavbarItem = dropdownRef.current!.nextElementSibling;
if (nextNavbarItem) {
(nextNavbarItem as HTMLElement).focus();
}
}
}}
activeClassName={dropdownLinkActiveClass}
{...childItemProps}
key={i}
/>
))}
</ul>
</div>
);
}
function DropdownNavbarItemMobile({
items,
className,
position: _position, // Need to destructure position from props so that it doesn't get passed on.
...props
}: DesktopOrMobileNavBarItemProps) {
const {pathname} = useLocation();
const {collapsed, toggleCollapsed} = useCollapsible({
initialState: () =>
!items?.some((item) => isSamePath(item.to, pathname)) ?? true,
});
return (
<li
className={clsx('menu__list-item', {
'menu__list-item--collapsed': collapsed,
})}>
<NavLink
role="button"
className={clsx('menu__link menu__link--sublist', className)}
{...props}
onClick={(e) => {
e.preventDefault();
toggleCollapsed();
}}>
{props.children ?? props.label}
</NavLink>
<Collapsible lazy as="ul" className="menu__list" collapsed={collapsed}>
{items.map((childItemProps, i) => (
<NavbarItem
mobile
isDropdownItem
onClick={props.onClick}
activeClassName="menu__link--active"
{...childItemProps}
key={i}
/>
))}
</Collapsible>
</li>
);
}
function DropdownNavbarItem({mobile = false, ...props}: Props): JSX.Element {
const Comp = mobile ? DropdownNavbarItemMobile : DropdownNavbarItemDesktop;
return <Comp {...props} />;
}
export default DropdownNavbarItem;

View file

@ -6,7 +6,7 @@
*/
import React from 'react';
import DefaultNavbarItem from '@theme/NavbarItem/DefaultNavbarItem';
import DropdownNavbarItem from '@theme/NavbarItem/DropdownNavbarItem';
import IconLanguage from '@theme/IconLanguage';
import type {Props} from '@theme/NavbarItem/LocaleDropdownNavbarItem';
import useDocusaurusContext from '@docusaurus/useDocusaurusContext';
@ -49,7 +49,7 @@ export default function LocaleDropdownNavbarItem({
const dropdownLabel = mobile ? 'Languages' : getLocaleLabel(currentLocale);
return (
<DefaultNavbarItem
<DropdownNavbarItem
{...props}
href="#"
mobile={mobile}

View file

@ -7,39 +7,54 @@
import React from 'react';
import DefaultNavbarItem from '@theme/NavbarItem/DefaultNavbarItem';
import DropdownNavbarItem, {
Props as DropdownNavbarItemProps,
} from '@theme/NavbarItem/DropdownNavbarItem';
import LocaleDropdownNavbarItem from '@theme/NavbarItem/LocaleDropdownNavbarItem';
import SearchNavbarItem from '@theme/NavbarItem/SearchNavbarItem';
import type {Props} from '@theme/NavbarItem';
import type {Types, Props} from '@theme/NavbarItem';
const NavbarItemComponents = {
const NavbarItemComponents: Record<
Exclude<Types, undefined>,
() => (props) => JSX.Element
> = {
default: () => DefaultNavbarItem,
localeDropdown: () => LocaleDropdownNavbarItem,
search: () => SearchNavbarItem,
dropdown: () => DropdownNavbarItem,
// Need to lazy load these items as we don't know for sure the docs plugin is loaded
// See https://github.com/facebook/docusaurus/issues/3360
docsVersion: () =>
// eslint-disable-next-line @typescript-eslint/no-var-requires, global-require
require('@theme/NavbarItem/DocsVersionNavbarItem').default,
/* eslint-disable @typescript-eslint/no-var-requires, global-require */
docsVersion: () => require('@theme/NavbarItem/DocsVersionNavbarItem').default,
docsVersionDropdown: () =>
// eslint-disable-next-line @typescript-eslint/no-var-requires, global-require
require('@theme/NavbarItem/DocsVersionDropdownNavbarItem').default,
doc: () =>
// eslint-disable-next-line @typescript-eslint/no-var-requires, global-require
require('@theme/NavbarItem/DocNavbarItem').default,
doc: () => require('@theme/NavbarItem/DocNavbarItem').default,
/* eslint-enable @typescript-eslint/no-var-requires, global-require */
} as const;
const getNavbarItemComponent = (
type: keyof typeof NavbarItemComponents = 'default',
) => {
const navbarItemComponent = NavbarItemComponents[type];
if (!navbarItemComponent) {
type NavbarItemComponentType = keyof typeof NavbarItemComponents;
const getNavbarItemComponent = (type: NavbarItemComponentType) => {
const navbarItemComponentFn = NavbarItemComponents[type];
if (!navbarItemComponentFn) {
throw new Error(`No NavbarItem component found for type "${type}".`);
}
return navbarItemComponent();
return navbarItemComponentFn();
};
export default function NavbarItem({type, ...props}: Props): JSX.Element {
const NavbarItemComponent = getNavbarItemComponent(type);
function getComponentType({type, ...props}: Props): NavbarItemComponentType {
// Backward compatibility: navbar item with no type set
// but containing dropdown items should use the type "dropdown"
if (!type || type === 'default') {
const isDropdown = (props as DropdownNavbarItemProps).items !== undefined;
return isDropdown ? 'dropdown' : 'default';
}
return type as NavbarItemComponentType;
}
export default function NavbarItem(props: Props): JSX.Element {
const componentType = getComponentType(props);
const NavbarItemComponent = getNavbarItemComponent(componentType);
return <NavbarItemComponent {...props} />;
}

View file

@ -334,23 +334,18 @@ declare module '@theme/Navbar' {
}
declare module '@theme/NavbarItem/DefaultNavbarItem' {
import type {ComponentProps, ReactNode} from 'react';
import type {LinkProps} from '@docusaurus/Link';
export type NavLinkProps = {
activeBasePath?: string;
activeBaseRegex?: string;
to?: string;
exact?: boolean;
href?: string;
label?: ReactNode;
activeClassName?: string;
prependBaseUrlToHref?: string;
isActive?: () => boolean;
} & ComponentProps<'a'>;
export type NavLinkProps = LinkProps & {
readonly activeBasePath?: string;
readonly activeBaseRegex?: string;
readonly exact?: boolean;
readonly label?: ReactNode;
readonly prependBaseUrlToHref?: string;
};
export type DesktopOrMobileNavBarItemProps = NavLinkProps & {
readonly items?: readonly NavLinkProps[];
readonly position?: 'left' | 'right';
readonly isDropdownItem?: boolean;
readonly className?: string;
};
@ -358,10 +353,30 @@ declare module '@theme/NavbarItem/DefaultNavbarItem' {
readonly mobile?: boolean;
};
export const NavLink: (props: NavLinkProps) => JSX.Element;
const DefaultNavbarItem: (props: Props) => JSX.Element;
export default DefaultNavbarItem;
}
declare module '@theme/NavbarItem/DropdownNavbarItem' {
import type {NavLinkProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {LinkLikeNavbarItemProps} from '@theme/NavbarItem';
export type DesktopOrMobileNavBarItemProps = NavLinkProps & {
readonly position?: 'left' | 'right';
readonly items: readonly LinkLikeNavbarItemProps[];
readonly className?: string;
};
export type Props = DesktopOrMobileNavBarItemProps & {
readonly mobile?: boolean;
};
const DropdownNavbarItem: (props: Props) => JSX.Element;
export default DropdownNavbarItem;
}
declare module '@theme/NavbarItem/SearchNavbarItem' {
export type Props = {readonly mobile?: boolean};
@ -370,12 +385,12 @@ declare module '@theme/NavbarItem/SearchNavbarItem' {
}
declare module '@theme/NavbarItem/LocaleDropdownNavbarItem' {
import type {Props as DefaultNavbarItemProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {NavLinkProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {Props as DropdownNavbarItemProps} from '@theme/NavbarItem/DropdownNavbarItem';
import type {LinkLikeNavbarItemProps} from '@theme/NavbarItem';
export type Props = DefaultNavbarItemProps & {
readonly dropdownItemsBefore: NavLinkProps[];
readonly dropdownItemsAfter: NavLinkProps[];
export type Props = DropdownNavbarItemProps & {
readonly dropdownItemsBefore: LinkLikeNavbarItemProps[];
readonly dropdownItemsAfter: LinkLikeNavbarItemProps[];
};
const LocaleDropdownNavbarItem: (props: Props) => JSX.Element;
@ -383,14 +398,14 @@ declare module '@theme/NavbarItem/LocaleDropdownNavbarItem' {
}
declare module '@theme/NavbarItem/DocsVersionDropdownNavbarItem' {
import type {Props as DefaultNavbarItemProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {NavLinkProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {Props as DropdownNavbarItemProps} from '@theme/NavbarItem/DropdownNavbarItem';
import type {LinkLikeNavbarItemProps} from '@theme/NavbarItem';
export type Props = DefaultNavbarItemProps & {
export type Props = DropdownNavbarItemProps & {
readonly docsPluginId?: string;
readonly dropdownActiveClassDisabled?: boolean;
readonly dropdownItemsBefore: NavLinkProps[];
readonly dropdownItemsAfter: NavLinkProps[];
readonly dropdownItemsBefore: LinkLikeNavbarItemProps[];
readonly dropdownItemsAfter: LinkLikeNavbarItemProps[];
};
const DocsVersionDropdownNavbarItem: (props: Props) => JSX.Element;
@ -420,18 +435,35 @@ declare module '@theme/NavbarItem/DocNavbarItem' {
}
declare module '@theme/NavbarItem' {
import type {ComponentProps} from 'react';
import type {Props as DefaultNavbarItemProps} from '@theme/NavbarItem/DefaultNavbarItem';
import type {Props as DocsVersionDropdownNavbarItemProps} from '@theme/NavbarItem/DocsVersionDropdownNavbarItem';
import type {Props as DocNavbarItemProps} from '@theme/NavbarItem/DocNavbarItem';
import type {Props as DocsVersionNavbarItemProps} from '@theme/NavbarItem/DocsVersionNavbarItem';
import type {Props as DropdownNavbarItemProps} from '@theme/NavbarItem/DropdownNavbarItem';
import type {Props as DocsVersionDropdownNavbarItemProps} from '@theme/NavbarItem/DocsVersionDropdownNavbarItem';
import type {Props as LocaleDropdownNavbarItemProps} from '@theme/NavbarItem/LocaleDropdownNavbarItem';
import type {Props as SearchNavbarItemProps} from '@theme/NavbarItem/SearchNavbarItem';
export type Props =
| ({readonly type?: 'default' | undefined} & DefaultNavbarItemProps)
export type LinkLikeNavbarItemProps =
| ({readonly type?: 'default'} & DefaultNavbarItemProps)
| ({readonly type: 'doc'} & DocNavbarItemProps)
| ({readonly type: 'docsVersion'} & DocsVersionNavbarItemProps);
export type Props = ComponentProps<'a'> & {
readonly position?: 'left' | 'right';
} & (
| LinkLikeNavbarItemProps
| ({readonly type?: 'dropdown'} & DropdownNavbarItemProps)
| ({
readonly type: 'docsVersionDropdown';
} & DocsVersionDropdownNavbarItemProps)
| ({readonly type: 'docsVersion'} & DocsVersionNavbarItemProps)
| ({readonly type: 'search'} & SearchNavbarItemProps);
| ({readonly type: 'localeDropdown'} & LocaleDropdownNavbarItemProps)
| ({
readonly type: 'search';
} & SearchNavbarItemProps)
);
export type Types = Props['type'];
const NavbarItem: (props: Props) => JSX.Element;
export default NavbarItem;

View file

@ -1,7 +1,7 @@
{
"extends": "../../tsconfig.json",
"compilerOptions": {
"lib": ["DOM"],
"lib": ["DOM", "ES2019"],
"module": "esnext",
"noEmit": true,
"noImplicitAny": false,

View file

@ -2,7 +2,7 @@
"extends": "../../tsconfig.json",
"compilerOptions": {
"incremental": true,
"lib": ["DOM"],
"lib": ["DOM", "ES2019"],
"module": "esnext",
"tsBuildInfoFile": "./lib/client/.tsbuildinfo",
"outDir": "lib/client",

View file

@ -2,7 +2,7 @@
"extends": "../../tsconfig.json",
"compilerOptions": {
"incremental": true,
"lib": ["DOM"],
"lib": ["DOM", "ES2019"],
"tsBuildInfoFile": "./lib/.tsbuildinfo",
"rootDir": "src",
"outDir": "lib",