Skip to content

Add recipes/ cookbook of common parametric CAD patterns #16

@gsdali

Description

@gsdali

Context

OCCTSwiftScripts has the harness (Sources/Script/main.swift), the runtime (occtkit run), and 10 verbs covering composition, validation, drawing export, feature recognition, and reconstruction. What's missing is a library of worked examples — concrete parametric CAD patterns that show the full toolchain in use, end-to-end.

A recipes folder serves three purposes:

  1. Onboarding. New users (and LLMs driving OCCTMCP) can copy a recipe and tweak parameters instead of starting from a blank main.swift.
  2. Coverage. Building the recipes surfaces latent ergonomic gaps in OCCTSwift — naming inconsistencies, missing convenience inits, awkward API combinations. Each gap becomes a follow-up issue against OCCTSwift.
  3. Distribution narrative. Turns OCCTSwiftScripts from "harness" into "harness + cookbook" — closer to what users expect from CadQuery / OpenSCAD ecosystems.

Proposed structure

recipes/
├── README.md                          # Index + screenshots
├── 01-spur-gear/
│   ├── main.swift                     # ~30–60 lines, runnable with `occtkit run`
│   ├── README.md                      # Algorithm explanation, parameters, gotchas
│   ├── output.png                     # Rendered preview
│   └── output.brep                    # Reference output (for CI smoke test)
├── 02-mounting-bracket/
│   ├── ...
└── ...

Each recipe is self-contained — no shared utility files, no cross-recipe imports. Copy-paste-friendly. Trade some duplication for radically simpler "open one folder, read three files, understand the recipe."

Recipes to seed (10)

Pick a spread that hits the most-used OCCTSwift surface areas. Suggested set, ordered roughly by complexity:

  1. Spur gear — involute tooth profile, parametric module / tooth count / pressure angle / face width. Exercises: 2D wire construction (involute curves via Curve2D), Wire.polygon for closure, Shape.extrude, circular pattern.
  2. Mounting bracket — L-bracket with 4 mounting holes, fillet on the inside corner, optional rib stiffener. Exercises: box, drilled holes, fillets, sweep for rib.
  3. Sheet-metal enclosure — base plate + 4 walls + lid via compose-sheet-metal verb (used as a script preamble), with cuts via reconstruct. Exercises: SheetMetal.Builder, FeatureReconstructor cuts.
  4. Lattice cube — 3D-printable lattice (octet truss or BCC unit cell), parametric cell size and strut diameter. Exercises: linear pattern, sweep along polyline, boolean union of many bodies.
  5. M8×40 bolt — hex head + threaded shank, ISO-standard thread profile. Exercises: hexagonal wire, revolve, helical sweep for threads, chamfer on thread start.
  6. Helical compression spring — parametric coil count / wire diameter / outside diameter / pitch. Exercises: Wire.helix, sweep with section.
  7. Finger-jointed lid box — laser-cut-style box with finger joints on all four corners. Exercises: 2D profile boolean ops, extrude, mirror.
  8. Fan blade — single airfoil-section blade, parametric chord / twist / span. Exercises: lofted surface from multiple section profiles, surface-of-revolution for hub.
  9. Planetary gear set — sun + 3 planets + ring, parametric ratios. Exercises: composition of recipe 1, transforms, assembly via Document / XCAF.
  10. Pipe flange — ANSI-style flange with bolt circle, raised face, gasket groove. Exercises: revolve, drilled bolt pattern, chamfer / fillet, threaded center bore.

(The list is a starting set — the exact recipes can be debated / swapped in the PR. The goal is breadth × ten.)

Per-recipe contract

Each recipe ships:

main.swift (~30–60 lines):

  • Top-of-file comment block: // Inputs: ..., // Outputs: ..., // Notes: ...
  • All parameters as named let constants at the top — no magic numbers buried in code
  • Single try ctx.add(shape, id:, color:, name:) per top-level body
  • Final try ctx.emit(description: "...") describing what was built
  • Runnable with occtkit run recipes/<name>/main.swift --format brep,manifest from repo root
  • No deps beyond OCCTSwift + ScriptHarness

README.md:

  • Title + one-line description
  • Parameters table: name, default, description, valid range
  • Algorithm explanation (3–8 sentences)
  • "OCCTSwift APIs used" — small bulleted list, useful for users searching by API
  • Gotchas / edge cases
  • Embedded output.png

output.png:

  • Rendered preview, isometric or three-view
  • 800×600 px, dark or neutral background (consistent across recipes)
  • Generated by OCCTSwiftViewport's OffscreenRenderer — see Scripts/render-recipe.sh (new) which calls the existing renderer
  • Optional: regenerate via make recipe-render NAME=<name>; missing PNG doesn't fail CI (Viewport may not be available in all environments)

output.brep:

  • Reference output committed for diff-ability
  • CI compares recipe → emit BREP against the committed output.brep via byte-equal or BREP-equivalence check (volume + bounding box + face count tolerance comparison if exact byte match is too brittle)

Tooling

Scaffolder:

make recipe NAME=widget

Creates recipes/NN-widget/ with skeleton main.swift + README.md + a placeholder for output.png. Auto-numbers NN.

CI:

  • Each recipe runs via swift run occtkit run recipes/<name>/main.swift --format brep,manifest
  • Asserts: emitted manifest is valid JSON; emitted BREP is non-empty; bounding box volume > 0
  • Optional reference comparison if output.brep exists
  • Recipe failures don't block unrelated PRs by default (separate CI job, allowed to fail) — promote to required after the seed batch settles

Renderer:

  • make recipes-render walks recipes/ and regenerates each output.png
  • Skips silently if Viewport / OffscreenRenderer not available
  • Don't commit auto-rendered PNGs from CI; treat them as locally-generated artifacts that get committed by the recipe author

Acceptance

  • recipes/ directory with the 10 seed recipes
  • Each recipe has main.swift, README.md, output.png, output.brep
  • Each recipe runs via occtkit run and emits non-empty BREP
  • Top-level recipes/README.md indexing all recipes with thumbnails + one-line descriptions
  • make recipe NAME=... scaffolder
  • CI job (allowed-to-fail initially) running each recipe
  • Top-level repo README links to recipes/ from a new "Examples" section
  • At least 3 follow-up issues filed against OCCTSwift for ergonomic gaps surfaced while building the recipes (this is the canary that the recipes are exercising real surface)

Out of scope

  • Recipe tutorials / video walk-throughs (recipes themselves are the tutorial)
  • Animated preview GIFs (single PNG per recipe is enough for v1)
  • Auto-publication to a recipe gallery website (could be a future GitHub Pages job, separate issue)
  • Recipe-as-NPM-package or recipe-registry semantics — keep them as plain folders for now

Related

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions