Workflow: Geometry Validation
This workflow covers the suite of tools for validating machining geometry after simulation, including collision detection, geometry difference comparison, defect scanning, and flying piece removal.
flowchart TD
Simulate["Run simulation"]
Collision["Collision detection"]
Diff["Geometry difference comparison"]
Defect["Geometry defect scanning"]
FlyPiece["Flying piece removal"]
Simulate --> Collision
Simulate --> Diff
Simulate --> Defect
Simulate --> FlyPiece
1. Collision Detection
Collision detection monitors whether the tool, holder, or spindle collides with the workpiece, fixture, or machine during simulation: the holder and the shank are checked against the stock on every step, the flute against the stock only on moves made before the program gives the spindle a speed, since the flute in the stock with the spindle turning is the cut. A plunge after the spindle is stopped — by M05 or by S0 — is not reported as a collision; a rapid one still raises the rapid-cut warning. Under the Feed Per Cycle or Feed Per Tooth motion resolution, an APT cutter drawn straight back up its own axis counts as touching the stock only when it reaches into it deeper than 0.001 mm: a shallower graze along the retract — what a program's decimals leave against the wall the cutter itself cut — removes nothing, carries no force and raises no rapid-cut warning, whatever RapidCutVolumeThreshold_mm3(API) is set to. The Fixed motion resolution makes no such exception. Before 3.2.42 the pairs against the workpiece were generated but not evaluated, so a holder or shank that entered the stock raised no message. Enable it before running the simulation.
Script Commands
EnableCollisionDetection = true;
EnablePauseOnCollision = false; // set true to pause on collision
| Property | Description |
|---|---|
EnableCollisionDetection |
Enables collision checking during simulation |
EnablePauseOnCollision |
Pauses execution when a collision is detected |
Combined with Pause on Failure
EnablePauseOnFailure provides a broader pause-on-error mechanism:
EnablePauseOnFailure = true;
EnableCollisionDetection = true;
PlayNcFile("NC/file1.nc"); // pauses if a collision occurs
GUI Operation
Enable collision detection in the main options panel before simulation.
Tip
Collision detection adds computation overhead. For exploratory simulations where speed matters, you can disable it and re-enable for final validation.
2. Geometry Difference Comparison
The Diff command compares the simulated workpiece shape against a target (design) shape to identify over-cut and under-cut regions.
Script Command
Diff(<DetectionRadius_mm>);
Detection Radius is the surface extension distance for the target shape. Deviations beyond this distance are not computed. Larger values take longer.
Diff(1); // detection radius = 1 mm
A difference with nothing to compare against builds nothing, and says so. Without an ideal (target) geometry — or with a target STL whose path does not resolve — Diff warns Diff--NoIdealGeom and returns; with no meshed geometry to compare it warns Diff--NoMeshedGeom; with no workpiece in the session at all it reports Diff--Empty. In each of those cases no overlay is attached and Diff--Built is not reported — that message is the positive evidence, and a run that skipped the comparison no longer claims to have finished one. Over the HTTP API the same thing reads as state: GET /api/Workpiece/diff-settings answers hasDiffOverlay — true only while a computed overlay is attached to the live meshed tree, which is neither “there are deviations” (a zero-deviation comparison attaches too) nor “a difference was requested” — and detectionRadius, which is null until an overlay exists and otherwise names the radius that overlay was built with. The overlay goes when the runtime is reset or the meshed tree is swapped, so read the state before the next Reset.
What else the comparison reports. A design whose surface is not closed — open or non-manifold edges, a T-junction counting as open — warns Diff--TargetNotClosed, and the comparison goes on, taking each cell's sign from the simulated part rather than from the design's winding. Without the licence feature it warns Diff--Unlicensed; a comparison that attaches nothing warns Diff--NoResult and gives the part its plain colours back. Neither reports Diff--Built. A completed comparison sends one Diff--Stats message with its counters — cells reported, cells refined, cells with no reading, wires measured, design triangles.
Budget the difference like a run of its own. Its time and memory grow with the size of the part and with every halving of the mesh. On a small part it takes seconds. The comparison measures each surface cell on the cell's own wires and refines only the cells whose design is not one plane within reach; comparing a part with its own design STL at 0.25 mm on the Linux build — the native comparison alone, both arms on one machine — took 1.2 s and 559 MB, 459 MB of which is the stock's tree itself, where the comparison up to 3.2.39, which first meshed the whole tree to its finest level, took 13.7 s and 859 MB. The large case has not been measured again since: with that older comparison, a stock a few hundred millimetres on each side, meshed at 0.25 mm, took about 14 minutes and some 85 GB for a 1 mm difference, where the play itself needed about 4 minutes and 6 GB. Until it is, compare a large part on a coarser replay first, and do not append a difference to a fine full-part run on a shared service instance without knowing the host has the memory to spare.
Interpreting Results
After comparison, the workpiece surface is color-coded:
- Green: Within tolerance
- Red (negative): Over-cut exceeding the threshold – the part has lost material the design keeps
- Blue (positive): Under-cut exceeding the threshold – material is left where the design has none
A stock tree built from the design itself reads within about 1e-6 mm of it everywhere, its edge and corner cells included. Up to 3.2.39 those cells read over-cut by a quarter to a third of the cell width, which drew a red line along every sharp edge of a part that matched.
The colour scale has a radius of its own. DiffVisualRadius_mm is the deviation at which the colouring saturates — 0.1 mm unless the project says otherwise. It is a project setting: the workpiece carries it, the .hincproj writes it as <DiffVisualRadius_mm>, and a file that carries none — or carries a non-positive or non-finite one — reads as the default rather than failing to load. So every snapshot of one part is read against the same criterion. It is independent of the detection radius: a visual radius above the detection radius is accepted and simply means the scale never saturates. Setting it recolours the attached overlay; it never re-runs the comparison, and anything that is not finite and positive is refused.
DiffVisualRadius_mm = 0.05; // saturate at 0.05 mm; saved with the project
Over the HTTP API it is POST /api/Workpiece/diff-settings with {"diffVisualRadius": 0.05}, which answers 400 for a value that is not finite and positive and NotFound when no project is loaded. In the web client it is the Visual Radius on the Program branch's Geometry Difference node.
Note
The path index on the workpiece surface is invalidated after running Diff. If you need to inspect individual step paths, do so before calling Diff.
Case Study: Reciprocating Slope Interference
CAM-generated NC code may contain subtle errors that are invisible without geometric comparison. Common issues found through Diff:
| Issue | Description |
|---|---|
| Right-angle wall under-cut | Under-cut near walls where target geometry has sharp corners |
| Inconsistent Z plunging | Over-cut from inconsistent Z values in reciprocating plunge regions |
| Insufficient radius clearance | Under-cut at reciprocating edges where the tool hasn't moved out by its radius |
| Zebra-pattern under-cut | Under-cut stripes from excessive reciprocating path spacing |
Tip
Without software comparison, these issues can only be discovered after physical machining, significantly impacting precision manufacturing.
3. Geometry Defect Scanning
Geometry defect scanning helps debug abnormal workpiece or tool geometry. This is typically used only when geometry construction problems are suspected.
ScanMeshedGeomInfDefect
ScanMeshedGeomInfDefect scans for infinite edge cut defects in the meshed geometry. After scanning, defect areas are rendered with colored markers.
ScanMeshedGeomInfDefect();
Return values:
true— defects detectedfalse— no defectsnull— unable to execute (e.g., workpiece does not exist)
Workflow: Scan Before Simulation
ScanMeshedGeomInfDefect();
Pause(); // visually inspect defects
ClearDefectDisplayee(); // clear markers
PlayNcFile("NC/file1.nc");
ClearDefectDisplayee
ClearDefectDisplayee removes defect markers from the workpiece:
ClearDefectDisplayee();
Note
Defect markers are automatically cleared when the workpiece is reloaded or the meshed geometry is reset. During workpiece initialization, if construction defects are detected, markers are automatically displayed.
4. Flying Piece Removal
During five-axis cutting, small disconnected residual material fragments (“flying pieces”) may appear. Use RemoveFlyPiece to clean them up.
Script Command
RemoveFlyPiece();
Tip
Run RemoveFlyPiece after simulation and before geometry export (ExportMeshedGeomToStl) to produce a clean output.
Combined Validation Script Example
// Configure and run simulation with collision detection
EnableCollisionDetection = true;
EnablePauseOnCollision = false;
EnablePhysics = true;
MachiningResolution_mm = 0.125;
PlayNcFile("NC/file1.nc");
// Remove any flying pieces
RemoveFlyPiece();
// Compare against target geometry (1 mm detection radius)
Diff(1);
// Scan for geometry defects
var hasDefects = ScanMeshedGeomInfDefect();
if (hasDefects == true)
{
WarningMessage("Geometry defects detected");
}
// Export final geometry
ExportMeshedGeomToStl("Output/final.stl");
WriteStepFiles("Output/[NcName].step.csv");
See Also
- Workflow: Basic Machining Simulation — basic simulation setup
- Workpiece from a Reference Mesh — building the target geometry a difference compares against
- Replay Acceptance over the HTTP API — checking
hasDiffOverlaywith the rest of a replay's evidence - SessionShell — SessionShell quick-reference