chroma
215 строк · 7.4 Кб
1import React, { createContext, useContext, useState } from 'react';
2import Head from 'next/head';
3import Link from 'next/link';
4import { GlobalStateContext, GlobalStateProvider } from '../components/layout/state';
5
6import {TopNav} from '../components/layout/TopNav';
7import {SideNav} from '../components/layout/SideNav';
8import {TableOfContents} from '../components/layout/TableOfContents';
9
10import { ThemeProvider } from 'next-themes'
11
12import '../public/globals.css'
13import 'katex/dist/katex.min.css';
14
15import type { AppProps } from 'next/app'
16import type { MarkdocNextJsPageProps } from '@markdoc/next.js'
17
18import { Inter, IBM_Plex_Mono } from 'next/font/google'
19// import IBM Plex Mono
20import { Toaster } from "../components/ui/toaster"
21import { Icons } from '../components/ui/icons';
22import { ThemeToggle } from '../components/ui/toggle-theme';
23import { Breadcrumb, BreadcrumbList, BreadcrumbItem, BreadcrumbLink, BreadcrumbSeparator, BreadcrumbPage } from '../components/ui/breadcrumb';
24import { useRouter } from 'next/router';
25
26const inter = Inter({
27subsets: ['latin'],
28display: 'swap',
29variable: '--font-inter',
30})
31
32const ibmPlexMono = IBM_Plex_Mono({
33subsets: ['latin'],
34display: 'swap',
35weight: "400",
36variable: '--font-ibm-plex-mono',
37})
38
39const TITLE = 'Markdoc';
40const DESCRIPTION = 'A powerful, flexible, Markdown-based authoring framework';
41
42function collectHeadings(node, sections = []) {
43if (node) {
44if (node.name === 'Heading') {
45const title = node.children[0];
46
47if (typeof title === 'string') {
48sections.push({
49...node.attributes,
50title
51});
52}
53}
54
55if (node.children) {
56for (const child of node.children) {
57collectHeadings(child, sections);
58}
59}
60}
61
62return sections;
63}
64
65const ROOT_ITEMS = require(`./_sidenav.js`).items;
66
67export type ChromaDocsProps = MarkdocNextJsPageProps
68
69export default function ChromaDocs({ Component, pageProps }: AppProps<ChromaDocsProps>) {
70const { markdoc } = pageProps;
71
72let title = TITLE;
73let description = DESCRIPTION;
74if (markdoc && (markdoc.frontmatter !== undefined)) {
75if (markdoc.frontmatter.title) {
76title = markdoc.frontmatter.title;
77}
78if (markdoc.frontmatter.description) {
79description = markdoc.frontmatter.description;
80}
81}
82
83const toc = pageProps.markdoc?.content
84? collectHeadings(pageProps.markdoc.content)
85: [];
86
87const router = useRouter()
88
89// get the pathname and figure out if we are in a group or not
90// this requires iterating through ROOT_ITEMS
91const pathname = router.pathname;
92let pathVar = router.asPath.split('/')[1] !== undefined ? router.asPath.split('/')[1] : '';
93let inGroup = false
94let groupObject = null
95// iterate through ROOT_ITEMS to see if pathVar is a group or not
96ROOT_ITEMS.map((item: any) => {
97if (item.href === `/${pathVar}` && item.type === 'group') {
98inGroup = true
99groupObject = item
100}
101})
102
103// if inGroup is true, then we need to build the breadcrumbs
104let breadcrumbs = []
105if (inGroup) {
106breadcrumbs.push({href: `/${pathVar}`, name: groupObject.title})
107}
108// if markdoc.frontmatter.title does not equal the groupObject.title, then we need to add it to our breadcrumbs
109// if the route is more than 1 level deep
110if (router.pathname.split('/').length > 2) {
111if (inGroup && (markdoc.frontmatter !== undefined) && markdoc.frontmatter.title !== groupObject.title) {
112breadcrumbs.push({href: `/${pathVar}/${markdoc.frontmatter.title}`, name: markdoc.frontmatter.title})
113}
114}
115
116const pageTitle = `${title}${title !== "Chroma" ? " | Chroma Docs": " Docs" }`
117
118return (
119<ThemeProvider>
120<main className={`${inter.variable} font-sans ${ibmPlexMono.variable}`} style={{paddingBottom: '200px'}}>
121<GlobalStateProvider>
122<Head>
123<title>{pageTitle}</title>
124<meta name="viewport" content="width=device-width, initial-scale=1.0" />
125<meta name="referrer" content="strict-origin" />
126<meta name="title" content={title} />
127<meta name="description" content={description} />
128<link rel="shortcut icon" href="/img/favicon.ico" />
129<link rel="icon" href="/img/favicon.ico" />
130<link
131rel="preconnect"
132href={`https://${process.env.NEXT_PUBLIC_ALGOLIA_APP_ID}-dsn.algolia.net`}
133crossOrigin=""
134/>
135</Head>
136<TopNav>
137<Link href="https://discord.gg/MMeYNTmh3x" className='hidden sm:block'>
138<img src="https://img.shields.io/discord/1073293645303795742"/>
139</Link>
140<Link href="https://github.com/chroma-core/chroma">
141<img src="https://img.shields.io/github/stars/chroma-core/chroma.svg?style=social&label=Star&maxAge=2400"/>
142</Link>
143<Link href="https://twitter.com/trychroma" className='hidden sm:block'>
144<img src="https://img.shields.io/twitter/follow/trychroma"/>
145</Link>
146<ThemeToggle/>
147</TopNav>
148<div className="flex flex-col space-y-8 lg:flex-row lg:space-x-12 lg:space-y-0 justify-between max-w-screen">
149<div className="block mt-[calc(var(--ifm-navbar-height)*-1)] transition-width w-[var(--doc-sidebar-width)] will-change-width clip-path-[inset(0)]">
150<div className="h-full overflow-y-scroll max-h-screen sticky top-0">
151<SideNav />
152</div>
153</div>
154
155<main className="max-w-screen-md article grow p-5 md:p-0 md:pt-8">
156
157{inGroup? (
158<Breadcrumb className='mb-8'>
159<BreadcrumbList>
160<BreadcrumbItem>
161<BreadcrumbLink href="/">Home</BreadcrumbLink>
162</BreadcrumbItem>
163<BreadcrumbSeparator />
164{breadcrumbs.map((item, index) => {
165return (
166<>
167<BreadcrumbItem key={index}>
168<BreadcrumbLink href={item.href}>{item.name}</BreadcrumbLink>
169</BreadcrumbItem>
170{/* if not the last item, add a BreadcrumbSeparator */}
171{index !== breadcrumbs.length - 1 ? (
172<BreadcrumbSeparator />
173) : (
174<></>
175)}
176</>
177)
178})}
179
180</BreadcrumbList>
181</Breadcrumb>
182) : <> </>}
183
184<div className='text-3xl mb-6 font-semibold'>{title}</div>
185<Component {...pageProps} />
186{/* <div className="mt-20">
187<a
188href={``}
189target="_blank"
190rel="noopener noreferrer"
191className="underline font-semibold"
192style={{textUnderlinePosition: 'under', textUnderlineOffset: '0.2em', textDecorationColor: '#bfbfbf'}}
193>
194<Icons.gitHub className="inline-block w-6 h-6 mr-2" />
195Edit this page on GitHub
196</a>
197</div> */}
198</main>
199
200<div className="block mt-[calc(var(--ifm-navbar-height)*-1)] transition-width w-[var(--doc-sidebar-width)] will-change-width clip-path-[inset(0)]"
201style={{margin: '0 !important'}}
202>
203<div className="h-full overflow-y-scroll max-h-screen sticky top-0">
204<TableOfContents toc={toc} />
205</div>
206</div>
207
208</div>
209<Toaster />
210</GlobalStateProvider>
211
212</main>
213</ThemeProvider>
214);
215}
216