forked from 1b-agent/fieldcraft-upstream
Engine: geometry.bodies lists each body's named edges
Each edge with its persistent name and length. A reference to an edge name selects its numbered pieces (`~k`), as a face name selects its `#k` pieces. Part of #230. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UhhZMBTviDQxZvwnyP89fo
This commit is contained in:
1 parent
a11b971dae
commit
ffb71de6e1
5 files changed
+21
-5
No files matched your search
@@ -25,7 +25,7 @@ pub const OPEN: CommandSpec = CommandSpec {
|
||||
pub const BODIES: CommandSpec = CommandSpec {
|
||||
id: "geometry.bodies",
|
||||
label: "Bodies",
|
||||
params: "{} — the open design's bodies: measures and persistent face names (by face index)",
|
||||
params: "{} — the open design's bodies: measures, persistent face names (by face index) and edges (persistent name `<face>|<face>`, `~k` when several separate the same faces, and length)",
|
||||
form: Some(&[]),
|
||||
kind: CommandKind::Model,
|
||||
requires: &[], // No design is an answer too: no bodies.
|
||||
@@ -126,6 +126,7 @@ fn bodies(s: &mut Session, _: &Value) -> Result<Value> {
|
||||
let mut out = Vec::with_capacity(design.bodies.len());
|
||||
for b in &design.bodies {
|
||||
let m = b.measure()?;
|
||||
let edges: Vec<Value> = b.edges()?.iter().map(|e| json!({"name": e.name, "length": e.length()})).collect();
|
||||
out.push(json!({
|
||||
"name": b.name,
|
||||
"volume": m.volume,
|
||||
@@ -133,6 +134,7 @@ fn bodies(s: &mut Session, _: &Value) -> Result<Value> {
|
||||
"centroid": m.centroid,
|
||||
"bbox": [m.bbox_min, m.bbox_max],
|
||||
"faces": b.faces().iter().map(|f| json!({"name": f.name, "exact": f.exact})).collect::<Vec<_>>(),
|
||||
"edges": edges,
|
||||
}));
|
||||
}
|
||||
Ok(Value::Array(out))
|
||||
|
||||
@@ -645,6 +645,10 @@ mod tests {
|
||||
assert!((volume - expect).abs() < 1e-3 * expect, "{volume}");
|
||||
let faces = bodies[0]["faces"].as_array().unwrap();
|
||||
assert_eq!(faces.len(), 8);
|
||||
let edges = bodies[0]["edges"].as_array().unwrap();
|
||||
assert_eq!(edges.len(), 18);
|
||||
// Through the thickness: four box corners, the two hole seams.
|
||||
assert_eq!(edges.iter().filter(|e| (e["length"].as_f64().unwrap() - 10.0).abs() < 1e-6).count(), 6);
|
||||
|
||||
let t = s.execute("geometry.tessellate", &json!({"body": "Body1", "tolerance": 0.05})).unwrap();
|
||||
let per_face: Vec<u64> = t["faces"].as_array().unwrap().iter().map(|f| f["triangles"].as_u64().unwrap()).collect();
|
||||
@@ -662,6 +666,8 @@ mod tests {
|
||||
let wider = s.execute("geometry.bodies", &json!({})).unwrap();
|
||||
assert!(wider[0]["volume"].as_f64().unwrap() > volume);
|
||||
assert_eq!(wider[0]["faces"], bodies[0]["faces"]);
|
||||
let names = |b: &Value| b[0]["edges"].as_array().unwrap().iter().map(|e| e["name"].clone()).collect::<Vec<_>>();
|
||||
assert_eq!(names(&wider), names(&bodies));
|
||||
assert_eq!(s.journal.len(), 2);
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user