45 lines
1.5 KiB
TypeScript
45 lines
1.5 KiB
TypeScript
import { Suspense } from "react";
|
|
import { SiteHeader } from "@/components/site-header";
|
|
import { SiteSidebar } from "@/components/site-sidebar";
|
|
import { SiteBottomNav } from "@/components/site-bottom-nav";
|
|
import { SiteFooter } from "@/components/site-footer";
|
|
import { VerifyEmailBanner } from "@/components/auth/verify-email-banner";
|
|
import { TextSelectionToolbar } from "@/components/text-selection-toolbar";
|
|
import { TextHighlighter } from "@/components/text-highlighter";
|
|
import { PageBookmarks } from "@/components/social/page-bookmarks";
|
|
import { PushPrompt } from "@/components/push/push-prompt";
|
|
|
|
/**
|
|
* Default app layout — the reading-app chrome that wraps the home page, all
|
|
* the book / letter / transcription / etc. routes, the user profile, and
|
|
* the auth pages.
|
|
*
|
|
* Sibling groups (e.g. `(legal)/`) opt out of this chrome by living in their
|
|
* own route group with their own layout. Everything in the root layout
|
|
* (providers, fonts, toaster, floating audio player) still wraps this layer.
|
|
*/
|
|
export default function AppLayout({
|
|
children,
|
|
}: {
|
|
children: React.ReactNode;
|
|
}) {
|
|
return (
|
|
<>
|
|
<VerifyEmailBanner />
|
|
<SiteSidebar />
|
|
<div className="flex-1 flex flex-col md:pl-16 pb-16 md:pb-0">
|
|
<SiteHeader />
|
|
{children}
|
|
<SiteFooter />
|
|
</div>
|
|
<SiteBottomNav />
|
|
<TextSelectionToolbar />
|
|
<Suspense fallback={null}>
|
|
<TextHighlighter />
|
|
</Suspense>
|
|
<PageBookmarks />
|
|
<PushPrompt />
|
|
</>
|
|
);
|
|
}
|