Files
cadSet/text-to-cad/packages/implicitjs/README.md
T
2026-07-22 19:38:36 +08:00

203 lines
6.2 KiB
Markdown

# implicitjs
`implicitjs` is a standalone JavaScript runtime for browser-native implicit CAD
models. It defines the `.implicit.js` model schema, builds GLSL raymarch
shaders, renders models with Three.js, evaluates SDFs on the CPU, produces
headless PNG/GIF snapshots, samples meshes, checks mesh quality, and exports
STL, 3MF, and GLB artifacts.
The package is UI-framework agnostic. Applications provide their own editor,
catalog, sidebar, persistence, and product workflow; `implicitjs` provides the
model, rendering, snapshot, and export logic.
## Install
```bash
npm install implicitjs
```
Peer usage expects a modern ESM JavaScript environment. Rendering APIs require
Three.js-compatible WebGL support. The headless snapshot CLI uses Playwright.
## Model Format
An implicit model is an ES module that exports an `implicit.js/0.1.0` object.
The `glsl` string must provide `float sdf(vec3 p)`. It may also provide
`vec3 color(vec3 p, vec3 normal)` for procedural color.
```js
const GLSL = `
float sdf(vec3 p) {
return implicit_sphere(p, vec3(0.0), radius);
}
vec3 color(vec3 p, vec3 normal) {
return mix(vec3(0.0, 0.65, 1.0), vec3(1.0, 0.3, 0.8), normal.z * 0.5 + 0.5);
}
`;
export default {
schema: "implicit.js/0.1.0",
name: "parametric sphere",
units: "mm",
params: {
radius: { type: "number", label: "Radius", min: 5, max: 50, default: 22, unit: "mm" }
},
bounds: ({ params }) => {
const r = params.radius + 2;
return [[-r, -r, -r], [r, r, r]];
},
render: { steps: 192 },
glsl: GLSL
};
```
Number, boolean, color, and button params automatically become GLSL uniforms
with matching names. Use param names directly in GLSL; a separate `uniforms`
object is not needed.
`bounds` is optional and can be estimated from the SDF, but explicit bounds are
recommended for unusual fields, thin features, periodic models, animated size
changes, or export-heavy workflows.
Authored GLSL can use built-in helpers in the `implicit_*` namespace, such as
`implicit_sphere`, `implicit_box_centered`, `implicit_cylinder_capped`,
`implicit_line_segment2`, `implicit_union_round`, and
`implicit_intersect_round`.
## Public APIs
Common imports:
```js
import {
loadImplicitModuleFromSource,
normalizeImplicitModel,
renderImplicitToDataUrl,
snapshotImplicitCadModel,
exportImplicitModel,
exportImplicitAnimatedGlb
} from "implicitjs";
```
Useful subpath exports:
- `implicitjs/model`: schema normalization and parameterized runtime models.
- `implicitjs/loader`: loading `.implicit.js` modules or source strings.
- `implicitjs/render`: Three.js shader and camera helpers.
- `implicitjs/snapshot`: browser PNG snapshot helpers.
- `implicitjs/mesh`: SDF mesh sampling.
- `implicitjs/meshQuality`: mesh quality checks.
- `implicitjs/export`: STL/3MF/GLB export APIs.
- `implicitjs/sdfEvaluator`: CPU SDF evaluator for compatible GLSL.
## Rendering
```js
import * as THREE from "three";
import { loadImplicitModuleFromSource, renderImplicitToDataUrl } from "implicitjs";
const model = await loadImplicitModuleFromSource(source);
const pngDataUrl = await renderImplicitToDataUrl(THREE, model, {
width: 1200,
height: 900,
camera: "iso",
render: { frameMargin: 1.45 },
graphics: { modelColors: true, detail: 1.2 }
});
```
Camera presets include `iso`, `front`, `back`, `left`, `right`, `top`, and
`bottom`. Cameras can also be JSON objects with `position`, `target`, `up`,
`direction`, `preset`, and `zoom`.
## Snapshots
From a package checkout:
```bash
npm run snapshot -- --input examples/model.implicit.js --output /tmp/model.png
npm run snapshot -- --input examples/model.implicit.js --output /tmp/model.gif --mode orbit
```
Orbit GIF jobs default to 6 fps over 12 seconds for a calmer review spin
without increasing default render frame count.
Override with `orbit.fps` and `orbit.durationSeconds` in JSON jobs when needed.
The snapshot CLI also accepts JSON jobs. A single job can include multiple
outputs, and `--job` can load one job, an array of jobs, or `{ "jobs": [...] }`.
Prefer one multi-output job when rendering review packets because the browser,
module, and runtime model can be reused.
```bash
npm run snapshot -- --job - <<'JSON'
{
"input": "examples/model.implicit.js",
"render": { "frameMargin": 1.55 },
"outputs": [
{ "path": "/tmp/model-iso.png", "camera": "iso" },
{ "path": "/tmp/model-front.png", "camera": "front" },
{ "path": "/tmp/model-top.png", "camera": "top" }
]
}
JSON
```
Each output path receives a UTC timestamp before its extension.
## Exports
```js
import { exportImplicitModel, exportImplicitAnimatedGlb } from "implicitjs/browser";
const glb = await exportImplicitModel(model, {
format: "glb",
resolution: 96,
params: { radius: 24 }
});
const animated = await exportImplicitAnimatedGlb(model, {
animationId: "breathe",
params: { radius: 24 },
frames: 24,
resolution: 72
});
```
From a package checkout:
```bash
npm run export -- --input examples/model.implicit.js --format glb --output /tmp/model.glb
npm run export -- --input examples/model.implicit.js --format stl --resolution 96
npm run export -- --input examples/model.implicit.js --format 3mf --params '{"radius":24}'
```
Exports sample the model's SDF inside its bounds. Higher resolutions produce
denser meshes and take longer.
## Package Layout
- `src/index.js`: public package entrypoint.
- `src/browser.js`: browser-oriented entrypoint.
- `src/common/`: shared camera, parameter, theme, render-option, and headless
snapshot helpers.
- `src/lib/implicitCad/`: schema, model normalization, loading, shader
rendering, CPU evaluation, mesh sampling, mesh quality, and exporters.
- `src/lib/viewer/`: internal render presentation defaults used by shaders.
- `scripts/`: snapshot, export, export-verification, and test CLIs.
Tests live beside the modules they cover as `*.test.js`.
## Development
```bash
npm test
npm run verify:exports -- --input examples/model.implicit.js
```
Keep the package reusable and UI-independent. Runtime behavior that applies to
model normalization, rendering, snapshots, CPU sampling, mesh export, graphics
settings, parameters, and animations belongs here. Product-specific UI state,
catalogs, editors, file sheets, routing, and persistence should live in the
consuming application.