Skip to content

[Feature Idea] Cheapo topology optimization loop via parametric cuts + SolidWorks SimulationXpress #76

Closed as not planned

Description

@andrewbartels1

Motivation

When designing 3D-printed parts (e.g. PETG TV legs), the workflow today is:

  1. Model in SolidWorks
  2. Manually guess where to put lightening holes
  3. Export STEP → FreeCAD + CalculiX → check Von Mises stress → iterate by hand
  4. Import shapes into Solidworks and make an extrude-cut.

This should be automatable using tools already in this MCP server.


Proposed Feature: "Poor Man's Topo-Opt" via Surface Selection + SimulationXpress Optimize

Inspired by how topology optimization tutorials actually work in practice: run topo-opt → sketch around the surviving material → cut away the rest. This is a free-stack approximation of that loop using only tools already in this repo — no paid Simulation add-in required.

Phase 1 — Identify cut zones (geometry analysis, no FEA needed)

Instead of running a full topology solver, select candidate faces using two criteria:

  • Large surface area — biggest wall panels have the most material to remove
  • Perpendicular or parallel to the applied force vector — these faces carry the least bending stress; faces at ~45° to the load are shear-critical and skipped
# Pseudocode — maps to MCP tools
faces = analyze_geometry(part)   # get face list with normals + areas
force_vec = (0, 0, -1)           # gravity / load direction

candidates = [
    f for f in faces
    if dot(f.normal, force_vec) in [~0, ~1]   # perpendicular or parallel to load
    and f.area > min_panel_threshold           # large enough to be worth cutting
    and f.centroid_height > 0.30 * part_height # stay out of base stress zone
]

Phase 2 — Place parametric demo cuts

For each candidate face, add a single equilateral triangle cut (with corner fillets) driven by a SolidWorks global variable so all holes share one sweepable parameter:

  • Global variable: hole_size = 15 mm ← the optimization target
  • Fillet radius: max(hole_size * 0.10, 1.5 mm)
  • Hole position: face centroid, upper 60–70% of panel height
  • Orientation: point-up triangle (better compressive load path)
  • Coverage cap: hole_size / panel_width ≤ 0.50

MCP call sequence: create_sketch() → add_polygon(sides=3) → add_fillet() → create_cut_extrude() → link dimension to hole_size global variable via set_dimension()

Phase 3 — SimulationXpress Step 6: Optimize

Once holes exist and are linked to hole_size:

  1. Re-run SimulationXpress (fixtures + load already configured)
  2. Step 6 → Optimize → Parameters → link the hole_size dimension
  3. Sweep range: 5 mm → 40 mm, step 2.5 mm
  4. Constraint: max Von Mises stress ≤ yield_Z / target_SF (e.g. 28 MPa ÷ 3 = 9.3 MPa for PETG)
  5. SimulationXpress finds the largest hole_size that satisfies the constraint in a single pass — no manual re-run loop needed
  6. Apply optimal value → rebuild → export STEP for slicer

Full loop sketch (updated)

load_part(path)

# Phase 1: geometry-based zone selection (no FEA required)
candidates = select_cut_faces(force_vec, min_area, no_cut_zone=0.30)

# Phase 2: place parametric cuts driven by global variable
for face in candidates:
    place_triangle_cut(face, global_var="hole_size", initial=15)
    check_constraints()         # min wall, coverage cap, fillet radius
    if constraints_violated:
        rollback_last_cut()

# Phase 3: let SimulationXpress sweep hole_size and find optimum
run_simulation_xpress()
result = optimize_dimension(
    var="hole_size",
    range=(5, 40), step=2.5,
    constraint=f"max_stress <= {yield_z / target_SF}"
)
apply_dimension(result.optimal_value)

output_report(mass_before, mass_after, sf_final, hole_size=result.optimal_value)

New MCP Tool: cheapo_topo (Lightweight Active-Model & Selection Inspection)

We also need a lightweight read-only tool for agent context gathering before modeling or simulation operations.

Purpose

Inspect the active SolidWorks model and any selected surfaces without triggering expensive simulations or rebuilds. Useful for:

  • Understanding which faces are currently selected
  • Getting basic topology summary (face/edge/body counts)
  • Pointing agents to the right SolidWorks API help docs for Simulation workflows

Desired input shape

{
  "document_path": "C:\\path\\to\\part.SLDPRT",
  "selection_mode": "active_selection",
  "include_topology": true,
  "include_help_links": true,
  "max_faces": 25,
  "include_mass_properties": false
}

Desired output shape (success)

{
  "status": "success",
  "document": {
    "title": "part.SLDPRT",
    "path": "C:\\path\\to\\part.SLDPRT",
    "type": "Part",
    "configuration": "Default",
    "feature_count": 42
  },
  "selection": {
    "selected_count": 3,
    "selected_entities": [
      {
        "entity_id": "Face<12>",
        "type": "Face",
        "kind": "planar",
        "area_mm2": 1248.7,
        "normal": [0, 1, 0]
      },
      {
        "entity_id": "Face<18>",
        "type": "Face",
        "kind": "cylindrical",
        "area_mm2": 932.2,
        "normal": [0.7, 0.1, 0.7]
      }
    ]
  },
  "topology_summary": {
    "face_count": 28,
    "edge_count": 61,
    "body_count": 1,
    "shells": 2
  },
  "help_links": [
    {
      "label": "ICosmosWorks",
      "url": "https://help.solidworks.com/2026/english/api/swsimulationapi/SOLIDWORKS.Interop.cosworks~SOLIDWORKS.Interop.cosworks.ICosmosWorks.html"
    },
    {
      "label": "SolidWorks API Help Index",
      "url": "https://help.solidworks.com/2026/english/api/help_list.htm?id=11"
    }
  ],
  "execution_time": 0.23
}

Error output shape

{
  "status": "error",
  "message": "No active SolidWorks document or no valid selection set found.",
  "help_links": [
    {
      "label": "ICosmosWorks",
      "url": "https://help.solidworks.com/2026/english/api/swsimulationapi/SOLIDWORKS.Interop.cosworks~SOLIDWORKS.Interop.cosworks.ICosmosWorks.html"
    }
  ]
}

Design notes

  • Intentionally cheap: no rebuild, no mesh generation, no simulation solve — read-only inspection only
  • Good first pass: before more expensive modeling or simulation prep workflows
  • Selection-aware: captures the current user's selected faces to help agents reason about where cuts or constraints should go
  • Help link embedding: returns the official SolidWorks Simulation API docs + help index so agents can reference the correct COM interfaces

References


Parametric cuts via global variables / equations

Each cut is driven by SolidWorks global variables and equations (not hardcoded dimensions) so that:

  • Hole size, spacing, and fillet radius are exposed as named parameters (e.g. "hole_size", "wall_clearance")
  • The agent can sweep parameter values without rebuilding sketches from scratch
  • Results are reproducible and human-editable after the run

Note: Full parametric variants / global variable / equation-driven curve tooling is already tracked in #23 (thanks @pedropaulovc). This feature depends on — or should be built on top of — those tools once they land.


Cut geometry constraints (FDM-safe defaults)

Constraint Default How enforced
Min remaining wall ≥ 2.5 mm (3 perimeters @ 0.4 mm nozzle) panel_width - hole_size ≥ 5 mm (both sides)
Hole spacing ≥ 1.5× hole width checked before each sketch
No-cut zone Bottom 30% of part (high bending stress) face centroid height filter in Phase 1
Corner fillets ≥ 1.5 mm (prevents stress risers) max(hole_size * 0.10, 1.5)
Max hole coverage ≤ 50% of wall panel area hole_size / panel_width ≤ 0.50

Implementation options

Option A — Free stack (full loop):

  • SolidWorks MCP → export_step() → FreeCAD + CalculiX for initial stress map
  • BESO or ToOptix for topology hint → use result to inform face selection in Phase 1
  • SimulationXpress Step 6 for final hole-size optimization

Option B — Native SW only (no FreeCAD):

  • Skip external FEA entirely; use face normal + area heuristic for Phase 1
  • SolidWorks MCP → SimulationXpress COM automation for stress check + Step 6 optimize
  • Simpler setup; limited to isotropic material model (no Z-axis anisotropy for FDM — use conservative PETG Z-yield as the constraint value to compensate)

Output

  • Lightened .SLDPRT with named, parametric cut features (editable post-run)
  • Report: original mass, final mass, % reduction, optimal hole_size, final safety factor
  • Optional: STEP export of final part ready for slicer

Related issues


Use case that motivated this

Designing PETG TV leg replacements for a Sharp Roku 55–65". FEA showed safety factor ~14–18× at 50 N load — massively overbuilt. Wanted to automate the "cut holes until SF drops to 3×" loop instead of doing it by hand.

/cc @pedropaulovc — the global variable / equation tools in #23 are a natural foundation for the hole_size sweep in Phase 3 here.

Activity

  1. andrewbartels1 commented on Aug 31, 2026

    @andrewbartels1
    OwnerAuthor

    Resolving the Option B premise against #78's finding: SolidWorks's own API docs confirm SimulationXpress has no COM API of its own, but automating SimulationXpress-equivalent functionality (fixtures, loads, meshing, static analysis on a single part) is possible via the SldWorks and CosmosWorks interfaces in a VBA Macro/C#/C++ environment. CosmosWorks is the paid Simulation add-in's COM interface (matches #78's CWAddincallback → CWModelDoc → CWStudyManager → CWStudy → CWMesh/CWLoads/CWFixt... chain) — it can reproduce what SimulationXpress does, but only through the paid add-in.

    So Option B as written ("native SW only... SimulationXpress COM automation... no paid add-in required") has two goals that can't both hold: automation is achievable via CosmosWorks, but not without the paid add-in. Worth re-scoping Option B as "paid Simulation via CosmosWorks" (drops the free-tier promise), or leaning on Option A (FreeCAD + CalculiX, genuinely free but external to SolidWorks) as the only actually-free path. Tracked in docs/planning/roadmap.md.

  2. andrewbartels1 commented on Nov 1, 2026

    @andrewbartels1
    OwnerAuthor

    Moving this to the roadmap (#196) to keep the issue list for work in progress. The write-up here stays as the reference; it gets reopened, or linked from a new issue, when someone picks it up.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

roadmapBigger idea tracked on the roadmap issue

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions