Build 3D scenes and print-ready pages from any LLM.
Tangibl3D exposes its modelling actions as an MCP server (Model Context Protocol) and a plain JSON-RPC API. An agent creates a project, places objects from recipes or dimensioned blueprints, extrudes, collapses and heals faces, and finally returns a link to a live 3D scene — no file download, no Python scripting, no raw vertex lists.
softedge objects are smooth subdivision cages (organic), hardedge objects are exact polymeshes (CAD-like).t3d_scene_share returns a viewer URL anyone can open.https://api.show-real.com · MCP endpoint POST https://api.show-real.com/mcp · This reference is generated from the live tool registry, so it is always in sync with the server.Quickstart
1. Get an API key
In 2Dream (2dream.studio): account menu → Agenten & API-Schlüssel. In Tangibl3D (app.show-real.com): open any project → Settings → MCP · API keys. One key drives both apps. Copy it once — the server only stores a hash. Keys look like t3d_….
2. Connect your agent
Claude Code
claude mcp add --transport http tangibl3d https://api.show-real.com/mcp --header "Authorization: Bearer t3d_YOUR_KEY"
Claude Desktop (via the mcp-remote bridge, in claude_desktop_config.json)
{
"mcpServers": {
"tangibl3d": {
"command": "npx",
"args": ["-y", "mcp-remote", "https://api.show-real.com/mcp", "--header", "Authorization: Bearer t3d_YOUR_KEY"]
}
}
}
Any client / curl — plain JSON-RPC 2.0 over HTTPS:
curl -s https://api.show-real.com/mcp \
-H "Authorization: Bearer t3d_YOUR_KEY" -H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/call","params":{"name":"t3d_scene_create","arguments":{"title":"Espresso machine","meshType":"softedge"}}}'
3. Say what you want
With the server connected, a prompt like “Build an espresso machine in Tangibl3D from recipes and give me the link” is enough. The agent will create a scene, add parts, describe the result and return the viewer URL. The same key and the same sandbox also drive 2Dream: “Lay out an A4 flyer in 2Dream with a dark header, title, three bullet points and our logo, then send me a link” — see 2Dream tools.
No account? Use the sandbox
For quick experiments there is a keyless endpoint: POST https://api.show-real.com/mcp/sandbox. Send a header X-Agent-Id: my-agent so your projects stay together (otherwise your IP is used as identity). Sandbox projects live in a shared system workspace, are visible only to the same agent id, and are deleted automatically after 24 hours, together with their viewer links. Limits are tight (see Limits, column sandbox).
claude mcp add --transport http tangibl3d-sandbox https://api.show-real.com/mcp/sandbox --header "X-Agent-Id: my-agent"
https://api.2dream.studio/mcp/sandbox?agent=<your-name> as the connector URL (no authentication); the ?agent= part keeps your projects together, because a connector cannot send headers.Authentication
Send the key as a bearer token: Authorization: Bearer t3d_… (or x-api-key: t3d_…). Keys are bound to your user and all workspaces you belong to. Revoke a key in the app at any time; revoked keys fail with 401 immediately.
| Status | Meaning |
|---|---|
401 | Missing, unknown or revoked key. |
403 | No access to that project, or the project is currently locked by another editor session (retry in ~90 s). |
429 | Rate limit or daily quota exceeded — see Limits. Honour Retry-After. |
Concepts
Coordinates
Left-handed, X right, Y up, Z depth, units in meters. The ground plane is y = 0; objects should stand on it. Positive Z is away from the default camera.
Scenes, objects, faces
A project holds one scene. A scene is a list of objects, each a polygon mesh (control cage) with a type: softedge (Doo-Sabin subdivision, level 0–4) or hardedge (rendered as is). Objects are addressed by name (case-insensitive, substring allowed) or by their 1-based index from t3d_scene_describe. Faces are addressed by 0-based index into the object's face list. Every mutating call saves a new version of the scene and returns a compact description of what changed.
One object per thing — v1.9.0
An object is what a person wants to select, move, colour, hide or animate on its own: a chair, a sun lounger, its cushion, a door, a window, a wheel. Never build one mesh per material or layer that holds every item of that kind in the whole house ("all cushions", "all window frames") — selecting one lounger would select thirty. Parts of one thing (leaves, tread lugs, screws, the slats of one pergola) stay inside it. Name = the thing plus number and place ("Window S 03", "Lounger 12"); material goes into t3d_object_material, not into the name.
t3d_object_add parts[]andt3d_scene_import objects[]create one object per entry;faceColorsgives a colour per face, so a wooden frame and a linen cushion can share one object.t3d_object_clone {object | objects[], copies[] | count + step}repeats a thing (or an assembly) as separate named objects — names count on ("Lounger 01" → "Lounger 02") and stay unique.t3d_object_group {name, objects[]}names an assembly (frame + cushion, frame + glass): a click in the editor selects the whole group, each member keeps its own colour and animation track.t3d_object_split {object, mode: clusters | islands, gap_m, names[]}repairs a merged mesh: clusters keeps touching pieces together, islands separates every disconnected piece; colours, materials and tags travel with their faces.t3d_scene_describereportsislandsper object, lists groups and warns about objects with many disconnected pieces.
Check & brief — v1.10.0
t3d_scene_check {project} scores a scene 0–100 and lists flags: generic names ("Object 3"), objects made of many disconnected pieces (one object per thing!), open Doo-Sabin cages, size outliers (> 300 m or < 3 mm) and objects below the ground (y < 0). Run it when a build is complete and fix what it flags — the same checker grades the built-in editor agent and the Tangibl3D CAD-model benchmark.
Give every scene a brief: t3d_scene_create {title, brief} or t3d_scene_brief {project, brief} — what the scene is for and what is being built, in one or two sentences. t3d_scene_describe returns it, so a later session (or another agent) knows the intent.
Every tool call is recorded with its arguments and result (tool, duration, ok): the basis for debugging agent runs and for training the Tangibl3D CAD model.
Recipes
| kind | parameters | notes |
|---|---|---|
box | center [x,y,z], size [w,h,d] | Axis-aligned box. |
sphere | center, diameter, res 1–4 | Quad sphere; as softedge it becomes perfectly round. |
torus | center, ringRadius, tubeRadius, axis x|y|z | Rings, tyres, handles. |
cylinder | center, radius, height, sides | Centered on center. |
lathe | position, profile [[radius,height],…] bottom→top, segments | Vases, bottles, knobs, wheels. |
prism | position, points [[x,z],…], height | Extruded floor plan / outline (concave OK). |
Every part accepts name and color [r,g,b] (0–255). Set softedge: true on the call to create smooth cages instead of hard-edge polymeshes.
Blueprints
Blueprints are reference bodies with real-world dimensions from norms (SAE J1100, DIN 33402, EN 1335, IEC 60335 …). t3d_blueprint_list returns keys, question options and dimension ranges; t3d_blueprint_place drops semi-transparent helper bodies (wheels, doors, seats, steering wheel, grips …) at a ground position so a designer can model around them. Override any dimension with dims.
Modelling: Doo-Sabin cages, soft shapes, the 3D turtle — v1.6
Tangibl3D is a cage modeller: you edit a coarse polygon cage, the app smooths it with Doo-Sabin subdivision (level 1–4) into a rounded surface that hugs the cage from inside. Hard-edge objects stay exact. Call t3d_howto once before building — it returns this guide with worked examples (topics overview, doo-sabin, turtle, joints, materials, recipes, animation).
- Think in cages. A bottle is a 12-sided cylinder plus three extrudes, never thousands of vertices. Quads with similar edge lengths smooth evenly. Keep the cage closed (
t3d_mesh_heal); remove material witht3d_mesh_collapserather than deleting faces. Sett3d_mesh_subdividelevel 2 at the end. - Soft shapes by extrude + squeeze. Extrude a face and scale the new cap below 1: after smoothing the end is rounded; two squeezes in a row give a dome; scale above 1 flares (bell, vase lip). Crisp edges come from two cage faces close together (a thin support ring), not from flags.
- The control gizmo is a 3D turtle. The selected face is the head, its normal the heading.
t3d_turtleextrudes forward (distance), squeezes or flares the cap (scale), steers it (pitch,yaw), twists it (roll), slides it sideways and returns the new head — chain calls to draw the object’s course through space: pipes, horns, handles, branches, letters. A 90° elbow is{pitch: 15, repeat: 6}. This extrude / squeeze / turn chain is the trademark of the Show-Real subdivision editor. - The gizmo without extrude:
t3d_face_transformmoves a selection (world vector oralongNormal), scales it per axis about its centre and rotates it about x / y / z / its normal — shared vertices drag the neighbouring faces along, which is what makes transitions soft. - Finding faces:
t3d_object_faceslists faces with centre, outward normal and area; filter byfacing(up, down, left, right, front, back or a vector),largestornear. - Joints, closed shapes, repairs — v1.7.
t3d_mesh_bridgeconnects two faces with the same number of corners by one new ring segment of quads (both faces vanish): inside one object (faces: [a, b]— a pipe through a block, the two ends of a bent turtle run) or across objects (faces: [a]+with: {object, face?}— the other object is merged in; the partner face is picked automatically when omitted).t3d_mesh_mergefuses two roughly opposite faces into a seamless joint: matching corners are moved together and welded, both faces disappear, no new segment — the editor’s dock-and-weld (across objects the second part is docked first;anchora | b | mid). Both return the new face indices (the segment, orseamFacesaround the joint),closedand an Euler topology check (2 = ball, 0 = ring/torus). Repairs:t3d_mesh_healcaps open borders,t3d_mesh_collapseremoves a face without a hole, merge welds a split part back. Within onet3d_turtlecall the frame is carried along, so a 23-step arc of 15° closes a ring that merge then seals.
Example — a soft bottle in five calls: t3d_object_add cylinder r 0.3 h 1 (softedge) → t3d_object_faces facing:"up" → t3d_turtle distance 0.1 scale 0.5 (shoulder) → t3d_turtle distance 0.4 (neck) → t3d_turtle distance 0.03 scale 0.6 (lip) → t3d_mesh_subdivide level 2.
Materials & tiling — v1.6
t3d_object_material sets a finish (standard, kunststoff plastic, keramik, beton, silber, alu, gold, glas), a library texture from t3d_material_list (brick, concrete, wood deck, oak, parquet, marble, rock, bark, hedges, meadow, forest floor, gravel, metal plate, steel, rust, brushed metals — alu, chrome, copper, gold, rose gold, tinted via color — camo patterns, glass ceramic, aerial terrain, street, displays), plus color, brightness, reflectivity, transparency. Materials are per object; per-face colours (t3d_object_color) show only on untextured objects.
Tiling in real units. Textures are box-projected (the cages carry no UVs) and repeat tile times across the object’s largest dimension — tile 1 is one repeat per object size, not per metre. Pass tileSize_m, the real-world size of one repeat (2 for a 2 m brick texture, 1.5 for oak planks), and the server computes tile = largest_extent / tileSize_m; omit it and the library’s typical realTile_m is used. tileSizeV_m sets the second axis, angle_deg rotates the projection. Smoothing never changes the projection, so materials survive every cage edit. t3d_scene_describe reports the material with the effective tileSize_m.
Animation & camera rides — v1.8
A project has a timeline of scenes (segments at 30 fps). Frame 0 is the placement — the objects exactly as they stand — and from frame 1 the animation runs, so every key is an offset from the placement. t3d_anim_describe lists scenes, tracks, cameras, paths, events and clickable objects; read it before changing an existing animation. The guide t3d_howto topic animation has the recipes (turntable, exploded view, fly-in, walkthrough, hot-spot tour).
- Objects:
t3d_anim_track—keys [{t_s, move, rotate_deg, scale, alpha, path_pos}]tweened linearly,entry/exiteffects (fade,grow,flyL/flyR/flyT/flyB),pathto follow a control path (pathAlignturns the object along it, vehicles steer),hide. Parametric groups (vehicle, watch, plant, eyewear) animate as one object via their driver. - Paths:
t3d_path_add {points, closed, smooth, flat}creates a control path (a helper curve, drawn as a line in the editor and hidden in the player) that objects and the camera can ride. - Camera rides, three ways: a static view =
t3d_camera_add+t3d_anim_scene camera; a keyframed ride =t3d_anim_camera keys [{t_s, pos, target, fov_deg}](dolly, crane, push-in with 2 keys; orbit with 6–9 keys), easedsmoothorlinear; a path ride =t3d_anim_camera path {path, look: ahead | center | object | [x,y,z], height_m, from, to, t0_s, t1_s}(walkthrough looking ahead, fly-over, turntable on a closed circle looking at the centre).depth0–1 on the scene is the perspective slider (0 ≈ flat/isometric, 1 = full perspective). - Events and clicks:
t3d_anim_event— label, goto (loops), stop, scene switch, prompt, sound;t3d_interact_setmakes objects clickable (play, stop, goto, scene, cam = fly to a named camera, url, sound, vis, light): hot spots, buttons, configurators. - Viewer: the
t3d_scene_sharelink plays scene 1 in a loop (?play=auto),?play=clicksteps through the named cameras,?play=freeleaves it to the triggers;?nav=orbit|spin|walk. The player button sits bottom-left; while playing, the controls fade out after a few seconds and come back on tap or mouse move. Camera rides play in the link (not in walk mode). - Player configuration (v1.8.2):
t3d_scene_share {nav, player: {controls, autoplay, click_cameras, loop, grid, helpers, lock}}writes the settings into the link (?ui=…,?play=click|free,?loop=0,?grid=1,?helpers=1,?lock=rot,zoom,pan,pinch) and returns the iframe embed code. Control groups: bar, menu, gizmo, nav, view, zoom, info, hint, anim —controls: []is the bare scene.loop:falseplays once and holds the last frame (Stop resets, double-click Stop replays);lockfixes the camera in orbit/spin, walk keeps its own controls. Presets: interactive (everything on), player (controls ["anim"]+ all four locks), thumbnail (controls [], nav spin). The editor's share dialog offers the same settings. - Walk mode & avatar (v1.8.1):
?nav=walk(or the Walk button) is first person — WASD / arrows / touch sticks, Shift = 2.8×.t3d_avatar {pos, yaw_deg | look_at, eye_height_m, speed_mps}sets the start point (feet on the floor), the view direction, the eye height (default 1.7 m) and the walking speed (default 2.0 m/s); the editor shows it as a mint figure with an orange view handle. Without an avatar the walk starts where the orbit camera stands. - Helper layer in the player: control paths, camera and light gizmos, helper cubes and the avatar are hidden by default; the eye button in the bottom-right navigation cluster or
?helpers=1shows them.
Agent workflow that works
t3d_scene_listort3d_scene_create— get a project id.t3d_howtoonce — thent3d_object_addwith a handful of recipes (softedge: true) — keep parts coarse; subdivision does the rounding.t3d_scene_describe— read back indices, bounding boxes, closedness.- Find faces with
t3d_object_faces, grow and shape witht3d_turtle/t3d_face_transform/t3d_mesh_extrude/collapse/heal/t3d_mesh_bridge/t3d_mesh_merge/t3d_object_transform; describe again after each step;t3d_mesh_subdividelevel 2 andt3d_object_materialat the end. - One object per thing: every chair, door, window, wheel is its own named object (
t3d_howto objects); repeat witht3d_object_clone, assemble witht3d_object_group, repair witht3d_object_split. t3d_scene_check— score 0–100 + flags before you finish; fix what it flags. Set abriefon every scene.t3d_scene_share— hand the user the viewer link (and the editor link if they own the project).
2Dream — vector & page layout (d2_*)
2Dream is the 2D app of the Show-Real suite: multi-page documents, vector shapes, flow text, images, photo effects, PDF export, a flipbook viewer and Sign & Confirm. The d2_* tools edit documents headless on the same endpoint (and in the same sandbox) as the 3D tools. One server, both apps.
Units and addressing
All lengths are millimetres, origin top-left, y down (page coordinates). Stroke widths and font sizes are in pt. Objects are addressed by id, by name (case-insensitive, substring allowed) or by their 1-based index from d2_doc_describe, which lists every page's objects in stacking order (bottom → top).
Object kinds (d2_node_add)
| kind | parameters | notes |
|---|---|---|
rect | x y w h, cornerRadius | Top-left corner at x,y. |
ellipse | x y w h | Bounding box; w = h gives a circle. |
line | points [[x1,y1],[x2,y2]] | Stroke only. |
polygon | points [[x,y],…] | Closed, ≥ 3 points. |
path | d (SVG path data in mm) | M L H V C S Q T A Z, relative and absolute; arcs become cubic curves; several subpaths = holes/parts (even-odd). |
text | x y w h text font fontSize align bold italic lineHeight mode | flow (default) = a text frame: paragraphs wrap at word boundaries inside w×h — body copy, headlines, captions; omit h to size the frame to the text. Extras: valign columns columnGap padding autofit hyphenate lang firstIndent paragraphSpacing; fill = text colour. art = display lettering scaled to the frame, fitted to its natural proportions (never for running text). Fonts: Arial, Verdana, Trebuchet MS, Segoe UI, Georgia, Times New Roman, Courier New, Impact (others fall back in the viewer). |
image | x y w h url | http(s) or data URL; the server fetches and embeds it (PNG, JPEG, GIF, WebP, SVG). Give w or h to keep the aspect ratio. |
Every kind accepts name, fill, stroke, strokeWidth (pt), opacity, rotation (degrees about the centre) and shadow. Colours are CSS colours or "none".
Body text (Fließtext) — v1.5
Running copy is a first-class citizen: every text object is a flow frame that wraps, and long copy flows through linked frames.
d2_text_story— the whole text once (paragraphs separated by\n) plus the frames in reading order (mm, any pages). The text flows frame to frame; omithon the last frame to size it to the remaining text. Returns the frame ids and an overflow estimate.d2_text_link— continue an existing frame in another empty flow frame (next column, next page);unlink:truecuts a chain.d2_wire_fill— fill a blueprint frame in one call: text / headline / footer become flow frames at the frame bbox in the CI fonts and colours (shrink-to-fit on overflow), image / logo take a URL (logo: the CI logo by default). Marks the frame done.- Resize with
d2_node_transform width/height: the frame changes, glyphs keep their size, the text re-wraps.scalechanges font size and frame together — text is never distorted. - Every text result carries
lines_est,capacity_linesand, if needed,overflow_est_lines+ ahint. The exact layout (real fonts, hyphenation) happens in the editor, viewer and PDF; overflow shows there as a red ⊞. - Objects always land on the printable layout layer (
layerpicks another). The “Wireframes” layer is non-printing — nothing placed there reaches the viewer or PDF;d2_doc_describeflags such objects (nonprinting,warnings).
Book author — v1.11.0
A book is a manuscript, never a layout: the model writes chapters (Markdown-light) and describes illustrations; the typesetter — deterministic code, no model — makes the pages: chapter openers on right-hand pages with blank versos, running heads and folios, contents with leaders and page numbers, half- and full-page illustrations at their anchors, chapter end-notes, widow/orphan control. Eight layout types (novel | nonfiction | textbook | children | coffeetable | documentation | paperback | poetry), book fonts (EB Garamond, Libre Bodoni, Tinos, Literata … / Inter, Source Sans 3 …), writing voices and an illustration style sheet (style, palette, mono, references) keep the whole book consistent.
d2_book_howtoonce, thend2_book_create— title, language, layout, fonts, voice, audience, synopsis, chapter plan with briefs and target lengths, image style. Returns the first unit.- Loop
d2_book_submit {doc, unit:"ch:<id>", text, images}chapter by chapter. Every result names the next unit (chapter or image) and a directive: do it at once, never ask whether to continue, never print the text in the chat. The server checks length, truncation and placeholders and rejects withproblems(force:trueoverrides). - Illustrations: the image unit carries the compiled prompt. Generate it with your image tool and hand it in with
d2_book_image {doc, id, url};mode:"generate"lets the server create it (user's ⚡ balance). If you cannot upload, the user pastes the picture into the slot in the editor. d2_book_typeset, thend2_doc_share mode view. Server page breaks are estimates — the 2Dream editor and viewer re-set the book with exact font metrics on opening.d2_book_get= resume point,d2_book_set= settings and chapter plan,d2_book_flatten= „Buch auf Dokument umrechnen" (pages become ordinary editable frames).
Manuscript syntax: ## section, blank line = paragraph, > quote, - list, *** scene break, \newpage,  places the illustration after that paragraph, [^1] + [^1]: note, [[ch:c2]] cross-reference, **bold**, *italic*.
Workflow that works
d2_doc_create— preseta4,letter,sq1080(social),hd…, optionalpages.- Add the big shapes first (header bars, backgrounds), then text, then images; keep text frames generous — flow text wraps and may overflow a frame that is too small (the result's
lines_est/capacity_linestell you); running copy goes throughd2_text_story. d2_doc_describe— read back indices and bounding boxes;d2_doc_svggives a quick rendering (flow text wrapped by estimate, wireframes hidden, no effects).- Adjust with
d2_node_update(text, fonts, colours),d2_node_transform(to,width,scale,rotate),d2_node_order,d2_node_group. - Blueprint (v1.4):
d2_expose_startcreates a document of a kind (report | yearbook | menu | letter | flyer | website) with wireframe frames on a non-printing “Wireframes” layer — each frame has a kind (image, text, headline, chart, table, logo, footer), a prompt and optionally a data binding (table, filter, chart type).d2_wire_listreturns the whole blueprint incl. CI and data tables;d2_wire_add/d2_wire_setedit frames (prompt, data,status=done,filledId). Humans draw the same frames in the editor (Einfügen → Exposé / Wireframes); your job is to fill them — simplest withd2_wire_fill(one call per frame, marks it done): create the content withd2_node_addat the frame's bbox, then mark the frame done. - Corporate identity:
d2_ci_get/d2_ci_set— colours with roles (primary, secondary, accent, text, bg, spot), heading/body fonts, logo variants, notes. Use them for everything you add; the editor's CI-Manager writes the same structure. d2_doc_share—view(PDF-like flipbook viewer),sign(recipient signs, a signed PDF copy comes back to the owner),sandbox(recipient edits a 24-hour copy in the full editor without an account — the right way to hand a draft to a human). Owners also get aneditordeep link.
Protocol
The endpoint implements MCP Streamable HTTP (spec 2025-06-18) with JSON responses: POST one JSON-RPC message (or a batch) to /mcp; requests get a JSON reply, notifications get 202 Accepted. No session ids are required; GET /mcp answers 405 (no server-initiated streams). Supported methods: initialize, ping, tools/list, tools/call (plus empty resources/list, prompts/list).
POST /mcp
{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-06-18","capabilities":{},"clientInfo":{"name":"my-agent","version":"1.0"}}}
→ {"jsonrpc":"2.0","id":1,"result":{"protocolVersion":"2025-06-18","capabilities":{"tools":{}},"serverInfo":{"name":"tangibl3d",…}}}
Tool results come back twice: as content[0].text (JSON string, for clients that only read text) and as structuredContent (the same object). Tool failures are returned as isError: true with a human-readable message — not as JSON-RPC errors — so agents can recover.
Tool reference
Loading the live tool registry from /mcp/docs.json …
Errors
| Where | Shape | Typical causes |
|---|---|---|
| HTTP | 401 / 403 / 429 | Key, access, quota — see Authentication. |
| JSON-RPC error | {"error":{"code":-32601}} / -32602 | Unknown method / unknown tool name. |
| Tool result | {"isError":true,"content":[{"type":"text","text":"⚠ …"}]} | Object not found (use t3d_scene_describe), invalid face indices, empty recipe, scene size cap. |
Limits & fair use
Tangibl3D is free to try. To keep the service fast for everyone, calls are metered per key and per user. The numbers below come from the live server:
Loading limits …
- Limits are enforced with
429and aRetry-Afterheader; the response also carriesX-RateLimit-Limit/X-RateLimit-Remainingfor the per-minute window andX-Quota-Remainingfor the day. - Only
tools/callrequests count against the daily quota;initialize,pingandtools/listare free. - Payload caps: max parts per
t3d_object_add, max vertices pert3d_scene_import, max objects and faces per scene. Oversized requests fail with a clear message instead of degrading the service. - Accounts are invite-based; keys can be revoked by the owner at any time, and abusive keys are suspended. Need more? support@show-real.com.
Import / export
The app imports OBJ+MTL, STL (binary/ASCII, incl. colour attributes), PLY, glTF/GLB, 3DS (with material colours) and Collada, and exports OBJ+MTL, GLB, STL and PLY — the GLB round trip is the bridge to Blender, Three.js, Unity and Godot. Over the API, use t3d_scene_import for arbitrary polygon meshes (vertices + faces) when a recipe can't express the geometry; export tools are on the roadmap.
Roadmap
- Live mode — tool calls applied inside the user's open editor session (visible, undoable), via the collaboration relay.
- OAuth for claude.ai and ChatGPT custom connectors.
- Snapshots — server-side render preview per call.
- Export tools (GLB/OBJ/STL) and vehicle/animation tools.
- Groups, layers, materials exposed as first-class parameters.
Changelog
Loading …