Skip to content

Commit 7c48ede

Browse files
ui(docs): implement toggle style for product switcher (#6114)
Co-authored-by: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com> Co-authored-by: Catherine Deskur <[email protected]>
1 parent 9063c49 commit 7c48ede

File tree

3 files changed

+53
-6
lines changed

3 files changed

+53
-6
lines changed

packages/fern-docs/bundle/src/app/[host]/[domain]/static/@productSelect/[slug]/page.tsx

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,12 @@ export default async function ProductSelectPage({
1818
const { host, domain, slug } = await params;
1919
const loader = await createCachedDocsLoader(host, domain, await getFernToken());
2020

21-
// preload:
22-
const [layout, _auth, _flags, root] = await Promise.all([
21+
const [layout, _auth, _flags, root, theme] = await Promise.all([
2322
loader.getLayout(),
2423
loader.getAuthState(),
2524
loader.getEdgeFlags(),
26-
loader.getRoot()
25+
loader.getRoot(),
26+
loader.getTheme()
2727
]);
2828
const useDenseLayout = layout.isHeaderDisabled;
2929

@@ -34,5 +34,12 @@ export default async function ProductSelectPage({
3434
return null;
3535
}
3636

37-
return <ProductDropdown loader={loader} fallbackProduct={fallbackProduct} useDenseLayout={useDenseLayout} />;
37+
return (
38+
<ProductDropdown
39+
loader={loader}
40+
fallbackProduct={fallbackProduct}
41+
useDenseLayout={useDenseLayout}
42+
productSwitcherTheme={theme?.productSwitcher}
43+
/>
44+
);
3845
}

packages/fern-docs/components/src/header/ProductDropdown.tsx

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import type { DocsLoader } from "@fern-api/docs-server/docs-loader";
22
import { createFileResolver } from "@fern-api/docs-server/file-resolver";
33
import { getProducts } from "@fern-api/docs-server/handle-node-fallbacks";
4+
import type { ProductSwitcherThemeConfig } from "@fern-api/docs-utils/types/theme-config";
45
import type { FernNavigation } from "@fern-api/fdr-sdk";
56
import Image from "next/image";
67
import { processIcon } from "../processIcon";
@@ -13,11 +14,13 @@ export declare namespace ProductDropdown {
1314
export async function ProductDropdown({
1415
loader,
1516
fallbackProduct,
16-
useDenseLayout = false
17+
useDenseLayout = false,
18+
productSwitcherTheme
1719
}: {
1820
loader: DocsLoader;
1921
fallbackProduct: FernNavigation.ProductNode;
2022
useDenseLayout?: boolean;
23+
productSwitcherTheme?: ProductSwitcherThemeConfig;
2124
}) {
2225
const root = await loader.getRoot();
2326
if (root.child.type !== "productgroup") {
@@ -71,6 +74,7 @@ export async function ProductDropdown({
7174
fallbackProduct={fallbackProduct}
7275
useDenseLayout={useDenseLayout}
7376
lang={lang}
77+
productSwitcherTheme={productSwitcherTheme}
7478
/>
7579
);
7680
}

packages/fern-docs/components/src/header/ProductDropdownClient.tsx

Lines changed: 37 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,13 @@
11
"use client";
22

33
import { slugToHref } from "@fern-api/docs-utils";
4+
import type { ProductSwitcherThemeConfig } from "@fern-api/docs-utils/types/theme-config";
45
import type { FernNavigation } from "@fern-api/fdr-sdk";
56
import { useIsDesktop } from "@fern-ui/react-commons";
67
import { ChevronDown, ChevronsUpDown } from "lucide-react";
78
import { cn } from "../cn";
89
import { FernDropdown } from "../FernDropdown";
10+
import { FernLink } from "../FernLink";
911
import { FernSelectionItem } from "../FernSelectionItem";
1012
import { useCurrentProductId, useCurrentProductSlug } from "../state/navigation";
1113

@@ -26,12 +28,14 @@ export function ProductDropdownClient({
2628
products,
2729
fallbackProduct,
2830
useDenseLayout = false,
29-
lang
31+
lang,
32+
productSwitcherTheme
3033
}: {
3134
products: ProductDropdownItem[];
3235
fallbackProduct: FernNavigation.ProductNode;
3336
useDenseLayout?: boolean;
3437
lang: string;
38+
productSwitcherTheme?: ProductSwitcherThemeConfig;
3539
}) {
3640
const isDesktop = useIsDesktop();
3741
const currentProductId = useCurrentProductId();
@@ -46,6 +50,38 @@ export function ProductDropdownClient({
4650
return null;
4751
}
4852

53+
const isToggleTheme = productSwitcherTheme === "toggle";
54+
55+
if (isToggleTheme && isDesktop) {
56+
return (
57+
<div className="fern-product-selector" data-testid="product-toggle">
58+
{products.map((product) => {
59+
const productHref =
60+
product.href ??
61+
slugToHref(
62+
pickProductSlug({
63+
currentProductSlug,
64+
defaultSlug: product.defaultSlug,
65+
slug: product.slug ?? ""
66+
})
67+
);
68+
const isActive = product.productId === currentProductId;
69+
return (
70+
<FernLink
71+
key={product.productId}
72+
href={productHref}
73+
target={product.target}
74+
className="product-dropdown-trigger"
75+
data-active={isActive}
76+
>
77+
{product.title}
78+
</FernLink>
79+
);
80+
})}
81+
</div>
82+
);
83+
}
84+
4985
return (
5086
<FernDropdown
5187
value={currentProductId}

0 commit comments

Comments
 (0)