@vizij/render
v0.0.7
Published
Higher-level visualization and interaction components for robot and ai faces.
Readme
@vizij/render
Three.js + React renderer, scene store, and helper controllers for Vizij faces.
This package exposes the Vizij canvas component along with hooks, stores, and GLTF helpers that power Vizij’s real-time character visualisation. It is the foundation that other packages (@vizij/rig, @vizij/orchestrator-react, etc.) build upon.
Table of Contents
- Overview
- Installation
- Usage
- Store & Hooks
- Controllers & Helpers
- Development & Testing
- Publishing
- Related Packages
Overview
Vizijrenders a fully managed@react-three/fibercanvas with sensible defaults for orthographic cameras and safe-area overlays.- A Zustand-powered store (
useVizijStore) tracks renderables, controllers, and transient state. Hooks let you read or mutate slices without re-rendering entire scenes. - Utilities (
loadGLTF,loadGLTFBlob, export helpers) streamline loading rigged GLTF assets and exporting scene snapshots. The tuple helpers now return[world, animatables, animations], whereanimationscontains parsed clip metadata for any channels embedded in the GLB. - Controllers wrap common behaviours (e.g., pointer interaction, safe-area visualisation) so you can compose features quickly.
Installation
# pnpm
pnpm add @vizij/render three @react-three/fiber @react-three/drei zustand @vizij/utils
# npm
npm install @vizij/render three @react-three/fiber @react-three/drei zustand @vizij/utils
# yarn
yarn add @vizij/render three @react-three/fiber @react-three/drei zustand @vizij/utilsPeer requirements:
react >= 18three >= 0.170@react-three/fiber >= 8@react-three/drei >= 9zustand >= 5- Optional UI integrations:
tailwindcss >= 4.1(declared as a peer for theme utilities)
Ensure these versions align with the rest of your app to avoid duplicate React or Three.js instances.
Usage
import { Vizij, useVizijStore } from "@vizij/render";
import { useEffect } from "react";
export function VizijCanvas() {
const setDebug = useVizijStore((state) => state.setDebugState);
useEffect(() => {
setDebug((debug) => ({ ...debug, showGrid: true }));
}, [setDebug]);
return (
<Vizij
rootId="default/root"
namespace="default"
showSafeArea
style={{ width: "100%", height: 480 }}
/>
);
}Wrap the component tree with VizijContext.Provider if you want to supply a custom store; otherwise the Vizij component creates one internally.
Store & Hooks
useVizijStore(selector?)– Access or mutate the renderer store with automatic subscription management.useVizijStoreGetter,useVizijStoreSetter,useVizijStoreSubscription– Fine-grained accessors when you need optimised reads/writes.useFeatures()– Inspect feature flags registered in the store.- Store types (
VizijData,VizijActions) are exported fromstore-typesfor strongly typed selectors.
The store tracks world graph entries, controllers, debug overlays, and renderable metadata. See src/store.ts for the full surface.
Controllers & Helpers
- Controllers under
src/controllersencapsulate input handling, camera logic, and other behaviours. Compose them with your own React components. loadGLTF/loadGLTFBlobsimplify loading rig assets and extract animatable metadata used by@vizij/rig.exporthelpers produce snapshots of the current scene (useful for tooling or exporting frames).
All exports are re-exported through src/index.tsx, so a simple import { loadGLTF } from "@vizij/render" works.
Dual-format Vizij bundles
Vizij scenes persist authoring metadata inside GLBs so third-party tools see baked animation, while Vizij runtimes retain orchestrator graphs and clips.
- Every renderable still carries a
RobotDataextension inuserDatadescribing features and animatable bindings. - The exporter now writes a root-level
extensions.VIZIJ_bundleblock following the schema insrc/types/vizij-bundle.ts. It contains rig graphs, pose configs, stored Vizij clips, and provenance hashes. - Use
exportScene(group, { bundle, animations })to embed both the Vizij bundle and optional bakedTHREE.AnimationClipinstances. The helper attaches the bundle only for the export call and restores the original object. - When loading assets, prefer
loadGLTFWithBundle/loadGLTFFromBlobWithBundleto retrieve{ world, animatables, bundle, animations }. The legacy tuple helpers return[world, animatables, animations]if you only need the renderer state. - The new
animationsfield exposesVizijAnimationClipData[], which maps each glTF animation channel back to Vizij animatable ids (RobotData.features.*.value.id). Each track provides component-awaretimes/valuesarrays so runtimes can register clips without re-parsing the GLB. extractVizijBundle(scene)andapplyVizijBundle(scene, bundle)(undersrc/functions/vizij-bundle.ts) let advanced tooling inspect or mutate bundles without triggering a fresh export.
With this structure, authoring tools can round-trip orchestrator assets while shipping native glTF animations for viewers that do not understand Vizij.
Development & Testing
pnpm --filter "@vizij/render" build
pnpm --filter "@vizij/render" test
pnpm --filter "@vizij/render" typecheck
pnpm --filter "@vizij/render" lint
pnpm --filter "@vizij/render" sizetsup produces both ESM and CJS bundles with type declarations. Tests run via Vitest (currently smoke-level), and size-limit guards against unexpected bundle growth.
Publishing
Use the shared workflow at .github/workflows/publish-npm.yml.
- Align dependency versions (
three,@react-three/*,zustand, Vizij packages) and generate a changeset:pnpm changeset pnpm version:packages - Validate locally:
pnpm install pnpm --filter "@vizij/render" build pnpm --filter "@vizij/render" test pnpm --filter "@vizij/render" typecheck pnpm --filter "@vizij/render" lint pnpm --filter "@vizij/render" exec npm pack --dry-run - Tag the release as
npm-render-vX.Y.Zand push the tag. The workflow will publish with provenance metadata.
Related Packages
@vizij/rig– Hooks that consume the renderer to load rigged models.@vizij/animation-react– React bindings that feed animation values back into the renderer.
Questions or contributions? Open an issue so we can keep the renderer API and docs sharp for the whole Vizij ecosystem. 🎨
