mirror of
https://github.com/makeplane/plane
synced 2024-06-14 14:31:34 +00:00
fix: build errors in docs (#204)
This commit is contained in:
parent
2cb708c63b
commit
143ba75604
@ -24,14 +24,8 @@
|
|||||||
// }
|
// }
|
||||||
{
|
{
|
||||||
"extends": "tsconfig/nextjs.json",
|
"extends": "tsconfig/nextjs.json",
|
||||||
"include": [
|
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
|
||||||
"next-env.d.ts",
|
"exclude": ["node_modules"],
|
||||||
"**/*.ts",
|
|
||||||
"**/*.tsx"
|
|
||||||
],
|
|
||||||
"exclude": [
|
|
||||||
"node_modules"
|
|
||||||
],
|
|
||||||
"compilerOptions": {
|
"compilerOptions": {
|
||||||
"baseUrl": ".",
|
"baseUrl": ".",
|
||||||
"jsx": "preserve"
|
"jsx": "preserve"
|
||||||
|
1
apps/docs/.eslintrc.js
Normal file
1
apps/docs/.eslintrc.js
Normal file
@ -0,0 +1 @@
|
|||||||
|
module.exports = require('config/.eslintrc')
|
@ -33,7 +33,7 @@ export function Button({
|
|||||||
arrow,
|
arrow,
|
||||||
...props
|
...props
|
||||||
}) {
|
}) {
|
||||||
let Component = props.href ? Link : 'button'
|
const Component = props.href ? Link : 'button'
|
||||||
|
|
||||||
className = clsx(
|
className = clsx(
|
||||||
'inline-flex gap-0.5 justify-center overflow-hidden text-sm font-medium transition',
|
'inline-flex gap-0.5 justify-center overflow-hidden text-sm font-medium transition',
|
||||||
@ -41,7 +41,7 @@ export function Button({
|
|||||||
className
|
className
|
||||||
)
|
)
|
||||||
|
|
||||||
let arrowIcon = (
|
const arrowIcon = (
|
||||||
<ArrowIcon
|
<ArrowIcon
|
||||||
className={clsx(
|
className={clsx(
|
||||||
'mt-0.5 h-5 w-5',
|
'mt-0.5 h-5 w-5',
|
||||||
|
@ -44,12 +44,12 @@ function ClipboardIcon(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function CopyButton({ code }) {
|
function CopyButton({ code }) {
|
||||||
let [copyCount, setCopyCount] = useState(0)
|
const [copyCount, setCopyCount] = useState(0)
|
||||||
let copied = copyCount > 0
|
const copied = copyCount > 0
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (copyCount > 0) {
|
if (copyCount > 0) {
|
||||||
let timeout = setTimeout(() => setCopyCount(0), 1000)
|
const timeout = setTimeout(() => setCopyCount(0), 1000)
|
||||||
return () => {
|
return () => {
|
||||||
clearTimeout(timeout)
|
clearTimeout(timeout)
|
||||||
}
|
}
|
||||||
@ -117,7 +117,7 @@ function CodePanelHeader({ tag, label }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function CodePanel({ tag, label, code, children }) {
|
function CodePanel({ tag, label, code, children }) {
|
||||||
let child = Children.only(children)
|
const child = Children.only(children)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="group dark:bg-white/2.5">
|
<div className="group dark:bg-white/2.5">
|
||||||
@ -134,7 +134,7 @@ function CodePanel({ tag, label, code, children }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function CodeGroupHeader({ title, children, selectedIndex }) {
|
function CodeGroupHeader({ title, children, selectedIndex }) {
|
||||||
let hasTabs = Children.count(children) > 1
|
const hasTabs = Children.count(children) > 1
|
||||||
|
|
||||||
if (!title && !hasTabs) {
|
if (!title && !hasTabs) {
|
||||||
return null
|
return null
|
||||||
@ -168,7 +168,7 @@ function CodeGroupHeader({ title, children, selectedIndex }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function CodeGroupPanels({ children, ...props }) {
|
function CodeGroupPanels({ children, ...props }) {
|
||||||
let hasTabs = Children.count(children) > 1
|
const hasTabs = Children.count(children) > 1
|
||||||
|
|
||||||
if (hasTabs) {
|
if (hasTabs) {
|
||||||
return (
|
return (
|
||||||
@ -186,24 +186,25 @@ function CodeGroupPanels({ children, ...props }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function usePreventLayoutShift() {
|
function usePreventLayoutShift() {
|
||||||
let positionRef = useRef()
|
const positionRef = useRef()
|
||||||
let rafRef = useRef()
|
const rafRef = useRef()
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(
|
||||||
return () => {
|
() => () => {
|
||||||
window.cancelAnimationFrame(rafRef.current)
|
window.cancelAnimationFrame(rafRef.current)
|
||||||
}
|
},
|
||||||
}, [])
|
[]
|
||||||
|
)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
positionRef,
|
positionRef,
|
||||||
preventLayoutShift(callback) {
|
preventLayoutShift(callback) {
|
||||||
let initialTop = positionRef.current.getBoundingClientRect().top
|
const initialTop = positionRef.current.getBoundingClientRect().top
|
||||||
|
|
||||||
callback()
|
callback()
|
||||||
|
|
||||||
rafRef.current = window.requestAnimationFrame(() => {
|
rafRef.current = window.requestAnimationFrame(() => {
|
||||||
let newTop = positionRef.current.getBoundingClientRect().top
|
const newTop = positionRef.current.getBoundingClientRect().top
|
||||||
window.scrollBy(0, newTop - initialTop)
|
window.scrollBy(0, newTop - initialTop)
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
@ -224,18 +225,19 @@ const usePreferredLanguageStore = create((set) => ({
|
|||||||
}))
|
}))
|
||||||
|
|
||||||
function useTabGroupProps(availableLanguages) {
|
function useTabGroupProps(availableLanguages) {
|
||||||
let { preferredLanguages, addPreferredLanguage } = usePreferredLanguageStore()
|
const { preferredLanguages, addPreferredLanguage } =
|
||||||
let [selectedIndex, setSelectedIndex] = useState(0)
|
usePreferredLanguageStore()
|
||||||
let activeLanguage = [...availableLanguages].sort(
|
const [selectedIndex, setSelectedIndex] = useState(0)
|
||||||
|
const activeLanguage = [...availableLanguages].sort(
|
||||||
(a, z) => preferredLanguages.indexOf(z) - preferredLanguages.indexOf(a)
|
(a, z) => preferredLanguages.indexOf(z) - preferredLanguages.indexOf(a)
|
||||||
)[0]
|
)[0]
|
||||||
let languageIndex = availableLanguages.indexOf(activeLanguage)
|
const languageIndex = availableLanguages.indexOf(activeLanguage)
|
||||||
let newSelectedIndex = languageIndex === -1 ? selectedIndex : languageIndex
|
const newSelectedIndex = languageIndex === -1 ? selectedIndex : languageIndex
|
||||||
if (newSelectedIndex !== selectedIndex) {
|
if (newSelectedIndex !== selectedIndex) {
|
||||||
setSelectedIndex(newSelectedIndex)
|
setSelectedIndex(newSelectedIndex)
|
||||||
}
|
}
|
||||||
|
|
||||||
let { positionRef, preventLayoutShift } = usePreventLayoutShift()
|
const { positionRef, preventLayoutShift } = usePreventLayoutShift()
|
||||||
|
|
||||||
return {
|
return {
|
||||||
as: 'div',
|
as: 'div',
|
||||||
@ -252,12 +254,14 @@ function useTabGroupProps(availableLanguages) {
|
|||||||
const CodeGroupContext = createContext(false)
|
const CodeGroupContext = createContext(false)
|
||||||
|
|
||||||
export function CodeGroup({ children, title, ...props }) {
|
export function CodeGroup({ children, title, ...props }) {
|
||||||
let languages = Children.map(children, (child) => getPanelTitle(child.props))
|
const languages = Children.map(children, (child) =>
|
||||||
let tabGroupProps = useTabGroupProps(languages)
|
getPanelTitle(child.props)
|
||||||
let hasTabs = Children.count(children) > 1
|
)
|
||||||
let Container = hasTabs ? Tab.Group : 'div'
|
const tabGroupProps = useTabGroupProps(languages)
|
||||||
let containerProps = hasTabs ? tabGroupProps : {}
|
const hasTabs = Children.count(children) > 1
|
||||||
let headerProps = hasTabs
|
const Container = hasTabs ? Tab.Group : 'div'
|
||||||
|
const containerProps = hasTabs ? tabGroupProps : {}
|
||||||
|
const headerProps = hasTabs
|
||||||
? { selectedIndex: tabGroupProps.selectedIndex }
|
? { selectedIndex: tabGroupProps.selectedIndex }
|
||||||
: {}
|
: {}
|
||||||
|
|
||||||
@ -277,7 +281,7 @@ export function CodeGroup({ children, title, ...props }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function Code({ children, ...props }) {
|
export function Code({ children, ...props }) {
|
||||||
let isGrouped = useContext(CodeGroupContext)
|
const isGrouped = useContext(CodeGroupContext)
|
||||||
|
|
||||||
if (isGrouped) {
|
if (isGrouped) {
|
||||||
return <code {...props} dangerouslySetInnerHTML={{ __html: children }} />
|
return <code {...props} dangerouslySetInnerHTML={{ __html: children }} />
|
||||||
@ -287,7 +291,7 @@ export function Code({ children, ...props }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function Pre({ children, ...props }) {
|
export function Pre({ children, ...props }) {
|
||||||
let isGrouped = useContext(CodeGroupContext)
|
const isGrouped = useContext(CodeGroupContext)
|
||||||
|
|
||||||
if (isGrouped) {
|
if (isGrouped) {
|
||||||
return children
|
return children
|
||||||
|
@ -65,7 +65,7 @@ const FeedbackThanks = forwardRef(function FeedbackThanks(_props, ref) {
|
|||||||
})
|
})
|
||||||
|
|
||||||
function Feedback() {
|
function Feedback() {
|
||||||
let [submitted, setSubmitted] = useState(false)
|
const [submitted, setSubmitted] = useState(false)
|
||||||
|
|
||||||
function onSubmit(event) {
|
function onSubmit(event) {
|
||||||
event.preventDefault()
|
event.preventDefault()
|
||||||
@ -124,9 +124,9 @@ function PageLink({ label, page, previous = false }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function PageNavigation() {
|
function PageNavigation() {
|
||||||
let router = useRouter()
|
const router = useRouter()
|
||||||
let allPages = navigation.flatMap((group) => group.links)
|
const allPages = navigation.flatMap((group) => group.links)
|
||||||
let currentPageIndex = allPages.findIndex(
|
const currentPageIndex = allPages.findIndex(
|
||||||
(page) => page.href === router.pathname
|
(page) => page.href === router.pathname
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -134,8 +134,8 @@ function PageNavigation() {
|
|||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
let previousPage = allPages[currentPageIndex - 1]
|
const previousPage = allPages[currentPageIndex - 1]
|
||||||
let nextPage = allPages[currentPageIndex + 1]
|
const nextPage = allPages[currentPageIndex + 1]
|
||||||
|
|
||||||
if (!previousPage && !nextPage) {
|
if (!previousPage && !nextPage) {
|
||||||
return null
|
return null
|
||||||
@ -207,7 +207,10 @@ function SmallPrint() {
|
|||||||
<SocialLink href="https://github.com/makeplane" icon={GitHubIcon}>
|
<SocialLink href="https://github.com/makeplane" icon={GitHubIcon}>
|
||||||
Follow us on GitHub
|
Follow us on GitHub
|
||||||
</SocialLink>
|
</SocialLink>
|
||||||
<SocialLink href="https://discord.com/invite/A92xrEGCge" icon={DiscordIcon}>
|
<SocialLink
|
||||||
|
href="https://discord.com/invite/A92xrEGCge"
|
||||||
|
icon={DiscordIcon}
|
||||||
|
>
|
||||||
Join our Discord server
|
Join our Discord server
|
||||||
</SocialLink>
|
</SocialLink>
|
||||||
</div>
|
</div>
|
||||||
@ -216,7 +219,7 @@ function SmallPrint() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function Footer() {
|
export function Footer() {
|
||||||
let router = useRouter()
|
const router = useRouter()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<footer className="mx-auto max-w-2xl space-y-10 pb-16 lg:max-w-5xl">
|
<footer className="mx-auto max-w-2xl space-y-10 pb-16 lg:max-w-5xl">
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import { useId } from 'react'
|
import { useId } from 'react'
|
||||||
|
|
||||||
export function GridPattern({ width, height, x, y, squares, ...props }) {
|
export function GridPattern({ width, height, x, y, squares, ...props }) {
|
||||||
let patternId = useId()
|
const patternId = useId()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<svg aria-hidden="true" {...props}>
|
<svg aria-hidden="true" {...props}>
|
||||||
|
@ -8,8 +8,8 @@ import { Logo } from '@/components/Logo'
|
|||||||
import {
|
import {
|
||||||
MobileNavigation,
|
MobileNavigation,
|
||||||
useIsInsideMobileNavigation,
|
useIsInsideMobileNavigation,
|
||||||
|
useMobileNavigationStore,
|
||||||
} from '@/components/MobileNavigation'
|
} from '@/components/MobileNavigation'
|
||||||
import { useMobileNavigationStore } from '@/components/MobileNavigation'
|
|
||||||
import { ModeToggle } from '@/components/ModeToggle'
|
import { ModeToggle } from '@/components/ModeToggle'
|
||||||
import { MobileSearch, Search } from '@/components/Search'
|
import { MobileSearch, Search } from '@/components/Search'
|
||||||
|
|
||||||
@ -27,12 +27,12 @@ function TopLevelNavItem({ href, children }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const Header = forwardRef(function Header({ className }, ref) {
|
export const Header = forwardRef(function Header({ className }, ref) {
|
||||||
let { isOpen: mobileNavIsOpen } = useMobileNavigationStore()
|
const { isOpen: mobileNavIsOpen } = useMobileNavigationStore()
|
||||||
let isInsideMobileNavigation = useIsInsideMobileNavigation()
|
const isInsideMobileNavigation = useIsInsideMobileNavigation()
|
||||||
|
|
||||||
let { scrollY } = useScroll()
|
const { scrollY } = useScroll()
|
||||||
let bgOpacityLight = useTransform(scrollY, [0, 72], [0.5, 0.9])
|
const bgOpacityLight = useTransform(scrollY, [0, 72], [0.5, 0.9])
|
||||||
let bgOpacityDark = useTransform(scrollY, [0, 72], [0.2, 0.8])
|
const bgOpacityDark = useTransform(scrollY, [0, 72], [0.2, 0.8])
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<motion.div
|
<motion.div
|
||||||
@ -62,15 +62,21 @@ export const Header = forwardRef(function Header({ className }, ref) {
|
|||||||
<div className="flex items-center gap-5 lg:hidden">
|
<div className="flex items-center gap-5 lg:hidden">
|
||||||
<MobileNavigation />
|
<MobileNavigation />
|
||||||
<Link href="/" aria-label="Home">
|
<Link href="/" aria-label="Home">
|
||||||
<Logo />
|
<Logo />
|
||||||
</Link>
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex items-center gap-5">
|
<div className="flex items-center gap-5">
|
||||||
<nav className="hidden md:block">
|
<nav className="hidden md:block">
|
||||||
<ul role="list" className="flex items-center gap-8">
|
<ul role="list" className="flex items-center gap-8">
|
||||||
<TopLevelNavItem href="https://plane.so/">Plane Cloud</TopLevelNavItem>
|
<TopLevelNavItem href="https://plane.so/">
|
||||||
<TopLevelNavItem href="https://github.com/makeplane/plane">GitHub</TopLevelNavItem>
|
Plane Cloud
|
||||||
<TopLevelNavItem href="https://discord.com/invite/A92xrEGCge">Discord | Support</TopLevelNavItem>
|
</TopLevelNavItem>
|
||||||
|
<TopLevelNavItem href="https://github.com/makeplane/plane">
|
||||||
|
GitHub
|
||||||
|
</TopLevelNavItem>
|
||||||
|
<TopLevelNavItem href="https://discord.com/invite/A92xrEGCge">
|
||||||
|
Discord | Support
|
||||||
|
</TopLevelNavItem>
|
||||||
</ul>
|
</ul>
|
||||||
</nav>
|
</nav>
|
||||||
<div className="hidden md:block md:h-5 md:w-px md:bg-zinc-900/10 md:dark:bg-white/15" />
|
<div className="hidden md:block md:h-5 md:w-px md:bg-zinc-900/10 md:dark:bg-white/15" />
|
||||||
|
@ -65,11 +65,11 @@ export function Heading({
|
|||||||
anchor = true,
|
anchor = true,
|
||||||
...props
|
...props
|
||||||
}) {
|
}) {
|
||||||
let Component = `h${level}`
|
const Component = `h${level}`
|
||||||
let ref = useRef()
|
const ref = useRef()
|
||||||
let registerHeading = useSectionStore((s) => s.registerHeading)
|
const registerHeading = useSectionStore((s) => s.registerHeading)
|
||||||
|
|
||||||
let inView = useInView(ref, {
|
const inView = useInView(ref, {
|
||||||
margin: `${remToPx(-3.5)}px 0px 0px 0px`,
|
margin: `${remToPx(-3.5)}px 0px 0px 0px`,
|
||||||
amount: 'all',
|
amount: 'all',
|
||||||
})
|
})
|
||||||
|
@ -8,7 +8,6 @@ import { Navigation } from '@/components/Navigation'
|
|||||||
import { Prose } from '@/components/Prose'
|
import { Prose } from '@/components/Prose'
|
||||||
import { SectionProvider } from '@/components/SectionProvider'
|
import { SectionProvider } from '@/components/SectionProvider'
|
||||||
|
|
||||||
|
|
||||||
export function Layout({ children, sections = [] }) {
|
export function Layout({ children, sections = [] }) {
|
||||||
return (
|
return (
|
||||||
<SectionProvider sections={sections}>
|
<SectionProvider sections={sections}>
|
||||||
@ -19,11 +18,7 @@ export function Layout({ children, sections = [] }) {
|
|||||||
>
|
>
|
||||||
<div className="hidden lg:flex">
|
<div className="hidden lg:flex">
|
||||||
<Link href="/" aria-label="Home">
|
<Link href="/" aria-label="Home">
|
||||||
<Logo />
|
<Logo />
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
</Link>
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
<Header />
|
<Header />
|
||||||
|
@ -1,5 +1,10 @@
|
|||||||
export function Logo() {
|
export function Logo() {
|
||||||
return (
|
return (
|
||||||
<img src="https://camo.githubusercontent.com/ef32512ae486a8cef8e000e74b2ff11c92c89c2cadb2d79674c6bd1599b99a56/68747470733a2f2f696b2e696d6167656b69742e696f2f77326f6b77627475322f706c616e652d6c6f676f5f306d383378756537522e706e673f696b2d73646b2d76657273696f6e3d6a6176617363726970742d312e342e33267570646174656441743d31363638383632373137303834" height={100} width={100} alt="Plane"/>
|
<img
|
||||||
|
src="https://camo.githubusercontent.com/ef32512ae486a8cef8e000e74b2ff11c92c89c2cadb2d79674c6bd1599b99a56/68747470733a2f2f696b2e696d6167656b69742e696f2f77326f6b77627475322f706c616e652d6c6f676f5f306d383378756537522e706e673f696b2d73646b2d76657273696f6e3d6a6176617363726970742d312e342e33267570646174656441743d31363638383632373137303834"
|
||||||
|
height={100}
|
||||||
|
width={100}
|
||||||
|
alt="Plane"
|
||||||
|
/>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -48,9 +48,9 @@ export const useMobileNavigationStore = create((set) => ({
|
|||||||
}))
|
}))
|
||||||
|
|
||||||
export function MobileNavigation() {
|
export function MobileNavigation() {
|
||||||
let isInsideMobileNavigation = useIsInsideMobileNavigation()
|
const isInsideMobileNavigation = useIsInsideMobileNavigation()
|
||||||
let { isOpen, toggle, close } = useMobileNavigationStore()
|
const { isOpen, toggle, close } = useMobileNavigationStore()
|
||||||
let ToggleIcon = isOpen ? XIcon : MenuIcon
|
const ToggleIcon = isOpen ? XIcon : MenuIcon
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<IsInsideMobileNavigationContext.Provider value={true}>
|
<IsInsideMobileNavigationContext.Provider value={true}>
|
||||||
|
@ -29,9 +29,9 @@ export function ModeToggle() {
|
|||||||
function toggleMode() {
|
function toggleMode() {
|
||||||
disableTransitionsTemporarily()
|
disableTransitionsTemporarily()
|
||||||
|
|
||||||
let darkModeMediaQuery = window.matchMedia('(prefers-color-scheme: dark)')
|
const darkModeMediaQuery = window.matchMedia('(prefers-color-scheme: dark)')
|
||||||
let isSystemDarkMode = darkModeMediaQuery.matches
|
const isSystemDarkMode = darkModeMediaQuery.matches
|
||||||
let isDarkMode = document.documentElement.classList.toggle('dark')
|
const isDarkMode = document.documentElement.classList.toggle('dark')
|
||||||
|
|
||||||
if (isDarkMode === isSystemDarkMode) {
|
if (isDarkMode === isSystemDarkMode) {
|
||||||
delete window.localStorage.isDarkMode
|
delete window.localStorage.isDarkMode
|
||||||
|
@ -11,7 +11,7 @@ import { Tag } from '@/components/Tag'
|
|||||||
import { remToPx } from '@/lib/remToPx'
|
import { remToPx } from '@/lib/remToPx'
|
||||||
|
|
||||||
function useInitialValue(value, condition = true) {
|
function useInitialValue(value, condition = true) {
|
||||||
let initialValue = useRef(value).current
|
const initialValue = useRef(value).current
|
||||||
return condition ? initialValue : value
|
return condition ? initialValue : value
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -52,7 +52,7 @@ function NavLink({ href, tag, active, isAnchorLink = false, children }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function VisibleSectionHighlight({ group, pathname }) {
|
function VisibleSectionHighlight({ group, pathname }) {
|
||||||
let [sections, visibleSections] = useInitialValue(
|
const [sections, visibleSections] = useInitialValue(
|
||||||
[
|
[
|
||||||
useSectionStore((s) => s.sections),
|
useSectionStore((s) => s.sections),
|
||||||
useSectionStore((s) => s.visibleSections),
|
useSectionStore((s) => s.visibleSections),
|
||||||
@ -60,18 +60,18 @@ function VisibleSectionHighlight({ group, pathname }) {
|
|||||||
useIsInsideMobileNavigation()
|
useIsInsideMobileNavigation()
|
||||||
)
|
)
|
||||||
|
|
||||||
let isPresent = useIsPresent()
|
const isPresent = useIsPresent()
|
||||||
let firstVisibleSectionIndex = Math.max(
|
const firstVisibleSectionIndex = Math.max(
|
||||||
0,
|
0,
|
||||||
[{ id: '_top' }, ...sections].findIndex(
|
[{ id: '_top' }, ...sections].findIndex(
|
||||||
(section) => section.id === visibleSections[0]
|
(section) => section.id === visibleSections[0]
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
let itemHeight = remToPx(2)
|
const itemHeight = remToPx(2)
|
||||||
let height = isPresent
|
const height = isPresent
|
||||||
? Math.max(1, visibleSections.length) * itemHeight
|
? Math.max(1, visibleSections.length) * itemHeight
|
||||||
: itemHeight
|
: itemHeight
|
||||||
let top =
|
const top =
|
||||||
group.links.findIndex((link) => link.href === pathname) * itemHeight +
|
group.links.findIndex((link) => link.href === pathname) * itemHeight +
|
||||||
firstVisibleSectionIndex * itemHeight
|
firstVisibleSectionIndex * itemHeight
|
||||||
|
|
||||||
@ -88,10 +88,12 @@ function VisibleSectionHighlight({ group, pathname }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function ActivePageMarker({ group, pathname }) {
|
function ActivePageMarker({ group, pathname }) {
|
||||||
let itemHeight = remToPx(2)
|
const itemHeight = remToPx(2)
|
||||||
let offset = remToPx(0.25)
|
const offset = remToPx(0.25)
|
||||||
let activePageIndex = group.links.findIndex((link) => link.href === pathname)
|
const activePageIndex = group.links.findIndex(
|
||||||
let top = offset + activePageIndex * itemHeight
|
(link) => link.href === pathname
|
||||||
|
)
|
||||||
|
const top = offset + activePageIndex * itemHeight
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<motion.div
|
<motion.div
|
||||||
@ -109,13 +111,13 @@ function NavigationGroup({ group, className }) {
|
|||||||
// If this is the mobile navigation then we always render the initial
|
// If this is the mobile navigation then we always render the initial
|
||||||
// state, so that the state does not change during the close animation.
|
// state, so that the state does not change during the close animation.
|
||||||
// The state will still update when we re-open (re-render) the navigation.
|
// The state will still update when we re-open (re-render) the navigation.
|
||||||
let isInsideMobileNavigation = useIsInsideMobileNavigation()
|
const isInsideMobileNavigation = useIsInsideMobileNavigation()
|
||||||
let [router, sections] = useInitialValue(
|
const [router, sections] = useInitialValue(
|
||||||
[useRouter(), useSectionStore((s) => s.sections)],
|
[useRouter(), useSectionStore((s) => s.sections)],
|
||||||
isInsideMobileNavigation
|
isInsideMobileNavigation
|
||||||
)
|
)
|
||||||
|
|
||||||
let isActiveGroup =
|
const isActiveGroup =
|
||||||
group.links.findIndex((link) => link.href === router.pathname) !== -1
|
group.links.findIndex((link) => link.href === router.pathname) !== -1
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
@ -71,8 +71,8 @@ function ResourceIcon({ icon: Icon }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function ResourcePattern({ mouseX, mouseY, ...gridProps }) {
|
function ResourcePattern({ mouseX, mouseY, ...gridProps }) {
|
||||||
let maskImage = useMotionTemplate`radial-gradient(180px at ${mouseX}px ${mouseY}px, white, transparent)`
|
const maskImage = useMotionTemplate`radial-gradient(180px at ${mouseX}px ${mouseY}px, white, transparent)`
|
||||||
let style = { maskImage, WebkitMaskImage: maskImage }
|
const style = { maskImage, WebkitMaskImage: maskImage }
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="pointer-events-none">
|
<div className="pointer-events-none">
|
||||||
@ -106,11 +106,11 @@ function ResourcePattern({ mouseX, mouseY, ...gridProps }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function Resource({ resource }) {
|
function Resource({ resource }) {
|
||||||
let mouseX = useMotionValue(0)
|
const mouseX = useMotionValue(0)
|
||||||
let mouseY = useMotionValue(0)
|
const mouseY = useMotionValue(0)
|
||||||
|
|
||||||
function onMouseMove({ currentTarget, clientX, clientY }) {
|
function onMouseMove({ currentTarget, clientX, clientY }) {
|
||||||
let { left, top } = currentTarget.getBoundingClientRect()
|
const { left, top } = currentTarget.getBoundingClientRect()
|
||||||
mouseX.set(clientX - left)
|
mouseX.set(clientX - left)
|
||||||
mouseY.set(clientY - top)
|
mouseY.set(clientY - top)
|
||||||
}
|
}
|
||||||
|
@ -12,11 +12,11 @@ const searchClient = algoliasearch(
|
|||||||
)
|
)
|
||||||
|
|
||||||
function useAutocomplete() {
|
function useAutocomplete() {
|
||||||
let id = useId()
|
const id = useId()
|
||||||
let router = useRouter()
|
const router = useRouter()
|
||||||
let [autocompleteState, setAutocompleteState] = useState({})
|
const [autocompleteState, setAutocompleteState] = useState({})
|
||||||
|
|
||||||
let [autocomplete] = useState(() =>
|
const [autocomplete] = useState(() =>
|
||||||
createAutocomplete({
|
createAutocomplete({
|
||||||
id,
|
id,
|
||||||
placeholder: 'Find something...',
|
placeholder: 'Find something...',
|
||||||
@ -74,13 +74,13 @@ function useAutocomplete() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function resolveResult(result) {
|
function resolveResult(result) {
|
||||||
let allLevels = Object.keys(result.hierarchy)
|
const allLevels = Object.keys(result.hierarchy)
|
||||||
let hierarchy = Object.entries(result._highlightResult.hierarchy).filter(
|
const hierarchy = Object.entries(result._highlightResult.hierarchy).filter(
|
||||||
([, { value }]) => Boolean(value)
|
([, { value }]) => Boolean(value)
|
||||||
)
|
)
|
||||||
let levels = hierarchy.map(([level]) => level)
|
const levels = hierarchy.map(([level]) => level)
|
||||||
|
|
||||||
let level =
|
const level =
|
||||||
result.type === 'content'
|
result.type === 'content'
|
||||||
? levels.pop()
|
? levels.pop()
|
||||||
: levels
|
: levels
|
||||||
@ -123,7 +123,7 @@ function NoResultsIcon(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function LoadingIcon(props) {
|
function LoadingIcon(props) {
|
||||||
let id = useId()
|
const id = useId()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<svg viewBox="0 0 20 20" fill="none" aria-hidden="true" {...props}>
|
<svg viewBox="0 0 20 20" fill="none" aria-hidden="true" {...props}>
|
||||||
@ -152,8 +152,8 @@ function LoadingIcon(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function SearchResult({ result, resultIndex, autocomplete, collection }) {
|
function SearchResult({ result, resultIndex, autocomplete, collection }) {
|
||||||
let id = useId()
|
const id = useId()
|
||||||
let { titleHtml, hierarchyHtml } = resolveResult(result)
|
const { titleHtml, hierarchyHtml } = resolveResult(result)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<li
|
<li
|
||||||
@ -234,7 +234,7 @@ const SearchInput = forwardRef(function SearchInput(
|
|||||||
{ autocomplete, autocompleteState, onClose },
|
{ autocomplete, autocompleteState, onClose },
|
||||||
inputRef
|
inputRef
|
||||||
) {
|
) {
|
||||||
let inputProps = autocomplete.getInputProps({})
|
const inputProps = autocomplete.getInputProps({})
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="group relative flex h-12">
|
<div className="group relative flex h-12">
|
||||||
@ -291,7 +291,7 @@ function AlgoliaLogo(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function SearchButton(props) {
|
function SearchButton(props) {
|
||||||
let [modifierKey, setModifierKey] = useState()
|
const [modifierKey, setModifierKey] = useState()
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setModifierKey(
|
setModifierKey(
|
||||||
@ -326,11 +326,11 @@ function SearchButton(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function SearchDialog({ open, setOpen, className }) {
|
function SearchDialog({ open, setOpen, className }) {
|
||||||
let router = useRouter()
|
const router = useRouter()
|
||||||
let formRef = useRef()
|
const formRef = useRef()
|
||||||
let panelRef = useRef()
|
const panelRef = useRef()
|
||||||
let inputRef = useRef()
|
const inputRef = useRef()
|
||||||
let { autocomplete, autocompleteState } = useAutocomplete()
|
const { autocomplete, autocompleteState } = useAutocomplete()
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!open) {
|
if (!open) {
|
||||||
@ -445,8 +445,8 @@ function SearchDialog({ open, setOpen, className }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function useSearchProps() {
|
function useSearchProps() {
|
||||||
let buttonRef = useRef()
|
const buttonRef = useRef()
|
||||||
let [open, setOpen] = useState(false)
|
const [open, setOpen] = useState(false)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
buttonProps: {
|
buttonProps: {
|
||||||
@ -458,7 +458,7 @@ function useSearchProps() {
|
|||||||
dialogProps: {
|
dialogProps: {
|
||||||
open,
|
open,
|
||||||
setOpen(open) {
|
setOpen(open) {
|
||||||
let { width, height } = buttonRef.current.getBoundingClientRect()
|
const { width, height } = buttonRef.current.getBoundingClientRect()
|
||||||
if (!open || (width !== 0 && height !== 0)) {
|
if (!open || (width !== 0 && height !== 0)) {
|
||||||
setOpen(open)
|
setOpen(open)
|
||||||
}
|
}
|
||||||
@ -468,8 +468,8 @@ function useSearchProps() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function Search() {
|
export function Search() {
|
||||||
let [modifierKey, setModifierKey] = useState()
|
const [modifierKey, setModifierKey] = useState()
|
||||||
let { buttonProps, dialogProps } = useSearchProps()
|
const { buttonProps, dialogProps } = useSearchProps()
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setModifierKey(
|
setModifierKey(
|
||||||
@ -497,7 +497,7 @@ export function Search() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function MobileSearch() {
|
export function MobileSearch() {
|
||||||
let { buttonProps, dialogProps } = useSearchProps()
|
const { buttonProps, dialogProps } = useSearchProps()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="contents lg:hidden">
|
<div className="contents lg:hidden">
|
||||||
|
@ -20,47 +20,45 @@ function createSectionStore(sections) {
|
|||||||
: { visibleSections }
|
: { visibleSections }
|
||||||
),
|
),
|
||||||
registerHeading: ({ id, ref, offsetRem }) =>
|
registerHeading: ({ id, ref, offsetRem }) =>
|
||||||
set((state) => {
|
set((state) => ({
|
||||||
return {
|
sections: state.sections.map((section) => {
|
||||||
sections: state.sections.map((section) => {
|
if (section.id === id) {
|
||||||
if (section.id === id) {
|
return {
|
||||||
return {
|
...section,
|
||||||
...section,
|
headingRef: ref,
|
||||||
headingRef: ref,
|
offsetRem,
|
||||||
offsetRem,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return section
|
}
|
||||||
}),
|
return section
|
||||||
}
|
}),
|
||||||
}),
|
})),
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
function useVisibleSections(sectionStore) {
|
function useVisibleSections(sectionStore) {
|
||||||
let setVisibleSections = useStore(sectionStore, (s) => s.setVisibleSections)
|
const setVisibleSections = useStore(sectionStore, (s) => s.setVisibleSections)
|
||||||
let sections = useStore(sectionStore, (s) => s.sections)
|
const sections = useStore(sectionStore, (s) => s.sections)
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
function checkVisibleSections() {
|
function checkVisibleSections() {
|
||||||
let { innerHeight, scrollY } = window
|
const { innerHeight, scrollY } = window
|
||||||
let newVisibleSections = []
|
const newVisibleSections = []
|
||||||
|
|
||||||
for (
|
for (
|
||||||
let sectionIndex = 0;
|
let sectionIndex = 0;
|
||||||
sectionIndex < sections.length;
|
sectionIndex < sections.length;
|
||||||
sectionIndex++
|
sectionIndex++
|
||||||
) {
|
) {
|
||||||
let { id, headingRef, offsetRem } = sections[sectionIndex]
|
const { id, headingRef, offsetRem } = sections[sectionIndex]
|
||||||
let offset = remToPx(offsetRem)
|
const offset = remToPx(offsetRem)
|
||||||
let top = headingRef.current.getBoundingClientRect().top + scrollY
|
const top = headingRef.current.getBoundingClientRect().top + scrollY
|
||||||
|
|
||||||
if (sectionIndex === 0 && top - offset > scrollY) {
|
if (sectionIndex === 0 && top - offset > scrollY) {
|
||||||
newVisibleSections.push('_top')
|
newVisibleSections.push('_top')
|
||||||
}
|
}
|
||||||
|
|
||||||
let nextSection = sections[sectionIndex + 1]
|
const nextSection = sections[sectionIndex + 1]
|
||||||
let bottom =
|
const bottom =
|
||||||
(nextSection?.headingRef.current.getBoundingClientRect().top ??
|
(nextSection?.headingRef.current.getBoundingClientRect().top ??
|
||||||
Infinity) +
|
Infinity) +
|
||||||
scrollY -
|
scrollY -
|
||||||
@ -78,7 +76,7 @@ function useVisibleSections(sectionStore) {
|
|||||||
setVisibleSections(newVisibleSections)
|
setVisibleSections(newVisibleSections)
|
||||||
}
|
}
|
||||||
|
|
||||||
let raf = window.requestAnimationFrame(() => checkVisibleSections())
|
const raf = window.requestAnimationFrame(() => checkVisibleSections())
|
||||||
window.addEventListener('scroll', checkVisibleSections, { passive: true })
|
window.addEventListener('scroll', checkVisibleSections, { passive: true })
|
||||||
window.addEventListener('resize', checkVisibleSections)
|
window.addEventListener('resize', checkVisibleSections)
|
||||||
|
|
||||||
@ -96,7 +94,7 @@ const useIsomorphicLayoutEffect =
|
|||||||
typeof window === 'undefined' ? useEffect : useLayoutEffect
|
typeof window === 'undefined' ? useEffect : useLayoutEffect
|
||||||
|
|
||||||
export function SectionProvider({ sections, children }) {
|
export function SectionProvider({ sections, children }) {
|
||||||
let [sectionStore] = useState(() => createSectionStore(sections))
|
const [sectionStore] = useState(() => createSectionStore(sections))
|
||||||
|
|
||||||
useVisibleSections(sectionStore)
|
useVisibleSections(sectionStore)
|
||||||
|
|
||||||
@ -112,6 +110,6 @@ export function SectionProvider({ sections, children }) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function useSectionStore(selector) {
|
export function useSectionStore(selector) {
|
||||||
let store = useContext(SectionStoreContext)
|
const store = useContext(SectionStoreContext)
|
||||||
return useStore(store, selector)
|
return useStore(store, selector)
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
export function remToPx(remValue) {
|
export function remToPx(remValue) {
|
||||||
let rootFontSize =
|
const rootFontSize =
|
||||||
typeof window === 'undefined'
|
typeof window === 'undefined'
|
||||||
? 16
|
? 16
|
||||||
: parseFloat(window.getComputedStyle(document.documentElement).fontSize)
|
: parseFloat(window.getComputedStyle(document.documentElement).fontSize)
|
||||||
|
@ -18,7 +18,7 @@ Router.events.on('routeChangeComplete', onRouteChange)
|
|||||||
Router.events.on('routeChangeError', onRouteChange)
|
Router.events.on('routeChangeError', onRouteChange)
|
||||||
|
|
||||||
export default function App({ Component, pageProps }) {
|
export default function App({ Component, pageProps }) {
|
||||||
let router = useRouter()
|
const router = useRouter()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
@ -39,7 +39,7 @@ export default function App({ Component, pageProps }) {
|
|||||||
defer
|
defer
|
||||||
data-domain="docs.plane.so"
|
data-domain="docs.plane.so"
|
||||||
src="https://plausible.io/js/script.js"
|
src="https://plausible.io/js/script.js"
|
||||||
></script>
|
/>
|
||||||
</>
|
</>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user