A Full Live-Scripted CAD Kernel in the Browser
See the codeUse code to create 3D Models with features ranging from simple primitives + CSG to complex revolves, sweeps, and fillets. Cascade Studio exposes the full power of the OpenCascade kernel (OCCT 8.0), while providing a concise standard library for simple operations.
Write in JavaScript or OpenSCAD, visualize in real-time, and export to .step, .stl, or .obj. Copy the URL to share your model with anyone.
new Sketch([x,y], 'XZ')) for drawing in XY, XZ, or YZ planesEdges(shape).parallel([0,0,1]).max([0,0,1]).indices()Volume(), SurfaceArea(), CenterOfMass()window.CascadeAPI) for programmatic control via Playwright or developer toolingcascade-core npm package for embedding CAD modeling in any web appoc. namespace.STEP/.IGES/.STL import and .STEP/.STL/.OBJ exportnpm install
npm run build
npx http-server ./packages/cascade-studio/dist -p 8080 -c-1
# Open http://localhost:8080
Cascade Studio provides a concise standard library for common CAD operations:
// Primitives
Box(x, y, z, centered?)
Sphere(radius)
Cylinder(radius, height, centered?)
Cone(r1, r2, height)
Circle(radius, wire?) // wire=true for Loft/Pipe, false for Extrude
Polygon(points, wire?)
Text3D(text, size, height, font?)
// Sketch API — draw in any plane
let face = new Sketch([0, 0]) // default XY plane
.LineTo([20, 0]).Fillet(3)
.LineTo([20, 10]).Fillet(3)
.LineTo([0, 10])
.End(true).Face();
let profile = new Sketch([0, 0], "XZ") // XZ plane for Revolve profiles
.LineTo([15, 0]).LineTo([10, 8]).LineTo([0, 8])
.End(true).Face();
Revolve(profile, 360);
// Transforms — all return NEW shapes
Translate([x, y, z], shape)
Rotate([ax, ay, az], degrees, shape)
Scale(factor, shape)
Mirror([vx, vy, vz], shape)
// Booleans
Union(shapes)
Difference(mainBody, [tools])
Intersection(shapes)
// Operations
Extrude(face, [dx, dy, dz], keepFace?)
Revolve(shape, degrees, [ax, ay, az]?)
Loft([wires])
Pipe(shape, wirePath)
Offset(shape, distance)
FilletEdges(shape, radius, edgeIndices)
ChamferEdges(shape, distance, edgeIndices)
// Selectors
Edges(shape).ofType("Line"|"Circle").parallel([axis]).max([axis]).min([axis]).indices()
Faces(shape).ofType("Plane"|"Cylinder").max([axis]).indices()
// Measurement
Volume(shape)
SurfaceArea(shape)
CenterOfMass(shape)
Switch to OpenSCAD mode via the dropdown in the top navigation bar. Cascade Studio transpiles OpenSCAD to its JavaScript standard library:
difference() {
cube([20, 20, 20], center=true);
sphere(r=12);
}
The CAD engine is available as a standalone package with no GUI dependencies:
import { CascadeEngine } from 'cascade-core';
const engine = new CascadeEngine({ workerUrl: './cascade-worker.js' });
await engine.init();
const result = await engine.evaluate(`
let box = Box(20, 20, 20);
FilletEdges(box, 3, Edges(box).max([0,0,1]).indices());
`, { guiState: { 'Cache?': true } });
// result.meshData = { faces: [...], edges: [...] }
// Render with Three.js, Babylon.js, or any WebGL framework
Cascade Studio exposes window.CascadeAPI for programmatic control via Playwright or other browser automation tools.
// Navigate and wait for WASM to load
await page.goto('http://localhost:8080');
await page.waitForFunction(() => window.CascadeAPI?.isReady());
// Learn the API
const guide = await page.evaluate(() => CascadeAPI.getQuickStart());
// Run CAD code and check results
const result = await page.evaluate(code => CascadeAPI.runCode(code), `
let profile = new Sketch([0, 0], "XZ")
.LineTo([15, 0]).LineTo([10, 8]).LineTo([0, 8])
.End(true).Face();
Revolve(profile, 360);
`);
// result = { success: true, errors: [], logs: [...], historySteps: [...] }
// Set camera angle and take a screenshot
await page.evaluate(() => {
CascadeAPI.setCameraAngle(30, 20); // azimuth, elevation
CascadeAPI.saveScreenshot('model.png');
});
This is an npm workspaces monorepo with two packages:
cascade-core — Reusable CAD engine (no GUI dependencies)cascade-studio — Browser IDE (Three.js viewport, Monaco editor, Tweakpane GUI)packages/
cascade-core/
src/
engine/
CascadeEngine.js ← Main-thread API wrapping Worker + MessageBus
MessageBus.js ← Typed worker message routing
worker/
CascadeWorker.js ← Web Worker entry; evaluates user code
StandardLibrary.js ← CAD primitives (Box, Sphere, Sketch, etc.)
ShapeToMesh.js ← OpenCascade shape → mesh triangulation
FileUtils.js ← STEP/IGES/STL import/export
openscad/
OpenSCADTranspiler.js ← OpenSCAD → JS transpiler
index.js ← Package entry point
cascade-studio/
src/
main.js ← ESM entry point
CascadeMain.js ← App shell, Dockview layout
CascadeAPI.js ← window.CascadeAPI for agent/programmatic use
CascadeView.js ← 3D viewport (Three.js), modeling timeline
EditorManager.js ← Monaco editor, code evaluation
ConsoleManager.js ← Console panel, log/error capture
GUIManager.js ← Tweakpane GUI panel (sliders, checkboxes)
css/, textures/, icon/, lib/ ← Static assets
test/ ← Playwright tests (monorepo root)
The build system uses esbuild. npm run build builds cascade-core first (worker bundle + WASM + fonts), then cascade-studio (main app bundle + static assets), outputting to packages/cascade-studio/dist/.
Cascade Studio includes a Playwright test suite covering primitives, transforms, booleans, operations, selectors, OpenSCAD, exports, and regression scenarios.
npm run build
npx playwright test # 12 tests, ~40s
WebGL rendering in headless mode requires --use-gl=angle --use-angle=swiftshader (configured in playwright.config.js).
Model code is saved to the URL upon every successful evaluation, so you can copy and paste that link to others to view your model. Share your creations in Github Discussions.
npm install
npm run build
npx http-server ./packages/cascade-studio/dist -p 8080 -c-1
Edit source files in packages/, rebuild, and refresh. Use a new port if changing JS code, as browsers cache ESM aggressively.
Pull Requests to this repo are automatically hosted to Vercel instances, so other users will be able to test and benefit from your modifications as soon as the PR is submitted.
Cascade Studio uses:
Cascade Studio is maintained by Johnathon Selstad @zalo
579 followers · starred Nov 2025
2,856 followers · starred Jan 2021
74 followers · starred Jan 2021
10 followers · starred Jan 2021
A Full Live-Scripted CAD Kernel in the Browser
See the codeUse code to create 3D Models with features ranging from simple primitives + CSG to complex revolves, sweeps, and fillets. Cascade Studio exposes the full power of the OpenCascade kernel (OCCT 8.0), while providing a concise standard library for simple operations.
Write in JavaScript or OpenSCAD, visualize in real-time, and export to .step, .stl, or .obj. Copy the URL to share your model with anyone.
new Sketch([x,y], 'XZ')) for drawing in XY, XZ, or YZ planesEdges(shape).parallel([0,0,1]).max([0,0,1]).indices()Volume(), SurfaceArea(), CenterOfMass()window.CascadeAPI) for programmatic control via Playwright or developer toolingcascade-core npm package for embedding CAD modeling in any web appoc. namespace.STEP/.IGES/.STL import and .STEP/.STL/.OBJ exportnpm install
npm run build
npx http-server ./packages/cascade-studio/dist -p 8080 -c-1
# Open http://localhost:8080
Cascade Studio provides a concise standard library for common CAD operations:
// Primitives
Box(x, y, z, centered?)
Sphere(radius)
Cylinder(radius, height, centered?)
Cone(r1, r2, height)
Circle(radius, wire?) // wire=true for Loft/Pipe, false for Extrude
Polygon(points, wire?)
Text3D(text, size, height, font?)
// Sketch API — draw in any plane
let face = new Sketch([0, 0]) // default XY plane
.LineTo([20, 0]).Fillet(3)
.LineTo([20, 10]).Fillet(3)
.LineTo([0, 10])
.End(true).Face();
let profile = new Sketch([0, 0], "XZ") // XZ plane for Revolve profiles
.LineTo([15, 0]).LineTo([10, 8]).LineTo([0, 8])
.End(true).Face();
Revolve(profile, 360);
// Transforms — all return NEW shapes
Translate([x, y, z], shape)
Rotate([ax, ay, az], degrees, shape)
Scale(factor, shape)
Mirror([vx, vy, vz], shape)
// Booleans
Union(shapes)
Difference(mainBody, [tools])
Intersection(shapes)
// Operations
Extrude(face, [dx, dy, dz], keepFace?)
Revolve(shape, degrees, [ax, ay, az]?)
Loft([wires])
Pipe(shape, wirePath)
Offset(shape, distance)
FilletEdges(shape, radius, edgeIndices)
ChamferEdges(shape, distance, edgeIndices)
// Selectors
Edges(shape).ofType("Line"|"Circle").parallel([axis]).max([axis]).min([axis]).indices()
Faces(shape).ofType("Plane"|"Cylinder").max([axis]).indices()
// Measurement
Volume(shape)
SurfaceArea(shape)
CenterOfMass(shape)
Switch to OpenSCAD mode via the dropdown in the top navigation bar. Cascade Studio transpiles OpenSCAD to its JavaScript standard library:
difference() {
cube([20, 20, 20], center=true);
sphere(r=12);
}
The CAD engine is available as a standalone package with no GUI dependencies:
import { CascadeEngine } from 'cascade-core';
const engine = new CascadeEngine({ workerUrl: './cascade-worker.js' });
await engine.init();
const result = await engine.evaluate(`
let box = Box(20, 20, 20);
FilletEdges(box, 3, Edges(box).max([0,0,1]).indices());
`, { guiState: { 'Cache?': true } });
// result.meshData = { faces: [...], edges: [...] }
// Render with Three.js, Babylon.js, or any WebGL framework
Cascade Studio exposes window.CascadeAPI for programmatic control via Playwright or other browser automation tools.
// Navigate and wait for WASM to load
await page.goto('http://localhost:8080');
await page.waitForFunction(() => window.CascadeAPI?.isReady());
// Learn the API
const guide = await page.evaluate(() => CascadeAPI.getQuickStart());
// Run CAD code and check results
const result = await page.evaluate(code => CascadeAPI.runCode(code), `
let profile = new Sketch([0, 0], "XZ")
.LineTo([15, 0]).LineTo([10, 8]).LineTo([0, 8])
.End(true).Face();
Revolve(profile, 360);
`);
// result = { success: true, errors: [], logs: [...], historySteps: [...] }
// Set camera angle and take a screenshot
await page.evaluate(() => {
CascadeAPI.setCameraAngle(30, 20); // azimuth, elevation
CascadeAPI.saveScreenshot('model.png');
});
This is an npm workspaces monorepo with two packages:
cascade-core — Reusable CAD engine (no GUI dependencies)cascade-studio — Browser IDE (Three.js viewport, Monaco editor, Tweakpane GUI)packages/
cascade-core/
src/
engine/
CascadeEngine.js ← Main-thread API wrapping Worker + MessageBus
MessageBus.js ← Typed worker message routing
worker/
CascadeWorker.js ← Web Worker entry; evaluates user code
StandardLibrary.js ← CAD primitives (Box, Sphere, Sketch, etc.)
ShapeToMesh.js ← OpenCascade shape → mesh triangulation
FileUtils.js ← STEP/IGES/STL import/export
openscad/
OpenSCADTranspiler.js ← OpenSCAD → JS transpiler
index.js ← Package entry point
cascade-studio/
src/
main.js ← ESM entry point
CascadeMain.js ← App shell, Dockview layout
CascadeAPI.js ← window.CascadeAPI for agent/programmatic use
CascadeView.js ← 3D viewport (Three.js), modeling timeline
EditorManager.js ← Monaco editor, code evaluation
ConsoleManager.js ← Console panel, log/error capture
GUIManager.js ← Tweakpane GUI panel (sliders, checkboxes)
css/, textures/, icon/, lib/ ← Static assets
test/ ← Playwright tests (monorepo root)
The build system uses esbuild. npm run build builds cascade-core first (worker bundle + WASM + fonts), then cascade-studio (main app bundle + static assets), outputting to packages/cascade-studio/dist/.
Cascade Studio includes a Playwright test suite covering primitives, transforms, booleans, operations, selectors, OpenSCAD, exports, and regression scenarios.
npm run build
npx playwright test # 12 tests, ~40s
WebGL rendering in headless mode requires --use-gl=angle --use-angle=swiftshader (configured in playwright.config.js).
Model code is saved to the URL upon every successful evaluation, so you can copy and paste that link to others to view your model. Share your creations in Github Discussions.
npm install
npm run build
npx http-server ./packages/cascade-studio/dist -p 8080 -c-1
Edit source files in packages/, rebuild, and refresh. Use a new port if changing JS code, as browsers cache ESM aggressively.
Pull Requests to this repo are automatically hosted to Vercel instances, so other users will be able to test and benefit from your modifications as soon as the PR is submitted.
Cascade Studio uses:
Cascade Studio is maintained by Johnathon Selstad @zalo
579 followers · starred Nov 2025
2,856 followers · starred Jan 2021
74 followers · starred Jan 2021
10 followers · starred Jan 2021