diff --git a/docs/package.json b/docs/package.json
index 0e1cd3ded..950ebdd6b 100644
--- a/docs/package.json
+++ b/docs/package.json
@@ -23,6 +23,7 @@
"next": "^13.4.1",
"react": "^18.2.0",
"react-dom": "^18.2.0",
+ "react-focus-lock": "^2.9.4",
"shiki": "^0.14.2",
"typescript": "^5.0.2"
},
diff --git a/docs/src/app/docs/[slug]/page.tsx b/docs/src/app/(public)/docs/[slug]/page.tsx
similarity index 84%
rename from docs/src/app/docs/[slug]/page.tsx
rename to docs/src/app/(public)/docs/[slug]/page.tsx
index 61dadda3e..e8d3427a1 100644
--- a/docs/src/app/docs/[slug]/page.tsx
+++ b/docs/src/app/(public)/docs/[slug]/page.tsx
@@ -1,6 +1,6 @@
import { createReader } from '@keystatic/core/reader';
-import DocumentRenderer from '../../../components/document-renderer';
-import keystaticConfig from '../../../../keystatic.config';
+import DocumentRenderer from '../../../../components/document-renderer';
+import keystaticConfig from '../../../../../keystatic.config';
const reader = createReader('', keystaticConfig);
diff --git a/docs/src/app/(public)/docs/layout.tsx b/docs/src/app/(public)/docs/layout.tsx
new file mode 100644
index 000000000..7e126a9da
--- /dev/null
+++ b/docs/src/app/(public)/docs/layout.tsx
@@ -0,0 +1,55 @@
+import '../../../styles/global.css';
+import { SideNav } from '../../../components/navigation/side-nav';
+import { NavGroup } from '../../../components/navigation/nav-group';
+import { NavItem } from '../../../components/navigation/nav-item';
+import { DocsFooter } from '../../../components/footer';
+import { TableOfContents } from '../../../components/navigation/toc';
+import { getNavigationMap } from '../../../utils/reader';
+
+export const metadata = {
+ title: 'Keystatic - Docs',
+ description: 'Documentation for Keystatic.',
+};
+
+export default async function RootLayout({
+ children,
+}: {
+ children: React.ReactNode;
+}) {
+ const navigationMap = await getNavigationMap();
+
+ return (
+
+
+ {navigationMap?.map(({ groupName, items }) => (
+
+ {items.map(({ label, href, title }) => (
+
+ ))}
+
+ ))}
+
+
+ {/** CONTENT */}
+
+
+
+ {/** INNER CONTENT */}
+ {children}
+
+ {/** TOCs */}
+
+
+
+
+
+
+
+ );
+}
diff --git a/docs/src/app/docs/page.tsx b/docs/src/app/(public)/docs/page.tsx
similarity index 75%
rename from docs/src/app/docs/page.tsx
rename to docs/src/app/(public)/docs/page.tsx
index 1281fa1db..3f662338e 100644
--- a/docs/src/app/docs/page.tsx
+++ b/docs/src/app/(public)/docs/page.tsx
@@ -1,25 +1,9 @@
-import Button from '../../components/button';
+import Button from '../../../components/button';
export default function Docs() {
return (
<>
-
- Welcome to Keystatic{' '}
-
-
- Docs
-
-
+ Keystatic Docs
Keystatic is a new project from
diff --git a/docs/src/app/layout.tsx b/docs/src/app/(public)/layout.tsx
similarity index 76%
rename from docs/src/app/layout.tsx
rename to docs/src/app/(public)/layout.tsx
index f6b8bd4f2..5a351b743 100644
--- a/docs/src/app/layout.tsx
+++ b/docs/src/app/(public)/layout.tsx
@@ -1,10 +1,12 @@
import Head from 'next/head';
import { Analytics } from '@vercel/analytics/react';
-import '../styles/global.css';
+import '../../styles/global.css';
+import { HeaderNav } from '../../components/navigation/header-nav';
+import { getNavigationMap } from '../../utils/reader';
export const metadata = {
- title: 'Meet Keystatic',
+ title: 'Keystatic',
description:
"Keystatic is a new tool from Thinkmill Labs that opens up your code-based content (written in Markdown, JSON or YAML) to contributors who aren't technical.",
openGraph: {
@@ -26,11 +28,13 @@ export const metadata = {
},
};
-export default function RootLayout({
+export default async function RootLayout({
children,
}: {
children: React.ReactNode;
}) {
+ const navigationMap = await getNavigationMap();
+
return (
@@ -56,7 +60,14 @@ export default function RootLayout({
- {children}
+
+
+
+
+ {children}
+
+
+
);
diff --git a/docs/src/app/(public)/page.tsx b/docs/src/app/(public)/page.tsx
new file mode 100644
index 000000000..714e13884
--- /dev/null
+++ b/docs/src/app/(public)/page.tsx
@@ -0,0 +1,21 @@
+import Hero from '../../components/hero';
+import Intro from '../../components/intro';
+import Templates from '../../components/templates';
+import MailingList from '../../components/mailing-list';
+import CallToAction from '../../components/call-to-action';
+import Footer from '../../components/footer';
+
+export default function Homepage() {
+ return (
+ <>
+
+
+
+
+
+
+
+
+ >
+ );
+}
diff --git a/docs/src/app/(public)/privacy-policy/page.tsx b/docs/src/app/(public)/privacy-policy/page.tsx
new file mode 100644
index 000000000..ae78cd059
--- /dev/null
+++ b/docs/src/app/(public)/privacy-policy/page.tsx
@@ -0,0 +1,13 @@
+import PrivacyPolicy from '../../../components/privacy-policy';
+import Footer from '../../../components/footer';
+
+export default function PrivacyPolicyPage() {
+ return (
+ <>
+
+
+
+
+ >
+ );
+}
diff --git a/docs/src/app/thank-you/page.tsx b/docs/src/app/(public)/thank-you/page.tsx
similarity index 84%
rename from docs/src/app/thank-you/page.tsx
rename to docs/src/app/(public)/thank-you/page.tsx
index 6a8cf4d79..ef2585820 100644
--- a/docs/src/app/thank-you/page.tsx
+++ b/docs/src/app/(public)/thank-you/page.tsx
@@ -1,11 +1,9 @@
-import Navigation from '../../components/navigation';
-import Footer from '../../components/footer';
+import Footer from '../../../components/footer';
-export default function Index() {
+export default function ThankYouPage() {
return (
-
-
-
+ <>
+
@@ -34,6 +32,6 @@ export default function Index() {
-
+ >
);
}
diff --git a/docs/src/app/docs/layout.tsx b/docs/src/app/docs/layout.tsx
deleted file mode 100644
index 323de3698..000000000
--- a/docs/src/app/docs/layout.tsx
+++ /dev/null
@@ -1,93 +0,0 @@
-import Link from 'next/link';
-import Navigation from '../../components/navigation';
-import { NavContainer, NavList, NavItem } from '../../components/sidenav';
-import '../../styles/global.css';
-import keystaticConfig from '../../../keystatic.config';
-import { createReader } from '@keystatic/core/reader';
-
-const reader = createReader('', keystaticConfig);
-
-export const metadata = {
- title: 'Keystatic - docs',
- description: 'Documentation for Keystatic',
-};
-
-export default async function RootLayout({
- children,
-}: {
- children: React.ReactNode;
-}) {
- const navigation = await reader.singletons.navigation.read();
- const pages = await reader.collections.pages.all();
-
- const pagesBySlug = Object.fromEntries(pages.map(page => [page.slug, page]));
-
- const navigationMap = navigation?.navGroups.map(({ groupName, items }) => ({
- groupName,
- items: items.map(({ label, link }) => {
- const { discriminant, value } = link;
- const page = discriminant === 'page' && value ? pagesBySlug[value] : null;
- const url = discriminant === 'url' ? value : `/docs/${page?.slug}`;
- return {
- label: label || page?.entry.title || '',
- href: url || '',
- title: page?.entry.title,
- };
- }),
- }));
-
- return (
-
- {/** TOP NAV */}
-
-
-
-
- {/** MAIN */}
-
- {/** SIDE NAV */}
-
- {navigationMap?.map(({ groupName, items }) => (
-
- {items.map(({ label, href, title }) => (
-
- ))}
-
- ))}
-
-
- {/** CONTENT */}
-
-
- {/** INNER CONTENT (markdoc goes here) */}
-
-
{children}
-
-
-
- On this page
-
-
-
-
- {/** FOOTER */}
-
-
-
-
-
- );
-}
diff --git a/docs/src/app/page.tsx b/docs/src/app/page.tsx
deleted file mode 100644
index 19596f535..000000000
--- a/docs/src/app/page.tsx
+++ /dev/null
@@ -1,23 +0,0 @@
-import Navigation from '../components/navigation';
-import Hero from '../components/hero';
-import Intro from '../components/intro';
-import Templates from '../components/templates';
-import MailingList from '../components/mailing-list';
-import CallToAction from '../components/call-to-action';
-import Footer from '../components/footer';
-
-export default function Index() {
- return (
-
-
-
-
-
-
-
-
-
-
-
- );
-}
diff --git a/docs/src/app/privacy-policy/page.tsx b/docs/src/app/privacy-policy/page.tsx
deleted file mode 100644
index f443a56f5..000000000
--- a/docs/src/app/privacy-policy/page.tsx
+++ /dev/null
@@ -1,15 +0,0 @@
-import Navigation from '../../components/navigation';
-import PrivacyPolicy from '../../components/privacy-policy';
-import Footer from '../../components/footer';
-
-export default function PrivacyPolicyPage() {
- return (
-
- );
-}
diff --git a/docs/src/components/button.tsx b/docs/src/components/button.tsx
index ed83a2199..4e2b725ee 100644
--- a/docs/src/components/button.tsx
+++ b/docs/src/components/button.tsx
@@ -11,11 +11,11 @@ type ButtonProps = {
} & AllHTMLAttributes;
const baseClasses =
- 'block rounded-lg px-5 py-3 text-center font-semibold leading-none border';
+ 'block rounded-lg px-5 py-3 text-center font-semibold leading-none border transition-colors';
const impactClasses: Record = {
bold: 'rounded-lg bg-black px-5 py-3 text-center font-semibold leading-none text-white hover:bg-stone-800 border-transparent',
light:
- 'rounded-lg bg-transparent border-black text-black px-5 py-3 text-center font-semibold leading-none hover:bg-stone-800/10',
+ 'rounded-lg bg-transparent border-black text-black px-5 py-3 text-center font-semibold leading-none hover:bg-stone-800/10 active:bg-stone-800/20',
};
// ----------
diff --git a/docs/src/components/footer.tsx b/docs/src/components/footer.tsx
index 1102dfd8d..23deca5e6 100644
--- a/docs/src/components/footer.tsx
+++ b/docs/src/components/footer.tsx
@@ -1,23 +1,50 @@
import Link from 'next/link';
-
-import Navigation from './navigation';
+import { KeystaticLogoLink } from './navigation/keystatic-logo-link';
+import { SocialLinks } from './navigation/social-links';
export default function Footer() {
return (