"use client"; import { useMemo, type ReactNode } from "react"; import { Renderer, type ComponentRegistry, type Spec, DataProvider, VisibilityProvider, ActionProvider, } from "@json-render/react"; import { components, Fallback } from "./catalog/components"; import { executeAction } from "./catalog/actions"; // ============================================================================= // PlaygroundRenderer // ============================================================================= interface PlaygroundRendererProps { spec: Spec | null; data?: Record; loading?: boolean; } // Build registry once - stable reference to prevent input focus loss function buildRegistry(loading?: boolean): ComponentRegistry { const registry: ComponentRegistry = {}; for (const [name, Component] of Object.entries(components)) { registry[name] = (renderProps: { element: { props: Record; type: string }; children?: ReactNode; }) => ( executeAction(a.name, a.params)} loading={loading} > {renderProps.children} ); } return registry; } // Fallback component for unknown types const fallbackRegistry = (renderProps: { element: { type: string } }) => ( ); export function PlaygroundRenderer({ spec, data, loading, }: PlaygroundRendererProps): ReactNode { // Memoize registry to prevent re-creating on every render const registry = useMemo(() => buildRegistry(loading), [loading]); if (!spec) return null; return ( ); }