Sketch
SketchDocs
by FileKit Studio

SSR & Next.js

How to safely mount HTML5 canvas components in Next.js App Router without hydration errors.

Next.js & SSR Integration

Because @filekit-studio/sketch and @filekit-studio/diagram use HTML5 Canvas (CanvasRenderingContext2D), they require the browser's window and document DOM APIs.

If Next.js attempts to pre-render the canvas on the Node.js server during SSR, you will encounter:

ReferenceError: window is not defined

The Solution: Dynamic Import (ssr: false)

To prevent hydration mismatches and server-side evaluation errors, use next/dynamic with { ssr: false }:

components/diagram-client.tsx
"use client";

import dynamic from "next/dynamic";
import type { DiagramData } from "@filekit-studio/diagram";

// Dynamically import Diagram with SSR disabled
const Diagram = dynamic(
  () => import("@filekit-studio/diagram").then((mod) => mod.Diagram),
  {
    ssr: false,
    loading: () => (
      <div className="w-full h-[400px] flex items-center justify-center bg-neutral-100 dark:bg-neutral-900 rounded-xl">
        <span className="text-sm text-neutral-500 animate-pulse">Loading diagram canvas...</span>
      </div>
    ),
  }
);

export function MyDiagramView({ data }: { data: DiagramData }) {
  return (
    <div className="w-full h-[500px] rounded-xl overflow-hidden border">
      <Diagram data={data} autoFit={true} mode="viewer" />
    </div>
  );
}

Dark Mode Theme Synchronization

Both @filekit-studio/sketch and @filekit-studio/diagram adapt automatically to light and dark themes.

If you are using next-themes, pass the resolved theme directly to the component:

TypeScript (TSX)
"use client";

import { useTheme } from "next-themes";
import { Diagram, type DiagramData } from "@filekit-studio/diagram";

export function ThemedDiagram({ data }: { data: DiagramData }) {
  const { resolvedTheme } = useTheme();
  const isDark = resolvedTheme === "dark";

  return (
    <Diagram
      data={data}
      theme={isDark ? "dark" : "light"}
      canvasBackground={isDark ? "#12141a" : "#f0f4f8"}
      mode="viewer"
      autoFit={true}
    />
  );
}

Memory Management

When unmounting <SketchEditor /> or exporting images, the SDK automatically manages and cleans up object URLs to prevent browser memory leaks.

If you create custom object URLs for assets in your own wrapper components, always revoke them:

TypeScript (TSX)
useEffect(() => {
  return () => {
    if (previewUrl) {
      URL.revokeObjectURL(previewUrl);
    }
  };
}, [previewUrl]);

On this page