diff --git a/lib/components/controls.tsx b/lib/components/controls.tsx index 81fe304..23338f9 100644 --- a/lib/components/controls.tsx +++ b/lib/components/controls.tsx @@ -1,10 +1,9 @@ import React, { useCallback, useMemo } from 'react' -import { Button, useTheme, Spacer } from 'components' +import { Button, useTheme, Select, Spacer } from 'components' import { useConfigs } from 'lib/config-context' import Router, { useRouter } from 'next/router' import MoonIcon from './icons/moon' import SunIcon from './icons/sun' -import GithubIcon from './icons/github' const Controls: React.FC<{}> = React.memo(({ }) => { @@ -12,14 +11,14 @@ const Controls: React.FC<{}> = React.memo(({ const { onChange, updateChineseState } = useConfigs() const { pathname } = useRouter() const currentLocaleText = useMemo(() => { - return pathname.toLowerCase().includes('zh-cn') ? 'EN' : '中' + return pathname.toLowerCase().includes('zh-cn') ? 'English' : '中文文档' }, [pathname]) const isDark = useMemo(() => theme.type === 'dark', [theme.type]) - const switchThemes = useCallback(() => { - const isDark = theme.type === 'dark' - onChange && onChange(!isDark) - }, [theme.type]) - + const switchThemes = (val: string) => { + const isDark = val === 'dark' + onChange && onChange(isDark) + } + const switchLanguages = useCallback(() => { const currentIsChinese = pathname.toLowerCase().includes('zh-cn') const nextPath = `/${currentIsChinese ? 'en-us' : 'zh-cn'}` @@ -36,39 +35,45 @@ const Controls: React.FC<{}> = React.memo(({ return (
- - - - + + + + +
+ + ) +} + +export default MenuLinks diff --git a/lib/components/menu/menu-sticker.tsx b/lib/components/menu/menu-sticker.tsx new file mode 100644 index 0000000..2d796ba --- /dev/null +++ b/lib/components/menu/menu-sticker.tsx @@ -0,0 +1,170 @@ +import React, { useEffect, useMemo } from 'react' +import { Tabs, useTheme } from 'components' +import useCurrentState from 'components/utils/use-current-state' +import sides from 'lib/data/metadata.json' +import { Sides } from 'lib/components/sidebar/side-item' +import Router, { useRouter } from 'next/router' +import { useConfigs } from '../../config-context' + +export interface MultilLocaleMetaInformation { + [key: string]: Sides[] +} + +const MenuSticker = () => { + const theme = useTheme() + const { pathname } = useRouter() + const { updateSides, updateTabbarFixed } = useConfigs() + const [fixed, setFixed, fixedRef] = useCurrentState(false) + + useEffect(() => updateTabbarFixed(fixed), [fixed]) + + const tabbarData = useMemo(() => { + const language = pathname + .split('/') + .filter(r => !!r) + const locale: string = language[0] || 'en-us' + return (sides as MultilLocaleMetaInformation)[locale] + }, [pathname, sides]) + + const currentTabValue = useMemo(() => { + const language = pathname + .split('/') + .filter(r => !!r) + return language[1] + }, [pathname]) + + + useEffect(() => { + const scrollHandler = () => { + const shouldFixed = document.documentElement.scrollTop > 60 + if (shouldFixed === fixedRef.current) return + setFixed(shouldFixed) + } + document.addEventListener('scroll', scrollHandler) + return () => document.removeEventListener('scroll', scrollHandler) + }, []) + + const tabChangeHandler = (value: string) => { + const currentTab = tabbarData.find(tab => tab.name === value) + if (!currentTab || !Array.isArray(currentTab.children)) return + + let firstChildren = currentTab.children + if (Array.isArray(firstChildren[0].children)) { + firstChildren = firstChildren[0].children + } + + const defaultPath = firstChildren[0].url + if (!defaultPath) return + updateSides(currentTab.children) + Router.push(defaultPath) + } + + useEffect(() => { + tabbarData && tabChangeHandler(currentTabValue) + }, []) + + return ( + <> +
+ + + + ) +} + +export default MenuSticker diff --git a/lib/components/sidebar/index.tsx b/lib/components/sidebar/index.tsx index bee74be..5cb90fd 100644 --- a/lib/components/sidebar/index.tsx +++ b/lib/components/sidebar/index.tsx @@ -56,7 +56,7 @@ export const Sidebar: React.FC = React.memo(({ sides }) => { .box { overflow-y: auto; overflow-x: hidden; - height: calc(100vh - 140px); + height: 100%; display: flex; flex-direction: column; align-items: center; diff --git a/lib/config-context.ts b/lib/config-context.ts index 74e2225..64f7907 100644 --- a/lib/config-context.ts +++ b/lib/config-context.ts @@ -1,4 +1,5 @@ import React from 'react' +import { Sides } from 'lib/components/sidebar/side-item' export interface Configs { onChange?: Function @@ -6,12 +7,24 @@ export interface Configs { updateChineseState: Function sidebarScrollHeight: number updateSidebarScrollHeight: Function + + sides: Sides[] + updateSides: Function + + tabbarFixed: boolean + updateTabbarFixed: Function } export const defaultConfigs: Configs = { sidebarScrollHeight: 0, updateSidebarScrollHeight: () => {}, updateChineseState: () => {}, + + sides: [], + updateSides: () => {}, + + tabbarFixed: false, + updateTabbarFixed: () => {}, } export const ConfigContext = React.createContext(defaultConfigs) diff --git a/lib/config-provider.tsx b/lib/config-provider.tsx index 31d8acf..5f5d8f3 100644 --- a/lib/config-provider.tsx +++ b/lib/config-provider.tsx @@ -2,6 +2,7 @@ import React, { useMemo, useState } from 'react' import withDefaults from 'components/utils/with-defaults' import { ConfigContext, Configs } from 'lib/config-context' import { useRouter } from 'next/router' +import { Sides } from 'lib/components/sidebar/side-item' interface Props { onChange?: Function @@ -18,16 +19,21 @@ const ConfigProvider: React.FC> = R const { pathname } = useRouter() const [isChinese, setIsChinese] = useState(() => pathname.includes('zh-cn')) const [scrollHeight, setScrollHeight] = useState(0) + const [sides, setSides] = useState([] as Sides[]) + const [tabbarFixed, setTabbarFixed] = useState(false) const updateSidebarScrollHeight = (height: number) => setScrollHeight(height) const updateChineseState = (state: boolean) => setIsChinese(state) + const updateSides = (sides: Sides[]) => setSides(sides) + const updateTabbarFixed = (state: boolean) => setTabbarFixed(state) const initialValue = useMemo(() => ({ - onChange, - isChinese, + onChange, sides, isChinese, tabbarFixed, + updateSides, + updateTabbarFixed, updateChineseState, sidebarScrollHeight: scrollHeight, updateSidebarScrollHeight, - }), [onChange, scrollHeight]) + }), [onChange, scrollHeight, sides, tabbarFixed]) return ( diff --git a/next.config.js b/next.config.js index 9820534..29011b8 100644 --- a/next.config.js +++ b/next.config.js @@ -30,9 +30,29 @@ const nextConfig = { redirects() { return [ { - source: '/docs/:path*', + source: '/docs/getting-started/:path*', permanent: true, - destination: '/en-us/:path*' + destination: '/en-us/guide/:path*' + }, + { + source: '/en-us/getting-started/:path*', + permanent: true, + destination: '/en-us/guide/:path*' + }, + { + source: '/en-us/customization/:path*', + permanent: true, + destination: '/en-us/guide/:path*' + }, + { + source: '/zh-cn/getting-started/:path*', + permanent: true, + destination: '/zh-cn/guide/:path*' + }, + { + source: '/zh-cn/customization/:path*', + permanent: true, + destination: '/zh-cn/guide/:path*' }, { source: '/zh-cn/', diff --git a/pages/_app.tsx b/pages/_app.tsx index 151c4fb..333a8b3 100644 --- a/pages/_app.tsx +++ b/pages/_app.tsx @@ -3,6 +3,7 @@ import { NextPage } from 'next' import { AppProps } from 'next/app' import { useCallback, useState } from 'react' import { CSSBaseline, ZEITUIProvider, useTheme } from 'components' +import Menu from 'lib/components/menu' import ConfigContext from 'lib/config-provider' const Application: NextPage = ({ Component, pageProps }) => { @@ -33,6 +34,7 @@ const Application: NextPage = ({ Component, pageProps }) => { +