Guide
Python Script Backend
How the app records UI work as Python, executes it, and rebuilds the model.
In FlywheelCAD, the script is not a secondary export. It is the persistent model text. The right-hand editor shows that text directly, and rerunning it reconstructs the design.
Source of Truth
Each document stores plain script text. When a document is opened, FlywheelCAD connects the document text to the command logger and, once the runtime graph is ready, replays the script to rebuild geometry. Because a document is an executable Python script, the app asks before running one whose exact contents you have not approved before.
Document text
The saved file contains Python source — a flat .py, or
main.py inside a .fwcad bundle — not a hidden binary model
representation. Saving prefers the current logger snapshot so the on-disk file matches
the editor.
Command logger
UI actions append new lines into a script buffer. The buffer ensures the standard
preamble exists and inserts the active cad.with_sketch(...) line when the
sketch context changes.
Script editor
The right panel is a real editable text editor. It is not read-only output. You can
change code there and rerun it directly. ⌘Z undoes typing,
⌘F finds and ⌥⌘F finds and
replaces.0.35
Live sync
If the command logger changes while the editor is still in sync, the panel refreshes to show the latest generated script instead of drifting behind the model.
What the UI Writes
A typical UI session quickly becomes ordinary Python lines. The structure is intentionally
simple: import, FlywheelCAD(), sketch context, geometry creation, then
constraints or body operations.
# flywheelcad-format: 1
from flywheelcad import *
cad = FlywheelCAD()
cad.with_sketch("xy")
p1 = cad.point2d(-60, -12.5)
p2 = cad.point2d(-20, -12.5)
l1 = cad.line2d(p1, p2)
cad.horizontal(line=l1)
cad.length(line=l1, length=40)
# additional UI-created lines and a hole circle would follow here
# before the region is turned into a body with cad.extrude(...)
The same model can then be edited by hand. You can rename variables, insert helper imports,
restructure code into functions, or replace repeated UI-authored geometry with loops. Keep
cad = FlywheelCAD() itself at module level: the app inserts document settings,
such as mesh quality, right after that line.
Edit and Rerun Cycle
| 1. Edit text | Change the generated script directly in the right-hand editor. Indentation is kept as raw text so ordinary Python formatting still matters. |
| 2. Execute | Press the Run button in the script pane (clear and run). The editor first loads your current text into the command logger, then execution starts without discarding that text buffer. |
| 3. Python stage |
FlywheelCAD runs the script through a Python subprocess using the bundled
flywheelcad.py module. The script emits CAD commands to stdout; output from
your own print() calls is not treated as a command. At this stage a
cad.variable used where a number is needed — a point coordinate, a
transform — is resolved to its value; only dimensions keep the expression live (see
Python syntax).0.35
|
| 4. Parse and validate | The emitted commands are parsed and validated before geometry changes are applied. This prevents half-applied scripts from mutating the model when syntax or reference errors are present. If a run fails later, during the rebuild itself, the app re-runs the last script that completed cleanly. |
| 5. Replay model | Existing geometry is cleared, origin points and standard planes are recreated, then commands are executed sequentially to rebuild the full design state. |
| 6. Rebuild scene | After execution, FlywheelCAD synchronizes 2D and 3D state, generates missing meshes — on the GPU where possible, including boolean trees evaluated in one pass — then rebuilds the 3D scene so the visual result matches the script. |
Imports and Local Helper Files
The document folder is used as the execution working directory. That is what makes ordinary sibling imports work: helper files next to the main script can be imported directly.
Project/
gearbox.py
CADgears.py
helpers.py
from flywheelcad import *
cad = FlywheelCAD()
from CADgears import gear_outline
from helpers import keyed_slot
gear = gear_outline(center_x=0, center_y=0, tooth_count=24, module=5.0, plane_name="xy")
gear_body = cad.extrude("xy", gear["region_ring"], 24, quality="high")
FlywheelCAD() return the same
singleton instance, so helper modules share the same variable-name counter and the same
origin references. A component module emits its geometry when it is imported, so put
imports of component modules below cad = FlywheelCAD().
The “document folder” is the enclosing folder for a flat .py, or the
bundle itself for a .fwcad project bundle — a folder that
packages main.py with everything it imports so the whole design travels as one
self-contained item. Either way the folder is the working directory, so imports resolve the
same. Catalog parts inserted from a component library are vendored under
lib/<library>/ in that same folder and imported as
from lib.standard.steppers import stepper; a loose helper or component can be
copied in with File → Add File to Project… or
Component → Insert Component from File… so it too travels with the design.
Imported modules appear as read-only tabs in the script pane.
Examples of Script Refinement
Start in the UI
Rough in lines, circles, and regions interactively. Let the logger create a direct, explicit first draft of the script.
Promote shared values
Replace hard-coded dimensions with cad.variable(...) bindings so lengths,
radii, and offsets become easier to reuse and rename. The same variables can also seed
point coordinates and set circle sizes, as in
cad.circle2d(c, HOLE_DIA / 2).0.35
Move generators into helpers
Once geometry becomes patterned or algorithmic, move it into a separate module like
CADgears.py or CADpolygons.py and import it from the main
file.
Rerun until stable
The best endpoint is a script you can rerun from a clean document and get the same model back every time.