Unified 3D workflow: create models (AI), search (Thingiverse), slice, print. Modular—enable only what you need.
Single skill for the full 3D pipeline: create models (AI), search (Thingiverse), slice, and print. Modular—only enabled capabilities appear below.
CRITICAL — Execute immediately, never stop after acknowledging. When you tell the user you'll do something (search, convert, preview, slice), you MUST execute the command in the SAME turn. Do NOT end your turn after just acknowledging — the user should never have to ask "done?" to get you to act. Acknowledge AND call the tool in one response.
Setup order: Printer first (when printing enabled) → then create/search models → slice → print.
When printing is enabled and the user has no printers configured, guide them to add a printer AND a linked slicing profile before creating or searching for models. A linked profile is required for slicing — it stores the build volume (width × depth × height) extracted from the 3MF, which determines how models are scaled.
Always run claw3d printer list first. If it returns nothing, go through setup below.
Send this message to the user:
Let's get your printer set up. I need 3 things:
- 1. Printer name — e.g. "Creality K2 Pro Living Room"
- IP address + port — e.g.
192.168.1.50:7125(Moonraker default: 7125; Creality K2 SE: 4408)- Cura project file (.3mf) — Export it from Cura: File → Save → "Export Universal Cura Project" with your printer loaded. This file carries your printer's build volume and all settings — it's required for correct slicing.
Wait for the user to provide all three.
CODEBLOCK0
This does everything in one step:
build_width, build_depth, build_height)If the user provides name+IP but no 3MF yet: Add without it (printer add --name ... --host ... --port ...), then immediately ask for the 3MF to create the profile:
Got it! Now please send the Cura project file (.3mf) so I can create the slicing profile. In Cura: File → Save → "Export Universal Cura Project".
Then: claw3d profile create --from-3mf <MediaPath> --name "<printer_name>_profile" → INLINECODE8
Printer backends: Run claw3d configure backends to see options (Moonraker, PrusaLink, etc.). Community can add backends in claw3d/backends/.
When the user asks for a 3D model without specifying how (e.g. "I need a cup", "I want a dragon", "find me a vase", no image attached), do NOT default to one option. Offer choices based on what's enabled:
Great! Would you like me to:
- 1. Search for existing models — I'll look on Thingiverse and show you options to download (if directory enabled)
- Create a 3D model from an image — Send me a sketch or photo and I'll turn it into 3D (if ai-forger enabled)
- Search first, then create from an image if nothing fits — Best of both (if both enabled)
Wait for the user to choose. Only if they explicitly say "create it", "from a photo/sketch", "search", "look up", etc., then proceed.
Never assume — "I need a dragon" could mean search OR create from image. Always clarify when ambiguous. Do not offer text-only 3D generation — results are inaccurate; always require an image or sketch.
MediaPath: When the user attaches a file (image, GLB, 3MF), the message includes a MediaPath — the full filesystem path. Always pass that exact path to --image, --edit-3d, --profile-from-3mf, etc. Copy it character-for-character.
Unique output paths: The workspace is shared. Using fixed names (model.glb, preview.mp4) causes old files from a previous request to be sent to new chats. Always derive a short ID from the MediaPath and use it for outputs.
MediaPath format: .../file_13---b10560d7-18fd-40e9-8a49-996ad190a26c.jpg — extract the segment after --- and use the first 8 chars (e.g. b10560d7) as ID.
If the MediaPath has no UUID (unusual), use date +%s to get a unique ID.
When the user attaches an image and asks to "3D print this", "print this", "make it printable", etc. — you CAN do it (if ai-forger + slicing + printing enabled):
claw3d printer list; note [WxDxH mm] if shown.claw3d preview --input model_<ID>.glb --output preview_<ID>.mp4 [--build-volume WxDxH] — send the videoclaw3d profile list, then slice with --build-volume <WxDxH> and profile or INLINECODE27claw3d printers, then INLINECODE29Do NOT say "I can't print from an image" — you can create the 3D model first. If FALAPIKEY is missing, convert will fail; then tell the user to set it up.
CODEBLOCK1
claw3d search → claw3d fetch → claw3d dimensions → present with previewclaw3d convert --image (requires image/sketch) → claw3d preview → presentclaw3d convert --edit-3d (when user sends GLB and asks to modify)claw3d slice (sends G-code + gcode preview video)| Command | Purpose |
|---|---|
| INLINECODE38 | Image/sketch → GLB, or edit existing GLB |
| INLINECODE39 |
claw3d search | Search Thingiverse |
| claw3d fetch | Download model from Thingiverse |
| claw3d dimensions | Bounding box (for slicing) |
| claw3d pack | Arrange multi-part on build plate |
| claw3d slice | GLB/STL → G-code |
| claw3d print | Upload G-code and start print |
| claw3d printer | Add/list/remove printers |
| claw3d profile | Create/list slicing profiles |
| claw3d configure | Select AI provider, see backends |
Run all via exec. Use claw3d.
All routing decisions, skill logic, and internal reasoning are for YOUR use only. NEVER send them to the user. The user should only see friendly, concise messages — never references to "Primary Gate", "SKILL.md", module names, decision rules, or your thought process. If you need to reason about which path to take, do it silently. The user just wants their model.
Bad (leaked reasoning): "According to the Primary Gate, a wine stand is a common functional object, so I should search Thingiverse..."
Good (user-facing): "Great, let me take a look at what you need — give me a moment!"
This is the FIRST decision for EVERY request — images, videos, and text. Run the Primary Gate BEFORE any analysis, frame extraction, or claw3d analyze. Make this decision silently — do NOT explain your routing to the user.
The key question is: Would an existing Thingiverse model likely satisfy this need, or does the request require something inherently custom/unique?
→ SEARCH path first (go to 03-directory module) when:
→ CREATE path (continue to CREATE section below) when:
Decision rule of thumb:
"Could I type this into Thingiverse and find 5+ decent results?" → YES → SEARCH first
"Does this require seeing a specific image, style, or personal constraint to design?" → YES → CREATE
→ ASK only when you genuinely cannot identify what physical object the user wants — e.g. "make something for my office" with no further context. If you can name the object, go to SEARCH. Do not ask.
SEARCH PATH — fallback to CREATE: After 3 rounds of search (up to 15 models reviewed) with no match, tell the user nothing matched and ask if they want a custom AI-generated model instead. If they have a photo/video, use it as reference for the AI generation.
When the user sends a video, you may receive a text Description (from OpenClaw's Gemini video understanding). Use the Description and/or the user's message text to run the Primary Gate — BEFORE extracting any frame or running claw3d analyze.
Steps for video:
03-directory module with that object as the search query. Do NOT extract a frame or run analyze⚠️ CRITICAL: A video showing someone demonstrating a common object does NOT make it a CREATE request. The video is just their way of communicating what they want — it doesn't mean they need AI generation. A person holding up a wine bottle and showing how they'd like a wine stand still maps to SEARCH. Only explicit artistic/stylistic/replication intent maps to CREATE.
This section handles finding the video file. It applies to BOTH paths (the CREATE path needs it for frame extraction; the SEARCH path may need it later if search fails and you fall back to CREATE).
Step 0 — Acknowledge immediately — Before doing anything else, send:
"Great, let me take a look at what you need — give me a moment!"
Step 1 — Get the video path. Three cases:
Case A — File path visible ([media attached: /home/node/.openclaw/media/inbound/...]):
Use that exact path.
Case B — No file path but Description is present (OpenClaw's Gemini video understanding ran and suppressed the path):
The video is still on disk. Find it:
ls -t /home/node/.openclaw/media/inbound/ 2>/dev/null | head -5
.mp4, .mov, .webm). Use that as the path.
Case C — No file path and no Description (video silently dropped — too large):
Your video was too large — OpenClaw's default limit is 5MB. I can increase it to 50MB right now. Want me to?
If confirmed:
python3 -c "
import json, pathlib
p = pathlib.Path('/home/node/.openclaw/openclaw.json')
cfg = json.loads(p.read_text())
cfg.setdefault('channels', {}).setdefault('telegram', {})['mediaMaxMb'] = 50
p.write_text(json.dumps(cfg, indent=2))
print('Done')
"
The config watcher restarts the Telegram channel automatically.
Step 2 — Run the Primary Gate using the Description/user message → SEARCH or CREATE. See above.
If SEARCH → go to 03-directory module. Note the video path — if search fails and you fall back to CREATE, you'll need it for frame extraction.
If CREATE → continue to the next section.
The bot rejects oversized files before the agent sees them. If the user reports this error in a text message, offer to fix it:
I can increase your video limit to 50MB right now. Want me to do that?
If confirmed, run the patch above.
Run once per session to understand the configuration:
CODEBLOCK4
| Mode | What happens |
|---|---|
| INLINECODE60 (default) | INLINECODE61 uses Gemini if key is set, else returns INLINECODE62 |
| INLINECODE63 |
claw3d analyze immediately returns native_mode: true — you do the analysis |gemini | claw3d analyze uses Gemini; errors if key missing |Only enter this section if the Primary Gate resolved to CREATE.
Before doing anything with a user's image or video, run claw3d analyze (images) or analyze the video natively + claw3d extract-frame --timestamp + claw3d analyze (videos).
Step 1 — Always run analyze:
CODEBLOCK5
Step 2 — Read the result and branch:
native_mode: true → you are the analysis layerAnalyze the image yourself using these rules:
Classify image_type:
sketch: hand-drawn, pencil/pen outlines, whiteboard drawings → intent is almost always create_new, proceed directlyDecide needs_clarification:
OVERRIDE — replicate/copy intent always sets needs_clarification: false:
If the user's message contains any of: "make another one", "copy this", "replicate this", "clone this", "I want one like this", "same as this", "reproduce this", "duplicate this", "print this one" — the photo/frame IS the complete design reference. Proceed directly to convert. Do NOT ask for a drawing. The whole point is that they're showing you the exact object they want.
INLINECODE80 (proceed without asking) when ALL of these are true:
INLINECODE81 (ask ONE clarifying question) when ANY of these:
Rule of thumb for functional objects: If you could design it 3+ different ways and the user hasn't said which way → send the frame/image back and ask them to draw on it (see below). Exception: replicate intent (see override above) → always proceed directly.
If needs_clarification: false:
Step A — Tell the user you're starting (do NOT stay silent):
"Creating your 3D model now — I'll send it when it's ready!"
Step B — Write a suggested_prompt and run convert:
CODEBLOCK6
CRITICAL — When writing suggested_prompt:
For replicate/copy intent ("make another one", "copy this", etc.):
Keep it SHORT — one sentence. The image already carries the shape. Do NOT add dimensions, material suggestions, or printing advice.
For all other intents:
Describe ONLY the 3D object to be printed. Keep it to 1-2 sentences max. Do NOT include:
Example — user shows a wine bottle next to a dog sculpture:
If needs_clarification: true:
Two cases:
Case 1 — Ambiguous subject (multiple objects, unclear what to print):
Ask ONE specific text question:
"I see a desk with a laptop and a mug. Which item would you like to 3D print?"
Case 2 — Subject is clear but it's a photo of a functional/custom object (holder, bracket, case, mount, stand, organizer, etc.):
frame_1a589237.jpg) — you will need it when the annotated image comes back.message tool to attach the frame — do NOT use inline MEDIA: syntax:message(text="Hey! Could you draw...", media="<frame_path>")When the user sends back the annotated image:
Do NOT say "Yes! On it!" and stop — immediately run exec:
claw3d convert --image <original_frame_path> --annotated-image <annotated_MediaPath> --prompt "<description of the object, NO scene context>" --output model_<ID>.glb
<original_frame_path> = the frame you sent them (e.g. frame_1a589237.jpg)native_mode: false (Gemini was used) → act on the JSONCODEBLOCK8
| INLINECODE93 | Action |
|---|---|
| INLINECODE94 | Check needs_clarification first — if false, then INLINECODE96 |
| INLINECODE97 |
create_new |find_existing | This shouldn't appear here — Primary Gate should have caught it. But if it does: go to 03-directory module |
If needs_clarification: true:
false and proceed directly regardless of what Gemini returned.clarification_question verbatim (Gemini wrote it to be friendly and specific)You should only be here if the Primary Gate resolved to CREATE.
Step 1 — Extract the best frame
Two paths depending on how the video arrived:
Case A — Video attached as media (you can see the video in this conversation):
You are a multimodal agent. Analyze the video directly to identify the best frame:
Pick the exact timestamp (HH:MM:SS), then extract:
CODEBLOCK9
Case B — Only text Description, no media in conversation (OpenClaw pre-processed the video):
You cannot see the video — you only have the text Description. Do NOT guess a timestamp from text. Use Gemini API for smart frame selection:
claw3d extract-frame --input <video_path> --output frame_<ID>.jpg
--timestamp → Gemini picks the best frame automatically)
If this fails because no Gemini API key is configured, stop and tell the user:
"I need a Gemini API key to pick the best frame from your video (the video isn't directly visible to me in this conversation). Please run:
claw3d configure analysis --gemini-api-key <YOUR_KEY>
You can get a free key at Google AI Studio."
Step 2 — Analyze extracted frame:
claw3d analyze --input frame_<ID>.jpg --description "<user's message or Gemini description>" --pretty
needs_clarification checks).
CRITICAL — Do NOT go silent after frame extraction. If needs_clarification: false, tell the user you're generating the model BEFORE running claw3d convert. The full sequence must be:
claw3d convert → claw3d preview → send both filesGeneric functional object — search first (even if user says "create"):
CODEBLOCK12
Video demonstrating a common object — STILL search first:
CODEBLOCK13
Same object + artistic constraint — create:
CODEBLOCK14
Sketch → 3D model (CREATE path):
CODEBLOCK15
Generic object, user says "I want this" with a photo:
CODEBLOCK16
Custom functional object (specific, unlikely to exist):
CODEBLOCK17
Video — user asking to find (any wording):
CODEBLOCK18
Search exhausted → fallback to CREATE:
→ 3 searches, 15 thumbnails reviewed, none match
→ "Couldn't find a good match. Want me to generate a custom one with AI?"
User: "yes"
→ If user has a video/photo: use it as reference for CREATE path
→ Extract frame (if video) → analyze → clarification if needed → convert
CODEBLOCK20
You CAN convert 2D images to 3D models AND edit existing 3D models (GLB). When the user sends a GLB and asks to modify it (e.g. "make it blue", "add wheels"), use claw3d convert --edit-3d <GLB_MediaPath>. When they send an image, use --image.
--edit-3d flowAlways require an image or sketch. Do not use text-only --prompt for new model creation — results are not accurate enough. If the user asks to "make a cup" without an image, ask them to send a sketch or photo, or offer to search Thingiverse instead.
CRITICAL — User sent a GLB and wants to edit it: Run claw3d convert --edit-3d <GLB_MediaPath> --prompt "..." --output edited_<ID>.glb. Never say you cannot edit 3D models.
When the user asks to create a 3D model from an image OR to edit a 3D model, REPLY IMMEDIATELY first:
Image conversion takes 1–2 minutes. Edit-3d can take 5–10+ minutes when Hunyuan is cold. Do NOT stay silent—always acknowledge first.
When the user attaches an image, the message includes a MediaPath. Always pass that exact path to --image. Copy it character-for-character.
IMPORTANT — Unique output paths: Derive a short ID from the MediaPath. Format: .../file_13---b10560d7-18fd-40e9-8a49-996ad190a26c.jpg — use first 8 chars after --- (e.g. b10560d7) as ID.
Build volume: Before running claw3d preview, check if a printer is configured with a known build volume: run claw3d printer list and look for [WxDxH mm] (e.g. [350×350×350mm]). If found, pass --build-volume WxDxH (e.g. --build-volume 350x350x350) — this renders the grey build plate and grid under the model for a realistic preview.
CODEBLOCK21
If the MediaPath has no UUID (unusual), use date +%s for a unique ID. NEVER send model.glb or preview.mp4 that existed before this request.
process poll <session> with timeout: 120000. You will be notified when it completes — do NOT poll in a rapid loop.
- When you see Wrote edited_<ID>.glb → convert is done.
--real-scale for edited models. AI-regenerated models use normalized units (~1 unit), not mm. The preview auto-scales the model to fill the build volume.
- Same: wait for result or single poll with timeout: 120000.
message(action="send", text="Here's the updated preview!", media="preview_edited_<ID>.mp4")
message(action="send", text="And the edited model:", media="edited_<ID>.glb")
CRITICAL: Do NOT end your turn after the first message(). You MUST send the .glb in a second message() call. The user needs the 3D model file, not just the video. Your turn is only complete after BOTH files are sent.
NEVER use --image for a GLB when modifying. --image is for 2D sketches/photos.
claw3d printer list; note [WxDxH mm] if present.Command still running), call process poll <session> once with timeout: 120000. You will get notified when it completes — do NOT poll in a rapid loop.
- When you see Wrote model_<ID>.glb → convert is done. Proceed immediately.
timeout: 120000.
- When you see Wrote preview_<ID>.mp4 → preview is done. Proceed immediately.
message(action="send", text="Here's your 3D model preview!", media="preview_<ID>.mp4")
message(action="send", text="And the 3D model file:", media="model_<ID>.glb")
CRITICAL: Do NOT end your turn after the first message(). You MUST send the .glb in a second message() call. The user needs the 3D model file, not just the video. Your turn is only complete after BOTH files are sent.
This is mandatory for AI-generated models — they have no real-world dimensions, so you MUST get the max print size from the user before slicing. Do NOT slice without asking. Do NOT use a default size.
CRITICAL: Run convert and preview via exec BEFORE sending. The files do not exist until you create them.
CODEBLOCK24
| Error | Check |
|---|---|
| Convert fails | FALAPIKEY set, image exists, PNG/JPG |
| No image URL in FLUX response |
API key errors: When convert fails with "FAL API key" or "401/403", ask the user to verify their API key in Control UI → Skills → claw3d. Get a key at https://fal.ai/dashboard/keys
You CAN search for existing 3D models on Thingiverse. Use claw3d find, claw3d fetch, and claw3d preview — do NOT use web search.
The intent classifier (06-intent.md) sets consider_search: true for common/functional objects. When that happens — or when the user explicitly asks to find/search/download a 3D model — follow this workflow.
Skip this flow and go straight to AI generation only when the user explicitly says "custom", "artistic", or describes something that clearly doesn't exist as a standard printable part.
Before running anything, send:
"Great, let me take a look at what you need — give me a moment!"
Run one command. It searches Thingiverse, downloads all thumbnails, fetches each model, packs multi-part models, and fit-checks all of them — returning only the models that physically fit in the printer.
CODEBLOCK25
⚠ claw3d find is a long-running command (1–2 minutes). When you see Command still running, this is the SEARCH running — NOT slicing. Do NOT say "Slicing started". Just poll silently with process poll <session> every 10 seconds until it finishes.
Output format:
CODEBLOCK26
--build WxDxH to override.View all returned thumbnail files visually (you are multimodal). Pick the 4 that best match what the user needs — considering shape, function, and apparent quality. Record the thing ID for each.
If fewer than 4 passed, use however many there are.
If exit 1 (none fit): run claw3d find with a refined query (change keywords, add constraints), up to 3 rounds total. After 3 rounds with no match, fall back to AI generation.
Stamp option letters and compose a single 2×2 grid image (A top-left, B top-right, C bottom-left, D bottom-right):
CODEBLOCK27
MANDATORY: Send ONE message with the grid image attached. Do NOT describe the options without the image. Do NOT skip the media= parameter. The user needs to SEE the thumbnails to choose — text-only is useless.
CODEBLOCK28
The media= field with the grid image path is REQUIRED. If you send this message without the grid image attached, the user cannot see the options.
Wait for user response before continuing.
claw3d find output for that option. Continue to Step 4 with that ID. The model is already downloaded and pre-rotated (if needed) — no re-fetch required.claw3d find with a refined query, repeat from Step 1 — up to 3 rounds totalThe chosen model is already downloaded. Use its thing ID to inspect variant/part structure:
CODEBLOCK29
This deterministically selects the best extension group (STL > OBJ > GLB > 3MF). Parse the output:
Best extension: .stl (N file(s)) — what will be downloadedRead the --list-grouped output and follow exactly one of these branches:
→ Output shows "Sub-variants" (size/version choices):
Ask the user which size/version they want:
"This model comes in several sizes: small, medium, large. Which would work best for you?"
--choose "<variant_tag>" in Step 6.
→ Output shows "Cosmetic variations" (same model, minor differences):
Do NOT ask the user. Auto-select the variant marked <- auto-selected and inform them:
"This model has a [no-text / simplified / …] version — I'll use that for a cleaner print."
--choose "<auto_selected_filename_keyword>" in Step 6. E.g. if TiltedWineBottleStand_NoText.stl is auto-selected, use --choose "NoText".
→ Output shows "Multi-part model" (multiple components): all parts are needed — model was already packed by claw3d find. Skip directly to Step 7.
→ Single file or complete-set: model already downloaded by claw3d find — skip directly to Step 7.
Skip this step if no --choose is needed (single file, complete-set, or already fetched correctly).
With sub-variant chosen (e.g. user picked "large"):
CODEBLOCK30
With cosmetic variant auto-selected (e.g. NoText):
CODEBLOCK31
claw3d find auto-computes dimensions from the fitted extents. The Extents: line in the output is the already-rotated bounding box.
Only run
claw3d dimensions -i <file>manually if the file was re-fetched in Step 6 (variant selection).
Build volume is auto-read from the default printer config. Generate the preview with --real-scale so the user sees the model at its actual physical size relative to the build plate:
CODEBLOCK32
INLINECODE178 shows the model at its true mm dimensions on the plate. --build-volume is auto-read from the default printer (no need to pass it). If no printer is configured yet, ask the user for their build volume and pass it explicitly.
Important: Thingiverse thumbnails are often lifestyle renders that can look very different from the actual printable model. The 3D preview video is the ground truth — always describe the dimensions so the user understands what they're actually getting.
Single plate:
CODEBLOCK33
Multi-plate (N plates needed):
message(action="send", text="This model needs N separate prints. Here's plate 1 (X × Y × Z mm):", media="preview_<ID>_p1.mp4")
message(action="send", text="Plate 2 (X × Y × Z mm):", media="preview_<ID>_p2.mp4")
# … all plates
message(action="send", text="Print them sequentially and assemble. Ready to slice when you are!")
When the user asks to print N copies of a model ("add 3 more", "print 4 of these", "fill the plate"):
claw3d pack --copies N on the original STL sidecar. Pass any rotation the user wants baked in via --rotation-x/y/z. The packer places all N copies with 2mm gaps.CODEBLOCK35
model_<ID>_x4_plate1.stl, model_<ID>_x4_plate2.stl): slice and queue each plate separately.CODEBLOCK36
Rotation is already baked in by --rotation-x/y/z in the pack step — do NOT also pass rotation to claw3d slice.
If no Thingiverse result matches, say:
"I couldn't find a good match in the Thingiverse library. I can generate a custom 3D model using AI — want me to do that?"
If yes, follow the AI generation flow from 02-ai-forger.md.
| Command | Purpose |
|---|---|
| INLINECODE187 | Search + download thumbnails + fetch + fit-check in one shot. Returns only models that fit the printer |
| INLINECODE188 |
claw3d fetch --list-only <id> | Raw file list (complete sets vs parts) |claw3d fetch <id> -o model.glb | Download + convert to GLB |claw3d fetch <id> --choose "large" -o model.glb | Download only files matching substring |claw3d pack -i dir/ --build WxHxD -o model.glb | Arrange multi-part on build plate (2mm gap). Exit 1 if part too large |claw3d pack -i model.stl --copies 4 --build WxHxD -o model_x4.stl | Duplicate single model 4 times on plate |claw3d pack -i model.stl --copies 4 --rotation-x 90 --build WxHxD -o model_x4.stl | Duplicate with baked rotation |claw3d fit-check -i model.stl --apply-rotation | One-off fit check: exits 0 = fits, exits 1 = doesn't fit |claw3d dimensions -i model.glb | Bounding box + save .dimensions.json sidecar for future slicing |claw3d preview -i model.glb -o preview.mp4 | 360° turntable video || Error | Action |
|---|---|
| No results / 401 | Check THINGIVERSEACCESSTOKEN in Control UI → Skills → claw3d |
| "No directory providers configured" |
claw3d find exit 1 (0 fitting models) | Refine query and retry, up to 3 rounds; then AI generation |
| claw3d find not found | Rebuild Docker: docker build -f Dockerfile.claw3d -t openclaw:claw3d . then restart |
NEVER use hardcoded or remembered profile IDs. Profile IDs are stored on the slicer server and are lost when the container restarts. Before every slice:
claw3d profile list — use whatever ID is listed there.--profile-from-3mf) or create a profile first.--profile <id>.INLINECODE205 reads the .source.json sidecar automatically. When it detects "source": "thingiverse", it:
--no-mesh-clean (skips mesh repair)You do NOT need to pass --no-mesh-clean manually — the code handles it. Just pass the model file and the slicer does the right thing based on provenance.
When re-slicing, the previous settings are saved in .slice_config.json and reused automatically (max-dimension, strength, quality). You only need to pass flags that changed.
Path A: Model from directory (Thingiverse) — The model is already at the correct physical size. NEVER ask for max print size. Do NOT pass --max-from-model or --max-dimension. The source-based routing handles this automatically.
.stl sidecar (model_<ID>.stl) if it exists — send it directly, no conversion..glb exists (model was fetched as GLB): use model_<ID>.glb. The auto-routing will apply --no-mesh-clean automatically.Ask the user only:
Before I slice, I need two things:
- 1. Strength — How strong should it be? (10%, 25%, 50%, 75%, or 100%)
- Detail — How much print detail / quality? (10%, 25%, 50%, 75%, or 100%)
Path B: Model from AI or user-provided — Use model_<ID>.glb. No dimensions file. MUST ask for max print size, strength, and detail before slicing. Use the printer's build volume (from claw3d printer list) as the default max dimension suggestion — use the smallest of width/depth/height.
Before I slice, I need a few things:
- 1. Max print size — What's the longest dimension you want? (e.g. 100mm or 150mm)
- Strength — How strong should it be? (10%, 25%, 50%, 75%, or 100%)
- Detail — How much print detail / quality? (10%, 25%, 50%, 75%, or 100%)
Map percentages to CLI: 10%→1, 25%→2, 50%→3, 75%→4, 100%→5. Use --max-dimension <N>, --strength, --quality.
Natural language → CLI flags:
claw3d rotate -i model.glb --rotation-y 90 (then preview/slice without rotation flags)--quality 4 or INLINECODE229Bed leveling: Do NOT add --bed-autocalibration unless the user explicitly asks. Default OFF.
INLINECODE231 permanently modifies the model file. Rotation is cumulative by design — each call rotates from the model's current orientation, like dragging an object in a 3D editor. No state tracking needed.
When the user asks to rotate a model ("rotate 90 on X", "flip it sideways", "turn it upside down"):
Step 1 — Rotate the file:
claw3d rotate -i model_<ID>.glb --rotation-x 90
Step 2 — Show preview (no rotation flags):
claw3d preview -i model_<ID>.glb --build-volume <WxDxH> -o preview_<ID>_rotated.mp4
Step 3 — When user confirms, slice (no rotation flags):
CODEBLOCK39
Multiple rotations just work:
| User says | You run | Result |
|---|---|---|
| "rotate 90 on X" | INLINECODE232 | Model is now 90° on X |
| "now rotate 90 on Y" |
claw3d rotate -i model.glb --rotation-y 90 | Model is now 90° X + 90° Y |claw3d rotate -i model.glb --rotation-z 45 | All three rotations accumulated |
Natural language mapping:
--rotation-x 90 --rotation-z 45 (one command)Undo rotation: If the user says "undo that rotation" or "go back":
claw3d rotate -i model_<ID>.glb --undo
Do NOT pass --rotation-x/y/z to claw3d preview or claw3d slice. Always use claw3d rotate first — the file is the source of truth.
CODEBLOCK41
CRITICAL: Both claw3d slice and claw3d preview are long-running commands. You MUST wait for them to finish before proceeding. Do NOT return control to the user while they run.
The exec call waits up to 2 minutes for the command to finish. Most commands complete within this window and return the result directly. If a command takes longer, exec returns Command still running with a session ID. In that case:
process poll <session> once with timeout: 120000 (2 min wait).Wrote <path> or [timing] → the command finished. Proceed immediately.claw3d slice:claw3d slice ... — tell the user: "Slicing started! I'll let you know when it's ready."Wrote <path> for the gcode preview → send both files immediately.claw3d preview:claw3d preview ... — tell the user: "Generating your 3D preview, I'll send it when it's ready!"Wrote <path> → send the file immediately. Do NOT ask the user if they want it.YOU MUST NOT return control to the user until you see Wrote <path> or an error.
After slice succeeds, send BOTH the G-code and the G-code preview video. Slice generates model_<ID>_gcode_preview.mp4 by default (body red, supports yellow). Use the message tool so both files attach in Telegram.
Include print estimates in your message. The slice output includes an [estimates] line with print time, filament usage, and layer count. Always include these stats when sending the G-code, e.g.: "Here's your G-code! Estimated print time: 2h 30m | Filament: 12.5m (37g) | Layers: 245"
When the user asks for "the video" after a slice: They mean the G-code preview (model_<ID>_gcode_preview.mp4). Do NOT run claw3d preview — that renders the 3D model. Send the existing gcode preview file.
Build volume for previews: When a default printer is configured (i.e. the printer was added with --profile-from-3mf), claw3d preview and claw3d slice automatically use that printer's build volume — you do NOT need to pass --build-volume explicitly. If needed, you can always override with --build-volume WxDxH (e.g. --build-volume 350x350x350). The build volume renders the grey build plate, 10mm grid, and volume wireframe in the preview video. To verify the current default printer's build volume, run claw3d printer list.
CODEBLOCK42
| Flag | Description |
|---|---|
| INLINECODE268 , INLINECODE269 | Input GLB, STL, or 3MF |
| INLINECODE270 , INLINECODE271 |
-p, --profile | Profile ID (use --profile OR --profile-from-3mf for GLB/STL) |
| --profile-from-3mf | Create profile from 3MF, then slice |
| --strength | 1–5 (10%→1 … 100%→5). Default 3 |
| --quality | 1–5 (10%→1 … 100%→5). Detail / print quality level |
| --max-dimension | Scale longest axis to N mm (AI models) |
| --max-from-model | Use max from dimensions.json (directory models) |
| --no-mesh-clean | Skip all mesh repair during GLB→STL conversion. Required for directory/Thingiverse GLBs — mesh fixes are for AI models only and can delete real model geometry |
| --rotation-x | ⚠️ Prefer claw3d rotate instead — bakes rotation into file. Only use in slice/preview for one-off tests |
| --rotation-y | Same as above |
| --rotation-z | Same as above |
| --layer-height | Override layer height in mm (e.g. 0.15) |
| --infill-density | Override infill percentage (e.g. 20) |
| --preview-video | Generate 360° G-code preview video (default ON) |
| --no-preview-video | Skip G-code preview video (faster) |
| --build-volume | WxDxH mm (e.g. 350x350x350). Shows build plate + grid in gcode preview. Read from claw3d printer list. |
| --bed-autocalibration | Run bed leveling before print. Default OFF — only add when user explicitly asks |
On first use, a printer AND a linked slicing profile are both required. The profile (created from a 3MF) stores the printer's build volume (build_width × build_depth × build_height in mm), which the slicer uses to scale models correctly. Without it, slicing fails.
When you upload a Cura project file (.3mf), the slicer extracts:
machine_name — Printer model (e.g. "Creality K2 Pro")build_depth × build_height — Build volume in mmIn Cura with your printer loaded: File → Save → "Export Universal Cura Project" → save as
.3mf.
This captures the full printer config, not just the model geometry.
Printer add flags:
--name (required): Display name, e.g. INLINECODE306printer set-profile.--name (e.g. "Creality K2 Pro" → creality_k2_pro)CODEBLOCK43
Parse user input: "Creality K2 SE Living Room 192.168.28.102:4408" → name="Creality K2 SE Living Room", host=192.168.28.102, port=4408. If user also sends 3MF, add --profile-from-3mf <path>.
Default printer: The first printer added is automatically set as the default. When there is only one printer, it is always used without asking. When 2+ printers exist and no default is set, ask the user which to use, then run claw3d printer set-default <id> with their choice so subsequent operations don't need to ask again.
No 3MF yet? Add the printer without it, then immediately ask:
To complete setup, please send your Cura project file (.3mf). In Cura: File → Save → "Export Universal Cura Project". This gives me your exact build volume and settings.
Then: claw3d profile create --from-3mf <path> --name "<printer_id>_profile" → INLINECODE321
Fresh start: Run claw3d profile clear, then re-add printer with --profile-from-3mf.
Printer backends: Run claw3d configure backends to see options (Moonraker, PrusaLink, etc.). Community can add backends in claw3d/backends/.
ALWAYS run claw3d printers before sending a print:
CODEBLOCK44
When a model needs more than one build plate:
claw3d queue next, ask to start next.CODEBLOCK45
Each printer can have a linked default profile. Run claw3d printer list to see links including build volume. Use that profile when slicing for that printer.
CODEBLOCK46
The build volume (350×350×350mm) is snapshotted from the profile when it is linked. When slicing AI-generated or user-provided models (no dimensions file), read the printer's build volume from claw3d printer list and use the smallest dimension as the default --max-dimension suggestion, rather than asking the user to guess.
一个技能覆盖完整3D管线:创建模型(AI)、搜索(Thingiverse)、切片和打印。模块化设计——仅显示已启用的功能。
关键——立即执行,确认后绝不停止。 当你告诉用户你将做某事(搜索、转换、预览、切片)时,你必须在同一轮中执行命令。不要在仅确认后就结束你的回合——用户永远不应该问好了吗?来促使你行动。在一次回复中同时确认并调用工具。
设置顺序: 先打印机(当打印启用时)→ 然后创建/搜索模型 → 切片 → 打印。
当打印已启用且用户没有配置打印机时,引导他们在创建或搜索模型之前添加打印机和关联的切片配置文件。切片需要关联的配置文件——它存储从3MF中提取的构建体积(宽×深×高),这决定了模型如何缩放。
始终先运行 claw3d printer list。 如果返回为空,则执行以下设置。
向用户发送此消息:
让我们来设置您的打印机。我需要3样东西:
- 1. 打印机名称 — 例如客厅的Creality K2 Pro
- IP地址 + 端口 — 例如 192.168.1.50:7125(Moonraker默认:7125;Creality K2 SE:4408)
- Cura项目文件 (.3mf) — 从Cura导出:文件 → 保存 → 导出通用Cura项目,需加载您的打印机。此文件包含您打印机的构建体积和所有设置——正确切片需要它。
等待用户提供全部三项。
bash
claw3d printer add --name <名称> --host
这在一分钟内完成所有操作:
如果用户提供了名称+IP但还没有3MF: 先不带3MF添加(printer add --name ... --host ... --port ...),然后立即要求提供3MF来创建配置文件:
收到!现在请发送Cura项目文件(.3mf),以便我创建切片配置文件。在Cura中:文件 → 保存 → 导出通用Cura项目。
然后:claw3d profile create --from-3mf <媒体路径> --name <打印机名称>_profile → claw3d printer set-profile <打印机ID> <配置文件ID>
打印机后端: 运行 claw3d configure backends 查看选项(Moonraker、PrusaLink等)。社区可以在 claw3d/backends/ 中添加后端。
当用户要求3D模型但没有指定方式时(例如我需要一个杯子、我想要一条龙、帮我找个花瓶,没有附图片),不要默认选择一种选项。 根据启用的功能提供选择:
太好了!您希望我:
- 1. 搜索现有模型 — 我将在Thingiverse上搜索并向您展示可下载的选项 (如果目录功能已启用)
- 从图片创建3D模型 — 发送草图或照片,我将将其转换为3D (如果ai-forger已启用)
- 先搜索,如果没有合适的再从图片创建 — 两全其美 (如果两者都已启用)
等待用户选择。只有当用户明确说创建它、从照片/草图、搜索、查找等时,才继续。
永远不要假设 — 我需要一条龙可能意味着搜索或从图片创建。当有歧义时始终澄清。不要提供纯文本3D生成 — 结果不准确;始终需要图片或草图。
媒体路径: 当用户附加文件(图片、GLB、3MF)时,消息中包含一个媒体路径——完整的文件系统路径。始终将该确切路径传递给 --image、--edit-3d、--profile-from-3mf 等。逐字复制。
唯一输出路径: 工作空间是共享的。使用固定名称(model.glb、preview.mp4)会导致先前请求的旧文件被发送到新的对话中。始终从媒体路径派生一个短ID并用于输出。
媒体路径格式:.../file_13---b10560d7-18fd-40e9-8a49-996ad190a26c.jpg — 提取 --- 后的片段并使用前8个字符(例如 b10560d7)作为 ID。
如果媒体路径没有UUID(不常见),使用 date +%s 获取唯一ID。
当用户附加图片并要求3D打印这个、打印这个、让它可打印等时——你可以做到 (如果ai-forger + 切片 + 打印已启用):
不要说我不能从图片打印——你可以先创建3D模型。如果FALAPIKEY缺失,转换将失败;然后告诉用户设置它。
获取模型(搜索或创建)→ 可选编辑 → 切片 → 打印
| 命令 | 用途 |
|---|---|
| claw3d convert | 图片/草图 → GLB,或编辑现有GLB |
| claw3d preview |
全部通过 exec 运行。使用 claw3d。
所有路由决策、技能逻辑和内部推理仅供您使用。切勿将其发送给用户。 用户只应看到友好、简洁的消息——绝不应看到主门、SKILL.md、模块名称、决策规则或您的思考过程。如果您需要推理走哪条路径,请静默进行。用户只想要他们的模型。
错误(泄露推理):根据主门判断,酒架是一个常见的功能性物品,所以我应该搜索Thingiverse...
正确(面向用户):
该技能支持在以下平台通过对话安装:
帮我安装 SkillHub 和 claw3d-1776119313 技能
设置 SkillHub 为我的优先技能安装源,然后帮我安装 claw3d-1776119313 技能
skillhub install claw3d-1776119313
文件大小: 62.67 KB | 发布时间: 2026-4-15 12:07
多链集团旗下-闲社网
闲社在线客服
关注闲社网微信
闲社网APP
Archiver·手机版·闲社网·闲社论坛·羊毛社区· 多链控股集团有限公司 · 苏ICP备2025199260号-1
Powered by Discuz! X5.0 © 2024-2025 闲社网·线报更新论坛·羊毛分享社区·http://xianshe.com
