Skip to content

Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG .gcode.3mf slice + re-importable project .3mf (H2D-only, supports enabled, scale 1.5× / cable_d 4.5 mm) + PLA-cables and PLA-struts/TPU-cables MM variants (with modeled-in PLA scaffo... - #35

Open
sgbaird-alt with Copilot wants to merge 53 commits into
mainfrom
copilot/get-bambu-sliced-print-t3-prism
Open

Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG .gcode.3mf slice + re-importable project .3mf (H2D-only, supports enabled, scale 1.5× / cable_d 4.5 mm) + PLA-cables and PLA-struts/TPU-cables MM variants (with modeled-in PLA scaffo...#35
sgbaird-alt with Copilot wants to merge 53 commits into
mainfrom
copilot/get-bambu-sliced-print-t3-prism

Conversation

Copilot AI commented May 8, 2026

Copy link
Copy Markdown
Contributor

T3-prism slicing fixes (PR #35 comment 4464399849)

  • Diagnosed "only PLA shown": Metadata/project_settings.config had filament_colour=['#00AE42'] and filament_map=['1'] (length 1) but filament_settings_id/filament_type had length 2 — Bambu Studio uses the shorter array length to determine filament count, so it imported as single-material PLA.
  • Diagnosed "floating supports": scaffold pillars started at SCAD z=0 but the lowest model point is the joint-sphere bottom at SCAD z=-joint_d/2 = -5.25 mm (scale 1.5). When Bambu lifted the assembly so the lowest point sat on the bed, the pillars floated ~5.25 mm above it.
  • Fix 1: patch_mm_extruder.py now also patches Metadata/project_settings.config — pads filament_colour from a default extruder palette and filament_map with ascending extruder IDs to match filament_settings_id length, and switches filament_map_mode to Manual so Bambu Studio honours the per-extruder routing.
  • Fix 2: in t3-prism.scad pillar_to(), drop pillar bases to SCAD z=-joint_d/2 so they reach the bed when the assembled model sits on it (matches the lowest point of the struts/joints).
  • Re-rendered STLs and re-ran render_print.sh end-to-end → all 3 MM project .3mfs now show filament_colour=['#00AE42','#76D9F4'], filament_map=['1','2'], filament_map_mode=Manual; scaffold STL z-range now [-1.75, 113.74] matching the struts STL exactly.
  • Re-rendered t3-prism.H2D-PETG-supports.png verification render.

T3-prism Sobol BO single-batch generator (PR #35 comment 4503109338)

BO batch multi-material project .3mf (PR #35 comment 4503267471)

  • "Split to parts" in Bambu Studio was producing a single object because the BO batch SCAD unioned struts and cables into one mesh and the generator only wrote a single combined STL.
  • Refactored bo/t3-prism-bo-batch.scad to expose per-specimen specimen_NN_struts() / specimen_NN_cables() modules and a top-level part = "all" | "struts" | "cables" switch, mirroring the cad/t3-prism/t3-prism.scad pattern used by the working t3-prism-separate-assembly.zip reference.
  • bo/t3_prism_sobol_batch.py now renders bo/t3-prism-bo-batch-struts.stl and bo/t3-prism-bo-batch-cables.stl as separate STLs (one per material), in addition to the combined preview STL.
  • Wired the BambuStudio CLI --assemble path into the BO script to produce bo/slices/t3-prism-bo-batch.H2D-MM-PLAstruts-TPUcables.3mf with PLA struts on extruder 1 (Bambu PLA Basic @BBL H2D), TPU 85A cables on extruder 2 (Bambu TPU 85A @BBL H2D 0.4 nozzle), and no auto-supports (manual-painting workflow). A --skip-mm-3mf flag is available for SCAD/STL-only runs.
  • Verified the MM project: filament_settings_id=['Bambu PLA Basic @BBL H2D','Bambu TPU 85A @BBL H2D 0.4 nozzle'], filament_type=['PLA','TPU'], filament_colour=['#00AE42','#76D9F4'], filament_map=['1','2'], filament_map_mode=Manual; Metadata/model_settings.config routes the struts STL to extruder 1 and the cables STL to extruder 2 — Split to parts now exposes both as independently-assignable parts.
  • Updated bo/README.md to document the new struts/cables STLs, the MM project .3mf, and the --skip-mm-3mf flag.

BO batch tighter plate spacing (PR #35 comment 4503427854)

  • Tightened the 3×3 plate packing in bo/t3_prism_sobol_batch.py by dropping the strut_d term from the per-specimen footprint estimate and reducing the inter-cell air gap from 5 mm → 2 mm.
  • Grid cell shrinks from 97.0 mm → 86.9 mm per axis (~30 mm tighter overall on the 350×320 mm H2D plate) while still keeping each specimen's bounding cylinder inside its cell.
  • Regenerated bo/t3-prism-bo-batch.{scad,stl,json,csv}, bo/t3-prism-bo-batch-{struts,cables}.stl, bo/t3-prism-bo-batch-{plate,iso}.png, and bo/slices/t3-prism-bo-batch.H2D-MM-PLAstruts-TPUcables.3mf end-to-end.

Captive TPU core inside PLA outer shell joints (PR #35 comment 4511036510)

  • Replaced solid joint spheres at every T3-prism vertex with a captive TPU core inside a hollow PLA outer shell (per PR Explore and validate joint design for PETG/PLA + TPU prints (5 candidate joints + OpenSCAD CAD + anchor-upset shape variants + Design F captive-core + Edison Phase-1/2/3/5 + Phase-4 submitted + lander-context reco + TPU-inside vs TPU-outside comparison... #39 comment 4461700096 / Design F adapted to a 3-cable junction):
    • PLA outer shell (joint_shell() in cad/t3-prism/t3-prism.scad): hollow sphere with a teardrop hull blend toward the strut and one cylindrical exit bore per outgoing TPU cable (3 per joint).
    • TPU captive core (joint_core() in cad/t3-prism/t3-prism.scad): solid sphere inside the cavity, continuous with the cable end-caps emerging through the bores.
    • Print-in-place clearance: bore = cable_d + 0.8 mm, core_od ≥ bore + 3 mm (TPU mass cannot back out any single bore), shell_id = core_od + 1 mm, shell_od = shell_id + 3.2 mm PLA wall.
    • use_captive_core toggle in t3-prism.scad (default true) preserves the legacy solid-joint path for direct comparison.
  • Mirrored the captive-core joint verbatim in the BO batch generator (bo/t3_prism_sobol_batch.py SPECIMEN_TEMPLATE) so every per-specimen joint is also captive-core, with per-specimen cable_d-derived shell/core/bore sizing.
  • Updated render_print.sh offset_z (3.5 → 8.15 mm), pillar_to(), and bo/specimen_footprint() / z_lift so the now-lower PLA shell underside lands on the bed and the per-specimen plate-grid cell accommodates the (larger) shell OD.
  • Re-rendered cad/t3-prism/{t3-prism, t3-prism-struts, t3-prism-cables, t3-prism-struts-scaffold}.stl + t3-prism-iso.png, and bo/t3-prism-bo-batch{.scad, .csv, .json, .stl, -struts.stl, -cables.stl, -plate.png, -iso.png}.
  • Documented the captive-core joint geometry, clearance rationale, and use_captive_core toggle in cad/t3-prism/README.md and bo/README.md.

TPU misalignment with joints

  • Diagnosed: previously cables.stl lowest world-Z was -cable_d/2 while struts.stl lowest was -max(strut_d, joint_d)/2; Bambu Studio's per-part auto-bed-placement therefore dropped the cables vs. the struts by ~3 mm — exactly the reported "horizontal cables going to the wrong z-height on the top and bottom".
  • Fixed by giving cables.stl the same world-Z bounding box as struts.stl:
    • The new captive TPU core spheres at every joint vertex naturally extend the cables-STL bbox to ±core_od/2.
    • Plus a 5 µm × 5 µm axial spike (cables_z_anchor() in t3-prism.scad, equivalent inline cube in the BO SPECIMEN_TEMPLATE) that pins the cables STL bbox to exactly the struts STL extents.
  • Verified at scale 1.5×: t3-prism-struts.stl z=[0.017, 121.283] vs t3-prism-cables.stl z=[0.000, 121.300] — sub-mm match. Verified for BO batch: struts.stl z=[0.068, 116.925] vs cables.stl z=[-0.000, 117.072] — sub-mm match across all 9 specimens.

BO batch plate spacing + prime tower reserve (PR #35 comments 4513164299 / 4513445377)

  • Added a reserved strip on +X of the H2D plate for the IDEX prime/flush tower (PRIME_TOWER_RESERVE_X), drawn as a thin slab marker in the preview SCAD only (not into the struts/cables STLs).
  • First pass dropped to 6 specimens in a 3×2 layout with a 12 mm air gap and 70 mm reserve; per follow-up feedback ("keep it to 3×3"), reverted N_SPECIMENS back to 9 in a 3×3 grid with a 6 mm inter-cell air gap and a 50 mm prime-tower reserve strip on +X, keeping the layout inside the 300×320 mm usable plate area while leaving room for the wipe tower.
  • Regenerated bo/t3-prism-bo-batch.{scad,stl,json,csv}, bo/t3-prism-bo-batch-{struts,cables}.stl, bo/t3-prism-bo-batch-{plate,iso}.png, and bo/slices/t3-prism-bo-batch.H2D-MM-PLAstruts-TPUcables.3mf end-to-end.
  • Added bo/__pycache__/ to .gitignore.

Bonded captive-core joints + per-specimen object grouping (PR #35 comment 4513722886)

Addressing three asks from @sgbaird:

  • TPU members connect at every vertex — the captive TPU core sphere at each vertex unions all three cable end-cap spheres + cable cylinders into one continuous TPU mass.
  • Full spherical PLA shell around each TPU vertex with no gaps except cable bores, in contact with the TPU core so the materials bond:
    • Dropped the teardrop hull blend toward the strut (every vertex shell is now a uniform sphere — consistent across all six vertices).
    • captive_core_clear = 0 so the TPU core touches the PLA inner wall (was a 0.5 mm radial print-in-place gap → now bonded).
    • captive_bore_clear = 0 so the PLA bore is exactly cable_d and the TPU cable fills it without an annular gap (was 0.4 mm/side).
    • Mirrored the same captive-core geometry in bo/t3_prism_sobol_batch.py SPECIMEN_TEMPLATE.
  • Each tensegrity iteration on the plate is its own Bambu Studio object with two part groups (PLA + TPU)bo/t3_prism_sobol_batch.py now:
    • Adds a spec=-1 filter to the generated batch SCAD so individual specimens can be rendered (-D spec=N).
    • Renders per-specimen STLs into bo/per-specimen-stls/t3-prism-bo-specNN-{struts,cables}.stl (one pair per specimen).
    • Passes all 2N STLs to BambuStudio --assemble and post-processes the resulting .3mf with a new _split_assembled_into_objects() helper that splits the single composite into N composite objects, each containing one struts part (extruder 1 / PLA) and one cables part (extruder 2 / TPU). Objects are not grouped; each can be moved independently while its PLA + TPU parts move together.
    • Verified in bo/slices/t3-prism-bo-batch.H2D-MM-PLAstruts-TPUcables.3mf: 9 <object> entries, each with two <part>s (struts→ext1, cables→ext2); 9 <model_instance> entries on the plate; filament_type=['PLA','TPU'], filament_map_mode=Manual, filament_map=['1','2'].
  • Re-rendered cad/t3-prism/{t3-prism, t3-prism-struts, t3-prism-cables, t3-prism-struts-scaffold}.stl + iso PNG, re-assembled cad/t3-prism/slices/t3-prism.H2D{,-PETG,-PETG.gcode,-MM,-MM-PLAcables,-MM-PLAstruts-TPUcables}.3mf, re-rendered bo/t3-prism-bo-batch-{plate,iso}.png + bo/t3-prism-bo-batch{,-struts,-cables}.stl + the 18 per-specimen STLs.
  • Updated cad/t3-prism/README.md and bo/README.md to document the bonded captive-core geometry and the per-specimen object grouping.

Accelerometer "igloo" mount on top vertices (PR #35 comment 4794790065)

Addressing @sgbaird's request to extrude a block on top of the top vertices with a pocket to secure the 3-axis accelerometer:

  • Added a parametric accelerometer mount to cad/t3-prism/t3-prism.scad (accel_mount() / accel_mount_local(), plus accel_* parameters and helper functions) fused onto each of the three top vertices:
    • Pocket sized to the Dytran 3133A4 accelerometer (measured 6 × 6 × 5.94 mm L×W×H, per PR Analyze drop-tower accelerometer "tuning" data (issue #71) #74 comment 4792400480), with accel_clear = 0.4 mm/side clearance for the adhesive bead and slide-in fit. Because the accelerometer is a physical part, its dimensions are absolute mm and are not multiplied by scale_factor.
    • Three walls + a floor and one open outward-facing front so the sensor slides in from the side and its cable feeds out horizontally.
    • A rounded "igloo" crown (accel_dome) over the pocket to reduce friction against the acrylic drop-test plate.
    • The mount is PLA and is unioned into t3_prism_struts(), so it routes to extruder 1 in the MM variant. Toggleable via add_accel_mount (default true).
    • Extended cables_z_anchor() by accel_rise() so the cables STL bounding box still matches the now-taller struts STL (verified sub-mm parity).
  • Re-rendered cad/t3-prism/{t3-prism, t3-prism-struts, t3-prism-cables, t3-prism-struts-scaffold}.stl + t3-prism-iso.png, and regenerated all cad/t3-prism/slices/*.3mf end-to-end via render_print.sh (BambuStudio CLI v02.06.00.51).
  • Documented the mount geometry, parameters, and igloo rationale in cad/t3-prism/README.md.

Accelerometer mount: flat seat above joint apex + 0.2 mm tolerances (PR #35 comment 4805516634)

Addressing @sgbaird's feedback that the joint underneath was poking through the pocket so the accelerometer could not sit flat, and the request to change the tolerances to 0.2 mm top / 0.2 mm bottom:

  • Flat pocket floor that clears the joint for all designs by default: the pocket floor was previously sunk below the joint apex (at apex − 0.5 mm), so the rounded captive-core joint shell poked up into the pocket. accel_mount() now places the pocket floor a full accel_floor (1.5 mm) above the joint apex V[2] + joint_outer_r(), while accel_mount_local() extends the body underside to -(accel_floor + accel_sink) so the walls still sink accel_sink (2 mm) past the apex and stay fused to the joint. Because the seat height is derived from joint_outer_r() (which tracks cable_d / scale_factor), the floor clears the joint apex for every design and scale by default (verified at scale 1.5×: top-vertex apex z=112.65 < pocket floor z=114.15; struts STL z=[0.52, 131.63] vs cables STL z=[0.50, 131.64] — sub-mm parity preserved).
  • 0.2 mm top / 0.2 mm bottom Z tolerances: added accel_clear_top and accel_clear_bot (0.2 mm each) for the pocket depth (accel_pocket_z() = accel_h + accel_clear_top + accel_clear_bot); the 0.4 mm lateral (XY) slide-in fit accel_clear is unchanged. Updated accel_rise() to drop the accel_sink term accordingly.
  • Re-rendered cad/t3-prism/{t3-prism, t3-prism-struts, t3-prism-cables, t3-prism-struts-scaffold}.stl + t3-prism-iso.png, regenerated all cad/t3-prism/slices/*.3mf end-to-end via render_print.sh (BambuStudio CLI; single-material sliced job return_code=0, 2.90 h / 34.87 g; MM project filament_type=['PLA','TPU'], filament_map_mode=Manual, filament_map=['1','2']), and re-rendered t3-prism.H2D-PETG-supports.png.
  • Documented the flat-floor seat geometry and the new top/bottom tolerance parameters in cad/t3-prism/README.md.

Accelerometer mount: fill the outer void / remove the overhanging lip (PR #35 comment 4813200802)

Addressing @sgbaird's feedback that there was an outer void under the igloo that should be filled by extruding from the surface below up to the underside of the igloo, removing the lip around the edge that could be a stress point:

  • Diagnosed the void: the igloo body's flat rectangular underside is wider than the rounded joint beneath it, so its rim overhung an unsupported gap — a thin lip / stress riser that could crack.
  • Added a skirt to accel_mount() that convex-hulls the body's underside footprint down onto the joint sphere, so PLA runs continuously from the joint surface up to the underside of the igloo (void filled, overhanging lip removed). Because it is derived from joint_outer_r(), this is correct for every design/scale by default.
  • The skirt re-applies the joint shell's cavity (captive_shell_id) and cable-bore cuts — the bores are lengthened so they always punch through the thicker fillet wall — so the captive TPU core and the three cable exits stay open. Struts STL volume topology is unchanged (manifold) and struts/cables world-Z parity is preserved (struts z=[0.516, 131.631] vs cables z=[0.500, 131.640]).
  • accel_mount() now takes the per-vertex cable_dirs so the call site passes vertex_cable_dirs_t(i).
  • Re-rendered cad/t3-prism/{t3-prism, t3-prism-struts, t3-prism-cables, t3-prism-struts-scaffold}.stl + t3-prism-iso.png, regenerated all cad/t3-prism/slices/*.3mf end-to-end via render_print.sh (MM project filament_type=['PLA','TPU'], filament_map=['1','2'], filament_map_mode=Manual), and re-rendered t3-prism.H2D-PETG-supports.png.
  • Documented the skirt / void-fill geometry in cad/t3-prism/README.md.

Copilot AI linked an issue May 8, 2026 that may be closed by this pull request
Copilot AI changed the title [WIP] Get bambu sliced print for T3-prism Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG slices May 8, 2026
Copilot AI requested a review from sgbaird-alt May 8, 2026 17:41
@sgbaird-alt

Copy link
Copy Markdown
Collaborator

@copilot we want a bambu lab 3mf file, similar to what's described in vertical-cloud-lab/powder-doser#23

We've started this print. It's printing without supports.
@sgbaird
sgbaird marked this pull request as ready for review May 8, 2026 17:53
Copilot AI review requested due to automatic review settings May 8, 2026 17:53
@me-madsen

Copy link
Copy Markdown
Collaborator

We've taken the file produced and began to print it without supports. The 3mf file is uploaded in this branch. A picture of the finished print will be posted later.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds a new cad/t3-prism/ subtree that provides a parametric OpenSCAD model of a canonical T3 tensegrity prism and a headless pipeline to render/check/slice it into Bambu-targeted PETG G-code, along with committed manufacturing artifacts (STL/PNG/G-code/3MF).

Changes:

  • Added parametric T3-prism OpenSCAD source (t3-prism.scad) with strut/cable connectivity and printable single-piece geometry.
  • Added a one-shot render/slice script (render_print.sh) to produce STL, an isometric preview PNG, and two bed-size-specific G-code outputs.
  • Documented the CAD deliverable and wired it into the repo structure (README.md, cad/t3-prism/README.md) and ignore rules (.gitignore), plus committed the generated artifacts.

Reviewed changes

Copilot reviewed 4 out of 10 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
README.md Adds cad/t3-prism/ to the repository structure overview.
cad/t3-prism/t3-prism.scad Parametric OpenSCAD definition of the single-piece T3-prism geometry.
cad/t3-prism/render_print.sh Headless pipeline: SCAD→STL, admesh check, PNG preview, PrusaSlicer CLI G-code export for two Bambu bed sizes.
cad/t3-prism/README.md Build/slice instructions, geometry/parameter documentation, and artifact links.
cad/t3-prism/t3-prism.stl Committed printable mesh artifact.
cad/t3-prism/t3-prism-iso.png Committed isometric preview image artifact.
cad/t3-prism/slices/t3-prism.X1C-PETG.gcode Committed G-code targeting 256×256 Bambu-class beds.
cad/t3-prism/slices/t3-prism.A1mini-PETG.gcode Committed G-code targeting 180×180 Bambu A1 mini bed.
cad/t3-prism/t3-prism.3mf Committed 3MF artifact present in the directory (currently not documented in the CAD README).
.gitignore Adds an ignore rule intended for scratch outputs.

Comment thread cad/t3-prism/README.md
@@ -0,0 +1,107 @@
# T3-prism (3-strut tensegrity) — Bambu PETG print

Resolves the issue [_"Get a bambu sliced print for a T3-prism"_](../../README.md):
Comment thread cad/t3-prism/README.md Outdated
| File | What |
| ---- | ---- |
| [`t3-prism.scad`](t3-prism.scad) | parametric source |
| [`t3-prism.stl`](t3-prism.stl) | watertight binary STL (manifold, single part) |
Comment thread cad/t3-prism/README.md
Comment on lines +99 to +103
## References & related work

- Issue: ["Get a bambu sliced print for a T3-prism"](../../README.md)
- Programmatic-CAD pattern reused from
[`vertical-cloud-lab/powder-doser` PR #16](https://github.com/vertical-cloud-lab/powder-doser/pull/16)
Comment thread cad/t3-prism/render_print.sh Outdated
Comment on lines +48 to +52
echo "==> OpenSCAD render -> ${STL##*/}"
xvfb-run -a openscad -o "${STL}" --export-format=binstl "${SCAD}"

echo "==> admesh manifold check"
admesh -fundecvb "${SCRATCH}/t3-prism-clean.stl" "${STL}" \
…reserve Marcus's project 3mf

Agent-Logs-Url: https://github.com/vertical-cloud-lab/tensegrity-optimization/sessions/bfc1f8fe-27b9-40fe-8c9d-f46712cc281e

Co-authored-by: sgbaird-alt <71569943+sgbaird-alt@users.noreply.github.com>

Copilot AI commented May 8, 2026

Copy link
Copy Markdown
Contributor Author

@copilot we want a bambu lab 3mf file, similar to what's described in vertical-cloud-lab/powder-doser#23

Switched the pipeline to produce real Bambu .gcode.3mf files using the empirical recipe from powder-doser PR #23 — official BambuStudio v02.06.00.51 AppImage under xvfb-run + software GL, with flatten_bambu_profile.py to walk the bundled BBL profiles' inherits: chain (the CLI doesn't resolve it), the three identity-field patches (from=system, inherits="", printer_settings_id), and curr_bed_type=Textured PEI Plate so PETG passes the bed-compatibility check. Also rebased onto Marcus's commit so cad/t3-prism/t3-prism.3mf (the H2D project file currently printing) is preserved untouched, and added an H2D-targeted slice that mirrors his settings — Bambu PETG Basic @BBL H2D 0.4 nozzle, IDEX manual filament-map (--filament-map-mode Manual --filament-map 1, --slice 1 because the manual-map setup is gated by plate_to_slice != 0), no supports. All three slices return return_code: 0, error_string: "Success." (a8a38ef):

Printer File Print time PETG Supports
H2D slices/t3-prism.H2D-PETG.gcode.3mf 1 h 30 m 46 s 6.74 g off
X1C slices/t3-prism.X1C-PETG.gcode.3mf 1 h 25 m 47 s 6.74 g auto
A1 mini slices/t3-prism.A1mini-PETG.gcode.3mf 1 h 5 m 33 s 6.85 g auto

Copilot AI changed the title Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG slices Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG .gcode.3mf slices (H2D / X1C / A1 mini) May 8, 2026
@sgbaird-alt

Copy link
Copy Markdown
Collaborator

@copilot we'll only ever be doing H2D. Make a note of that in copilot-instructions.md ; So far, print (using the stl that Marcus downloaded from you) seems ok. We'll see once we get to the "cantilever warning" (maybe it's too far to be considered a bridge)

image

I tried importing slices/t3-prism.H2D-PETG.gcode.3mf, but got the following errors:

The file does not contain any geometry data
Loading of a model file failed

image

If it helps, you can also have a look at the 3mf file that Marcus uploaded (cad/t3-prism/t3-prism.3mf) and so far seems to be printing OK, to see if you can catch any errors. Send the code and figures and files to edison analysis to get some feedback as well on what might be going wrong while trying to import it. Look at bambu lab forum etc. to also figure out what might be going on.

@sgbaird-alt

Copy link
Copy Markdown
Collaborator

@copilot also, make a second version of this print such that it is a multi-material print. One material as PETG and one material as PLA. One material type for the struts and one for the "strings" (up to you which you make PETG vs. PLA, I'm not sure which would mimic more the tensegrity structure, but we'll be swapping one of these out with TPU eventually anyway)

…n copilot-instructions.md

Agent-Logs-Url: https://github.com/vertical-cloud-lab/tensegrity-optimization/sessions/2b0380fe-5fe2-417a-bcb8-ead0b3206e74

Co-authored-by: sgbaird-alt <71569943+sgbaird-alt@users.noreply.github.com>

Copilot AI commented May 8, 2026

Copy link
Copy Markdown
Contributor Author

@copilot we'll only ever be doing H2D. Make a note of that in copilot-instructions.md ; So far, print (using the stl that Marcus downloaded from you) seems ok. We'll see once we get to...

Done in 08a139d:

H2D-only: added a new "Hardware / target printer" section to .github/copilot-instructions.md with the H2D-only constraint, the verified PETG profile triple (Bambu Lab H2D 0.4 nozzle / 0.20mm Standard @BBL H2D / Bambu PETG Basic @BBL H2D 0.4 nozzle), and the IDEX-needs---filament-map-mode Manual --filament-map 1 --slice 1 caveat. Dropped slices/t3-prism.X1C-PETG.gcode.3mf and slices/t3-prism.A1mini-PETG.gcode.3mf; render_print.sh now calls slice_bambu once.

Import error: confirmed the failing file is a sliced print job, not a project — Bambu Studio's drag/import deliberately rejects .gcode.3mf (which carries Metadata/plate_1.gcode, ~3.97 MB of actual print g-code) with "does not contain any geometry data" because the import path treats it as a printer-side artifact. The fix is a second CLI pass without --slice, which produces a true project .3mf. Now committed:

File Use Size
slices/t3-prism.H2D.3mf Open in Bambu Studio (project, re-sliceable, drag-and-drop or File → Open Project) 175 KB
slices/t3-prism.H2D-PETG.gcode.3mf Upload to printer (LAN MQTT param: "Metadata/plate_1.gcode") 1.06 MB

Both regenerated by bash cad/t3-prism/render_print.sh, both return_code: 0, error_string: "Success.", both 385 layers @ 0.20 mm / 6.74 g PETG / 1 h 30 m 46 s / no supports — settings match your in-progress print.

Edison ANALYSIS: submitted task 25c1c897-6d66-462f-bfdb-7df05ff12d9b (non-blocking) with all 9 relevant files attached — both 3mf flavors, scad, stl, iso png, render_print.sh, flatten_bambu_profile.py, README. Asked for (a) confirmation/refutation of the project-vs-sliced hypothesis with Bambu Lab forum citations, (b) cantilever-warning / print-quality assessment for the H2D PETG print at the upcoming top-triangle bridge. I'll fetch results and wire them into the README next session.

Copilot AI changed the title Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG .gcode.3mf slices (H2D / X1C / A1 mini) Add T3-prism (3-strut tensegrity) parametric CAD with Bambu PETG .gcode.3mf slice + re-importable project .3mf (H2D-only) May 8, 2026
@me-madsen

me-madsen commented Jul 28, 2026

Copy link
Copy Markdown
Collaborator

@achris0520 integrated an idea similar to #35 (comment) by adding a somewhat surrounding support that constricted movement.
Timelapse: https://youtu.be/2wneIJc1WV8

Added additional edge supports along cables to minimize wobble. Left gaps between bottom and edge supports to maintain easy removal. Realized partially through print the 'Support/object xy distance' needed to be smaller to make contact in order to minimize wobble. Only slight improvement from previous print. Will fix on next print.

It should be noted that removing these supports was slightly more difficult than removing prior supports, however they were still relatively easy to remove. Below is picture and video documentation on the supports applied, the stabilized printing in action, the printed model, and a comparison video of the last few prints.

The applied supports:
image

There is almost no visible wobble on the tendons:

20260728_104541.mp4

The printed model, id "Cruela":
20260728_133009
20260728_134557

Video showing each of the last 4 prints: https://byu.box.com/s/d8kga3d5djcrvkiys7non9thdhvg413z
also: https://youtube.com/shorts/n7wlCLvXLmI?feature=share

@me-madsen

me-madsen commented Jul 29, 2026

Copy link
Copy Markdown
Collaborator

@achris0520 changed the default 'Support/object xy distance' from .35 to .2 to minimize wobble. Much improved.
Timelapse: https://youtu.be/xVBunPal9Kw

The most recent print, bpX68c, using the same specimen here #35 (comment) turned out even better and more consistent. It seems likely that humidity does not play as large a role in tendon quality as tendon stabilization during printing. Though there were still some imperfections likely attributable to moisture, the tendons printed significantly more uniform with very few print errors compared to the last three prints of the exact same digital model. Though consistency is yet to be shown, it appears that stabilizing the tendons so they cannot wobble/wiggle significantly improves the print quality.

It should be noted that these supports were more difficult to remove, and at certain points it seemed a risk of breaking the tendon removing the supports as the supports had bonded to the tendons more significantly with this print. I estimate it would consistently take 10 to 20 minutes to remove supports for models printed this way.

20260729_100242 20260729_121805

@sgbaird

sgbaird commented Jul 30, 2026

Copy link
Copy Markdown
Collaborator

@claude we need the T3 prism structures associated with the first Sobol batch (#35 (comment), note you'll likely need to use github api to be able to see the comments, since there are several hundred hidden items/comments in this thread); however, these structures need to be re-generated with the latest housing design for the sensors. Also make sure that the constant mass constraint and the max volume constraint (if I'm not mistaken, those being the two constraints we imposed) are met and that we're using the same fixed mass as we have been in our most recent prints.

@claude

claude Bot commented Jul 30, 2026

Copy link
Copy Markdown

First Sobol batch regenerated with the latest sensor housings + both constraints enforced (cf39fe0)

How the constraints were applied

Constant mass (Route A): each design's (R, H, strut_d, cable_d, joint_d) is uniformly re-scaled — twist and all shape ratios preserved, exactly the projection sim_bo_hybrid_campaign.py prescribes — until its as-printed solid mass equals m* = 30.95 g. Because the sensor housings are absolute-mm physical fixtures that don't scale (~6.76 g PLA for all six), the solve iterates on rendered STL volumes (m(s) = m_housings + m_body·s³), so the converged mass includes joints, cores, skirts, housings, and boolean overlaps. All nine converged to 30.90–30.97 g.

Max envelope volume (Route B): envelope = π·R_print²·H_print ≤ 250 cm³ (the bo_evaluator.cell_geometry_metrics definition). The uniform scale is consumed by the mass constraint, so a shape whose envelope still exceeds V* at m* is infeasible under both constraints simultaneously — no scale can fix it. Three of the nine first-batch shapes are in that category and are flagged envelope_ok=False (kept on the plate rather than silently dropped — printing them still yields valid infeasibility observations for the BO model; excluding them is your call).

Per-specimen results

spec Sobol R/H/twist/strut/cable scale as-print R/H/strut/cable (mm) mass (PLA+TPU) envelope flags
0 32.1 / 89.6 / 59.8° / 7.88 / 5.39 0.850 27.3 / 76.2 / 6.70 / 4.58 30.93 g (20.0+10.9) 178 cm³ ok
1 33.8 / 80.1 / 77.4° / 10.87 / 3.00 0.850 28.7 / 68.1 / 9.24 / 2.55 30.97 g (27.3+3.6) 177 cm³ cable < 3 mm¹
2 39.0 / 100.0 / 47.7° / 7.07 / 3.92 0.935 36.4 / 93.5 / 6.61 / 3.67 30.93 g (21.7+9.2) 390 cm³ envelope violation
3 25.1 / 72.1 / 65.1° / 10.18 / 4.66 0.864 21.7 / 62.3 / 8.79 / 4.03 30.90 g (24.0+6.9) 92 cm³ ok
4 27.6 / 104.1 / 70.4° / 9.28 / 4.49 0.823 22.7 / 85.7 / 7.64 / 3.70 30.93 g (24.0+6.9) 139 cm³ ok
5 36.3 / 63.2 / 53.0° / 6.46 / 4.06 1.044 37.9 / 66.0 / 6.74 / 4.23 30.95 g (19.8+11.1) 298 cm³ envelope violation
6 36.0 / 96.4 / 62.1° / 11.66 / 3.49 0.775 27.9 / 74.7 / 9.04 / 2.71 30.93 g (26.9+4.0) 182 cm³ cable < 3 mm¹
7 30.1 / 74.8 / 44.5° / 8.58 / 4.94 0.889 26.8 / 66.5 / 7.63 / 4.39 30.91 g (21.3+9.6) 150 cm³ ok
8 29.0 / 100.9 / 63.8° / 6.20 / 3.20 1.040 30.2 / 104.9 / 6.45 / 3.32 30.95 g (23.5+7.5) 300 cm³ envelope violation

¹ As-printed cable Ø falls below the 3.0 mm TPU self-bridging floor after mass projection — fine under the manual-painted-supports workflow (the floor only matters for unsupported bridging), just flagged cable_bridge_ok=False in the CSV.

Masses are solid-volume estimates (PLA 1.24 / TPU 1.21 g/cm³) — weighing a couple of prints would calibrate this (the still-open batch01.csv metadata ask); --mass-g accepts a measured target. If the 250 cm³ cap isn't the V* you had in mind, it's --envelope-max-cm3 on the CLI.

Previews (variable-width 3×3 grid; +X strip reserved for the prime tower)

plate

iso

Every specimen carries the three igloo top mounts + three beside-mounted bottom key-seats, seats on the bed at z=0, keeps sub-mm struts/cables z-parity, and stays inside the 290×310 mm usable area.

Files (at cf39fe0)

(Job note: the run's GitHub token expired mid-render — ~45 min of OpenSCAD solves — so the push/comment used a refreshed app token; everything above is committed and verified on the branch.)

View job run

@sgbaird

sgbaird commented Jul 30, 2026

Copy link
Copy Markdown
Collaborator

Noting that we can instruct claude to upload to onshape and provide the links back to us so we can easily analyze and spot check the structures.

…ass / max-envelope constraints

Per PR #35 comment 5132975378: the 9 pinned first-batch Sobol designs are
re-rendered directly from the canonical cad/t3-prism/t3-prism.scad via -D
overrides (captive-core joints + A3 igloo top mounts + beside-mounted flat
bottom key-seats always in sync), each projected onto the constant-mass
manifold (m* = 30.95 g, the solid-volume mass of the committed S0 reference
STLs = most recent instrumented prints) via a rendered-volume cube-root
solve, and checked against the Route-B envelope cap pi*R^2*H <= 250 cm^3
(sim_bo_hybrid_campaign.py). Specs 02/05/08 exceed the cap at m* and are
flagged envelope_ok=False. Variable-width 3x3 plate grid keeps the pack
inside the prime-tower-reduced usable area. MM .3mf re-assembled: 9 objects
x (PLA struts ext1 + TPU cables ext2), filament_map_mode=Manual.

Co-authored-by: Sterling G. Baird <45469701+sgbaird@users.noreply.github.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@achris0520

Copy link
Copy Markdown
Collaborator

@claude if you got stuck here (#35 (comment)), please finish where you left off. If you are not finished after 20min, please state so.

@claude

claude Bot commented Aug 4, 2026

Copy link
Copy Markdown

Claude finished @achris0520's task in 8m 40s —— View job


Finished — nothing was actually left undone in cf39fe0; the missing piece was the Onshape upload

  • Audited cf39fe0 (the commit from 5132983514) — despite the token expiring mid-run, everything it claimed is on the branch and consistent. No geometry work needed redoing.
  • Identified the genuinely-unfinished item: the Onshape upload + spot-check links @sgbaird asked for immediately after in 5133453991 — that never ran
  • Uploaded all 9 specimens (18 STLs) to a public Onshape document
  • Found + fixed a real bug in the uploader while verifying scale
  • Committed + pushed (32addaf)

1. cf39fe0 audit — all green

Check Result
Per-specimen STLs 18/18 regenerated in that commit
MM project .3mf 9 objects × 2 parts = 18 parts, 9 plate instances ✔
Filament routing filament_type=['PLA','TPU'], filament_map=['1','2'], filament_map_mode=Manual
Supports enable_support=0 (manual painting, as intended) ✔
Constant mass all 9 at 30.90–30.97 g vs m* = 30.95 g, mass_ok=True ×9 ✔
Envelope cap specs 02 / 05 / 08 envelope_ok=False, as reported ✔

2. Onshape — 9 specimens, PLA + TPU part studios each

Document: https://cad.onshape.com/documents/8439090bebf9d3c9f54f2185/w/bb7f2cf3dbf5dc3f824916a6 (public, "T3-prism Sobol batch 01 - constant mass (PR #35)")

spec R/H/twist (as-print) mass envelope PLA struts TPU cables struts bbox (mm) flags
0 27.3 / 76.2 / 60° 30.93 g 178.3 cm³ struts cables 77.24 × 74.09 × 97.74
1 28.7 / 68.1 / 77° 30.97 g 176.5 cm³ struts cables 78.29 × 75.10 × 88.33 cable < 3 mm
2 36.4 / 93.5 / 48° 30.93 g 390.0 cm³ struts cables 92.51 × 91.16 × 114.44 envelope > 250 cm³
3 21.7 / 62.3 / 65° 30.90 g 92.1 cm³ struts cables 67.11 × 62.30 × 83.33
4 22.7 / 85.7 / 70° 30.93 g 138.9 cm³ struts cables 68.46 × 63.88 × 106.28
5 37.9 / 66.0 / 53° 30.95 g 297.5 cm³ struts cables 95.87 × 95.32 × 87.92 envelope > 250 cm³
6 27.9 / 74.7 / 62° 30.93 g 182.4 cm³ struts cables 76.41 × 73.54 × 94.62 cable < 3 mm
7 26.8 / 66.5 / 44° 30.91 g 149.8 cm³ struts cables 76.27 × 72.20 × 88.05
8 30.2 / 104.9 / 64° 30.95 g 299.9 cm³ struts cables 82.48 × 80.07 × 126.75 envelope > 250 cm³

Each specimen's struts and cables studios agree in Z to within ~0.3 mm (e.g. spec 05: 87.92 vs 87.94), confirming the world-Z parity that keeps Bambu Studio from dropping the TPU relative to the PLA on import.

3. Bug found while verifying scale (32addaf)

The uploader's bounding-box readback multiplied by 1000 on the assumption that Onshape reports metres. /partstudios/.../boundingboxes actually returns millimetres, so every past scale check printed a 1000×-oversized number. Cross-checked spec 05 struts against the local STL extents — Onshape 95.87 × 95.32 × 87.92 vs local 95.87 × 95.32 × 87.92, exact match. Also added --stl NAME=PATH / --doc-name / --jobs to cad/t3-prism/onshape_upload_t3prism.py so any STL set can be pushed without editing the file, and documented the recipe in bo/README.md.

Print files (unchanged, from cf39fe0)

Two minor leftovers, both harmless: a throwaway unittest-millimeter part studio in the Onshape doc that the API key lacks delete permission for (someone with edit rights can remove it in the browser), and the batch is still a full 9-up plate — per 4938386087 you may want batch size 1 for now, in which case just delete the other eight objects after import.
· branch copilot/get-bambu-sliced-print-t3-prism

… readback

Adds --stl NAME=PATH / --doc-name / --jobs so any STL set (e.g. the nine
per-specimen Sobol batch pairs) can be pushed to its own public Onshape
document without editing the script, and drops the bogus *1000 in the
bounding-box readback: /partstudios/.../boundingboxes already reports
millimetres, so every import previously looked 1000x oversized (verified
against local STL extents: spec05 struts 95.87 x 95.32 x 87.92 mm).

Per PR #35 comment 5133453991 (upload the regenerated first Sobol batch to
Onshape for spot-checking).

Co-authored-by: Audrey Christiansen <280533809+achris0520@users.noreply.github.com>
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@me-madsen

Copy link
Copy Markdown
Collaborator

@claude, this is not direction for what you should do in the future, this is a hypothetical question for you to simply answer: if we ever were to need to manually edit the files you generate, then, to my knowledge, it would be significantly easier to do this if the files you provided were .step files instead of .stl or .3mf files (again, this isn't direction for you to change the file type that you give us, just a hypothetical). Would it be possible for you to provide .step files of the same geometries that you've been generating, and to upload those to onshape if needed? Do not provide these files now, just answer the inquiry.

@claude

claude Bot commented Aug 4, 2026

Copy link
Copy Markdown

Claude finished @me-madsen's task in 1m 52s —— View job


Hypothetical: could you ship .step instead of .stl/.3mf?

  • Read the trigger comment (hypothetical — no files produced)
  • Check the current geometry toolchain (OpenSCAD kernel, Onshape uploader)
  • Answer

Short answer: yes, but not from the current toolchain — it would require swapping the geometry kernel, and there's a trap where you get a .step file that's technically valid and practically useless.


Why the current pipeline can't do it

Everything I generate comes out of OpenSCAD (cad/t3-prism/t3-prism.scad). OpenSCAD is a mesh kernel (CGAL/Manifold) — internally there is no such thing as "a sphere" or "a cylinder," only triangles. $fn = 48 on line 59 is exactly that: my "spheres" are 48-sided polyhedra. There is no B-rep to write out, so OpenSCAD has no STEP exporter and structurally can't have one. Same for the .3mf/.stl artifacts downstream — all tessellated.

Three ways to actually get STEP, in increasing order of effort and usefulness

A. Tessellated STEP (mesh → B-rep conversion, e.g. FreeCAD makeShapeFromMesh). ~an hour of work, and I'd advise against it. t3-prism-struts.stl is 49,846 facets — you'd get a STEP with ~50k planar triangular faces. It opens in Onshape/SolidWorks, it's a solid, and it is worse to edit than the STL: no cylindrical face to grab, no sphere to change the radius of, no edge to fillet. This is the trap — it satisfies "give me a STEP" while satisfying none of the reason you asked.

B. Port the model to an OCCT-backed parametric kernel (CadQuery or build123d, both Python). This is the real answer, ~1–2 days. export_step() then emits true analytic geometry: a sphere is a spherical face with a radius you can type a new number into, a strut is a cylindrical face, fillets are real fillets. Feasibility on our specific model is good — the SCAD uses only 36 sphere, 8 cylinder, 7 cube, and the booleans, all of which map 1:1 onto OCCT and come out better than the mesh version. The one genuinely awkward spot is the 10 hull() calls (the teardrop joint blend, the accel-mount skirt, the scaffold pillars) — OCCT has no convex-hull operation, so those would need re-expressing as lofts or revolved tangent profiles. Doable, and arguably cleaner geometry than the hulls, but it's the part that makes this a port rather than a translation.

C. Drive Onshape directly via FeatureScript / the API so you get a live feature tree (sketches, extrudes, parameters) rather than an imported dumb solid. Heaviest by a wide margin. Worth mentioning only because it's the one option that gives you rollback and named dimensions — a STEP import, no matter how clean, arrives in any CAD package with no history, so you'd be direct-editing (move face / offset face / delete face / fillet). Much better than mesh, still not the same as parametric.

Uploading STEP to Onshape

Essentially free — the plumbing already exists. cad/t3-prism/onshape_upload_t3prism.py uploads via /api/v6/blobelements/... with translate=true and polls /api/v6/translations/{id}. That same endpoint accepts .step/.stp with no code change beyond the filename list — and it imports as a solid Part Studio part rather than a mesh part, which is the good outcome. The existing mm bounding-box readback check would keep working as-is.

Three caveats worth having on record

  1. STEP can't replace the .3mf. The .3mf files aren't geometry containers — they carry the plate layout, per-part extruder routing (PLA→ext 1, TPU→ext 2), filament profiles, and support settings. STEP is geometry only. It would be an additional artifact next to the STL/3MF, not a substitute.
  2. The genuinely editable source today is the .scad, not the mesh — 780 lines, fully parametric, diffable in git. For a change like "make the accel pocket 0.2 mm deeper," editing one parameter and re-rendering is strictly easier than hand-editing a STEP. STEP wins for the different case: someone wants to nudge a face in Onshape/SolidWorks without touching code.
  3. Round-tripping is the thing to decide up front. If anyone hand-edits a STEP, the SCAD immediately goes stale and my next regeneration silently overwrites their change. Whichever way you'd go, we'd need to pick one source of truth.

If you ever do pull the trigger: route B (build123d) plus the existing Onshape uploader, emitting .step alongside the current STLs. That keeps generation parametric on my side while giving you real B-rep on yours. Not doing anything now, per your note.
· branch copilot/get-bambu-sliced-print-t3-prism

@achris0520

Copy link
Copy Markdown
Collaborator

@claude Feedback on: #35 (comment). This was excellent. The .3mf file worked great.

@claude

claude Bot commented Aug 4, 2026

Copy link
Copy Markdown

Claude finished @achris0520's task in 46s —— View job


Thanks for the confirmation, @achris0520 🎉

Good to hear the batch .3mf imported and printed cleanly — that closes the loop on the format that took the longest to get right, so recording what "working" means here for future reference:

The .3mf recipe that works (produced by bo/t3_prism_sobol_batch.py):

  • Render per-specimen STL pairs (bo/per-specimen-stls/t3-prism-bo-specNN-{struts,cables}.stl) rather than one combined mesh, pass all 2N to the BambuStudio CLI --assemble, then split the composite into N objects × 2 parts. That's what makes each specimen movable as a unit while its PLA + TPU parts stay together.
  • patch_mm_extruder.py pads filament_colour / filament_map / filament_nozzle_map to match filament_settings_id length and sets filament_map_mode=Manual — without this Bambu Studio silently imports it as single-material PLA.
  • Struts and cables STLs are given matching world-Z bounding boxes (captive core spheres + the cables_z_anchor() spike), which is what stops Bambu's per-part auto-bed-placement from dropping the TPU ~3 mm relative to the PLA.
  • enable_support=0 — supports stay manual-painted per your bottom-view brush workflow.

Two leftovers from that run, both cosmetic:

  • A throwaway unittest-millimeter part studio in the Onshape doc that the API key can't delete — anyone with edit rights can remove it in the browser.
  • The plate is still a full 9-up; per 4938386087 you may want batch size 1 for now — just delete the other eight objects after import, or say the word and I'll regenerate with --n 1.

What would be most useful next, whenever you're ready:

  1. UUID ↔ specimen index mapping for whatever gets printed, against bo/t3-prism-bo-batch.csv — without it the drop-test outcomes can't be attached to (R, H, twist, strut_d, cable_d).
  2. Print notes per specimen (mass, time, defects, usable y/n). Failures and pulled-from-plate specimens are worth logging too — those are valid infeasible observations for the GP.
  3. Whether the A3 accel housing (6.2 × 6.2 × 6.8 mm pocket, a553b57) fits the Dytran with wax in practice — that's the one dimension I still can't verify without a physical part.

Also still open from @sgbaird's 07-01 comment: flat (non-igloo) key-seats below the lower vertices landed in be51d5e / 75fac28, so if the printed bottom seats look wrong on a real part, a photo would help me correct them.

No code changes made in this run — this was acknowledgement only.
· branch copilot/get-bambu-sliced-print-t3-prism

@sgbaird

sgbaird commented Aug 21, 2026

Copy link
Copy Markdown
Collaborator

@claude we need a new 3mf (or is it multiple? not sure, just whatever Audrey needs) for the newly suggested batch shown in #102 (comment)

Also do whatever onshape uploading you were doing before

@claude

claude Bot commented Aug 21, 2026

Copy link
Copy Markdown

Claude finished @sgbaird's task in 42m 20s —— View job


Round-1 BO batch: one H2D multi-material .3mf + Onshape upload

Audrey needs one file: bo/slices/t3-prism-bo-round1.H2D-MM-PLAstruts-TPUcables.3mf (4.3 MB). Drag it into Bambu Studio, paint supports, Slice plate. All 9 specimens are on one plate, each as its own movable object with a PLA part and a TPU part already assigned.

  • Read PR Add T-3_01 Sobol batch print key (ID-to-spec mapping + as-printed .3mf) #102 comment 5365706779, pull the round-1 suggestion table (Ax trials 10 to 18)
  • Teach bo/t3_prism_sobol_batch.py to take an arbitrary design table (--designs-csv) and its own artifact prefix (--out-prefix)
  • Render the 9 specimens, pack the 3x3 plate, assemble the MM project
  • Onshape upload: 18 per-specimen STLs, bounding boxes read back in mm
  • Update bo/README.md, commit + push (76e88bf)

The batch

These are the model-based suggestions from the mass-aware campaign, not a fresh Sobol draw. The generator previously only knew how to replay the pinned first-batch CSV, so I added --designs-csv (reads the same five swept columns out of any design table, including t3-prism-bo-suggestions-roundN.csv straight from the campaign script) and --out-prefix (so a round's artifacts land beside the Sobol batch instead of overwriting it). Each row's Ax trial_index is carried into the batch table as source_trial, so plate position maps back to trial without guessing.

python3 bo/t3_prism_sobol_batch.py \
    --designs-csv bo/t3-prism-bo-suggestions-round1.csv \
    --out-prefix t3-prism-bo-round1

Everything else is unchanged from the last batch: constant-mass projection onto m* = 30.95 g, 250 cm³ envelope cap, captive-core joints, A3 igloo top mounts and flat bottom key-seats, supports off for manual painting.

plate trial R (mm) H (mm) twist strut Ø cable Ø scale as-printed cable Ø mass (g) PLA / TPU (g) envelope (cm³)
00 10 25.0 60.0 80° 12.0 3.0 0.878 2.63 30.99 27.9 / 3.1 79.7
01 11 40.0 60.0 80° 12.0 5.5 0.753 4.14 30.91 23.0 / 7.9 128.8
02 12 25.0 60.0 40° 12.0 3.0 0.899 2.70 31.01 27.6 / 3.4 85.5
03 13 25.0 60.0 80° 7.40 3.0 1.092 3.28 30.95 25.0 / 6.0 153.4
04 14 25.0 60.0 40° 12.0 5.5 0.816 4.49 30.88 23.2 / 7.6 64.0
05 15 40.0 60.0 40° 12.0 3.0 0.872 2.62 31.00 26.8 / 4.2 200.1
06 16 25.0 60.0 80° 12.0 5.5 0.803 4.42 30.88 23.8 / 7.1 61.0
07 17 40.0 110.0 80° 12.0 5.5 0.673 3.70 30.94 23.9 / 7.0 168.7
08 18 25.0 60.0 80° 6.00 5.5 1.002 5.51 30.85 17.6 / 13.3 118.6

All nine hold the mass target within tolerance and clear the envelope cap. Three need extra care when painting supports: specimens 00, 02 and 05 (trials 10, 12, 15) land at 2.6 to 2.7 mm as-printed cable diameter, below the 3.0 mm TPU self-bridging floor, so they are flagged cable_bridge_ok=False in the design table. That is the direct consequence of holding mass constant on a 12 mm-strut / 3 mm-cable design: the constant-mass scale factor shrinks the cables along with everything else. Those three have the thinnest top-triangle cables on the plate.

Top-down plate (the empty strip on +X is the 50 mm prime/flush-tower reserve):

Verified inside the .3mf: 9 <object> entries, 18 <part> entries (struts to extruder 1, cables to extruder 2), 9 plate instances, filament_settings_id=['Bambu PLA Basic @BBL H2D','Bambu TPU 85A @BBL H2D 0.4 nozzle'], filament_type=['PLA','TPU'], filament_map=['1','2'], filament_nozzle_map=['1','2'], filament_map_mode=Manual, enable_support=0. Grid is 3x3 with variable column widths (97.1 / 81.1 / 71.2 mm) and row heights (97.1 / 88.2 / 84.1 mm), total 261 x 281 mm inside the tower-reduced usable area.

Other files

File What
bo/t3-prism-bo-round1.csv design table with source_trial, as-printed dims, mass audit, constraint flags
bo/t3-prism-bo-round1-struts.stl all 9 PLA parts, plate-positioned (extruder 1)
bo/t3-prism-bo-round1-cables.stl all 9 TPU parts, plate-positioned (extruder 2)
bo/per-specimen-stls/ t3-prism-bo-round1-specNN-{struts,cables}.stl, one pair per specimen
bo/t3-prism-bo-suggestions-round1.csv the source suggestion table, copied verbatim from PR #102

If you want the specimens as separate files instead of one project, use the per-specimen pairs and import them two at a time (the combined t3-prism-bo-round1.stl fuses PLA and TPU into one mesh and cannot be split by material after import).

Onshape

All 18 per-specimen STLs are imported into a public document for browser-side measurement, each bounding box read back through the API in mm as a scale check (no unit mix-up: every part landed at the expected tens-of-mm size, not metres or 1000x):

Document: https://cad.onshape.com/documents/09b2b586cfe785215ff2b1fa/w/4ad66babf9d15db6bdde321c

Specimen PLA struts TPU cables
00 66.80 x 61.84 x 73.70 mm 46.75 x 48.70 x 72.93 mm
01 81.48 x 78.00 x 66.02 mm 62.88 x 65.56 x 66.04 mm
02 67.88 x 62.95 x 75.17 mm 47.85 x 49.85 x 74.38 mm
03 77.97 x 73.32 x 87.94 mm 58.16 x 60.58 x 87.96 mm
04 65.11 x 59.41 x 70.33 mm 45.22 x 47.04 x 70.35 mm
05 89.16 x 86.91 x 73.30 mm 70.66 x 73.76 x 72.53 mm
06 64.45 x 58.72 x 69.44 mm 44.55 x 46.33 x 69.46 mm
07 75.34 x 71.45 x 94.19 mm 56.52 x 58.92 x 94.20 mm
08 74.58 x 69.51 x 83.14 mm 54.87 x 57.10 x 83.16 mm

Struts and cables agree in Z to under a millimetre on every specimen, which is the check that the two parts will not be dropped to different bed heights by Bambu's per-part auto-placement.

One thing I did not do

I did not slice the project headless. The BambuStudio v02.06.00.51 CLI still refuses to honour per-part extruder assignment when re-loading an assembled multi-object project (filament TPU can not be printed on extruder <garbage id>), the limitation documented in render_print.sh slice_bambu_mm. The GUI handles it correctly, so the .3mf is built and verified at the project level but the actual slice still happens on Audrey's machine.

--- • • Branch copilot/get-bambu-sliced-print-t3-prism

…ions

Generate the first model-based batch (PR #102 comment 5365706779, Ax trials
10-18) as a printable H2D IDEX project. bo/t3_prism_sobol_batch.py grows
--designs-csv (read the five swept columns from any design table, e.g. a
t3-prism-bo-suggestions-roundN.csv emitted by the campaign script) and
--out-prefix (so a round lands beside the pinned Sobol batch instead of
overwriting it). Each row's Ax trial_index is carried into the batch table
as source_trial.

Artifacts: bo/t3-prism-bo-round1.{csv,json,scad,stl}, -struts/-cables STLs,
plate/iso previews, 9 per-specimen STL pairs, and
bo/slices/t3-prism-bo-round1.H2D-MM-PLAstruts-TPUcables.3mf (9 objects, each
with a PLA struts part on extruder 1 and a TPU cables part on extruder 2,
filament_map_mode=Manual, supports off for manual painting).

All 9 hold m* = 30.95 g within tolerance and clear the 250 cm^3 envelope cap;
specimens 00/02/05 (trials 10/12/15) drop to 2.6-2.7 mm as-printed cable
diameter and are flagged cable_bridge_ok=False.

Co-authored-by: Sterling G. Baird <45469701+sgbaird@users.noreply.github.com>
@achris0520

achris0520 commented Aug 21, 2026

Copy link
Copy Markdown
Collaborator

Here is the file for the next round of prints with manual supports and printing presets input:
t3-prism-bo-round1.H2D-MM-PLAstruts-TPUcables_manual-supports.zip

@sgbaird

sgbaird commented Aug 21, 2026

Copy link
Copy Markdown
Collaborator

@claude grab file from #35 (comment) and commit it. Show a visualization of the sliced version of it for provenance

@claude

claude Bot commented Aug 21, 2026

Copy link
Copy Markdown

Claude finished @sgbaird's task in 6m 9s —— View job


Committed @achris0520's manual-support round-1 project + sliced provenance renders

What's in the file

It is the generated round-1 project with supports painted by hand on all nine specimens and print presets applied (Bambu Studio 02.04.00.70), not a regenerated artifact:

Setting Value
Printer / process Bambu Lab H2D 0.6 nozzle, 0.30mm Standard @BBL H2D 0.6 nozzle
Filaments Bambu PLA Basic @BBL H2D 0.6 nozzle (ext 1, struts) + Bambu TPU 85A (ext 2, cables)
Filament map Manual, ['1','2'], filament_nozzle_map=['1','2']
Supports tree(manual) (painted), support_filament=1 (PLA), build-plate only
Prime tower on, 60 mm
Infill / walls / bed 15% sparse, 2 walls, Textured PEI Plate

Painted coverage is stored as paint_supports triangle attributes: 16,628 painted facets across the nine 3D/Objects/object_*.model parts (1,236 to 2,790 per specimen). Nine objects, each with a struts part on extruder 1 and a cables part on extruder 2.

Sliced provenance

BambuStudio CLI v02.06.00.51, headless, on the committed file: 13 h 58 m, 255.45 g PLA + 66.94 g TPU, 0.30 mm layers. Feature-tagged extrusion moves from Metadata/plate_1.gcode: 198,567 support + 63,545 support-interface out of 883,256 total, i.e. the painted supports do materialize as toolpaths.

Iso view (gray = model, red = support, orange = support interface). The nine specimens and the prime tower at back-left are all visible, with the painted scaffolding running under the members:

Top-down, showing the 3x3 plate layout and the prime tower clear of the grid on -X:

Bambu Studio's own plate thumbnail carried inside the project file, for cross-reference:

Caveat on the headless slice

The CLI run ends with return_code=-102 ("Found G-code in unprintable area of multi-extruder printers"), preceded by could not found extruder_type Direct Drive, nozzle_volume_type Standard, filament_index 2 and bogus T1001 / T65535 tool changes. That is the same headless IDEX extruder-mapping limitation already documented in cad/t3-prism/render_print.sh slice_bambu_mm, not something wrong with Audrey's file. It still writes complete toolpaths, which is what the renders above are drawn from, but the printable job has to come out of the GUI. Because of that I did not commit a .gcode.3mf, only the project and the renders.

Also touched cad/t3-prism/render_supports.py: two optional env knobs, RS_MODEL_MAX (model-segment cap, default unchanged at 40,000; a nine-specimen plate reads as haze at the default) and RS_VIEW (elev,azim), plus a Z box aspect scaled to part height instead of a forced cube, which on a 350 mm plate spent most of the frame on empty air. Defaults reproduce the previous single-prism renders.
· branch copilot/get-bambu-sliced-print-t3-prism

claude Bot and others added 2 commits August 21, 2026 20:12
Uploaded by @achris0520 in PR #35 comment 5374553137: the round-1 BO batch
prepared in Bambu Studio v02.04.00.70 with supports painted by hand on all
nine specimens (tree(manual), support_filament=1 / PLA, build-plate-only),
H2D 0.6 nozzle, 0.30mm Standard process, PLA struts (ext 1) + TPU 85A
cables (ext 2), filament_map_mode=Manual.

Co-authored-by: Sterling G. Baird <45469701+sgbaird@users.noreply.github.com>
Slice the committed project headlessly (BambuStudio CLI v02.06.00.51) and
render the resulting plate_1.gcode with render_supports.py: 13 h 58 m,
255.45 g PLA + 66.94 g TPU, 198567 support + 63545 support-interface
extrusion moves of 883256 total.

render_supports.py gains two optional env knobs, RS_MODEL_MAX (model
segment cap, default unchanged at 40000) and RS_VIEW (elev,azim), and now
scales the Z box aspect to the part height instead of forcing a cube, which
on a full 350 mm plate spent most of the frame on empty air.

Co-authored-by: Sterling G. Baird <45469701+sgbaird@users.noreply.github.com>
@sgbaird

sgbaird commented Aug 21, 2026

Copy link
Copy Markdown
Collaborator

That is the same headless IDEX extruder-mapping limitation already documented in cad/t3-prism/render_print.sh slice_bambu_mm, not something wrong with Audrey's file. It still writes complete toolpaths, which is what the renders above are drawn from, but the printable job has to come out of the GUI. Because of that I did not commit a .gcode.3mf, only the project and the renders.

Noting I thought we had resolved this somewhere already, perhaps even on the actual bambu lab github (or at least a fork of it).

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Get a bambu sliced print for a T3-prism

8 participants