cross_sections
Compute cross-sectional areas at evenly spaced planes along an axis to detect internal voids, wall-thickness variation, or verify profile.
Instructions
Compute cross-sectional areas at evenly spaced planes along an axis. Returns a list of {position, area} pairs. axis: X, Y, or Z (default Z). num_slices: number of planes (default 10, minimum 2). Useful for detecting internal voids, wall-thickness variation, or verifying that a shape's cross-section profile matches a reference. object_name: named object from show() (default: current shape).
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| object_name | No | ||
| axis | No | Z | |
| num_slices | No |
Output Schema
| Name | Required | Description | Default |
|---|---|---|---|
| result | Yes |
Implementation Reference
- Core implementation of _cross_sections() — computes cross-sectional areas at evenly spaced planes along X/Y/Z axis using OCC BRepAlgoAPI_Section. Returns list of {position, area} pairs.
def _cross_sections(shape, axis: str = "Z", num_slices: int = 10) -> list: from OCP.BRepAlgoAPI import BRepAlgoAPI_Section from OCP.BRepBuilderAPI import BRepBuilderAPI_MakeFace from OCP.BRepGProp import BRepGProp from OCP.GProp import GProp_GProps from OCP.ShapeAnalysis import ShapeAnalysis_FreeBounds from OCP.TopAbs import TopAbs_EDGE from OCP.TopExp import TopExp_Explorer from OCP.TopTools import TopTools_HSequenceOfShape from OCP.TopoDS import TopoDS from OCP.gp import gp_Dir, gp_Pln, gp_Pnt axis = axis.upper() bb = shape.bounding_box() if axis == "X": lo, hi = bb.min.X, bb.max.X pln_dir = gp_Dir(1, 0, 0) make_pnt = lambda pos: gp_Pnt(pos, 0, 0) elif axis == "Y": lo, hi = bb.min.Y, bb.max.Y pln_dir = gp_Dir(0, 1, 0) make_pnt = lambda pos: gp_Pnt(0, pos, 0) else: lo, hi = bb.min.Z, bb.max.Z pln_dir = gp_Dir(0, 0, 1) make_pnt = lambda pos: gp_Pnt(0, 0, pos) span = hi - lo lo_s = lo + span * 0.01 hi_s = hi - span * 0.01 num_slices = max(num_slices, 2) step = (hi_s - lo_s) / (num_slices - 1) results = [] for i in range(num_slices): pos = lo_s + i * step plane = gp_Pln(make_pnt(pos), pln_dir) section = BRepAlgoAPI_Section(shape.wrapped, plane, False) section.Build() edges = TopTools_HSequenceOfShape() exp = TopExp_Explorer(section.Shape(), TopAbs_EDGE) while exp.More(): edges.Append(exp.Current()) exp.Next() wires = TopTools_HSequenceOfShape() ShapeAnalysis_FreeBounds.ConnectEdgesToWires_s(edges, 1e-7, False, wires) total_area = 0.0 for j in range(1, wires.Length() + 1): wire = TopoDS.Wire_s(wires.Value(j)) try: face_maker = BRepBuilderAPI_MakeFace(plane, wire) if face_maker.IsDone(): face = face_maker.Face() props = GProp_GProps() BRepGProp.SurfaceProperties_s(face, props) total_area += abs(props.Mass()) except Exception: pass results.append({"position": round(pos, 4), "area": round(total_area, 4)}) return results - Public cross_sections() entry point — resolves the shape from session and delegates to _cross_sections helper.
import json def cross_sections(session, object_name: str = "", axis: str = "Z", num_slices: int = 10) -> str: from build123d_mcp.tools.measure import _resolve_shape, _cross_sections shape = _resolve_shape(session, object_name) return json.dumps(_cross_sections(shape, axis, num_slices), indent=2) - src/build123d_mcp/server.py:67-71 (registration)MCP tool registration via @mcp.tool() decorator on cross_sections(). This is the server-level tool definition with its description and parameter schema.
@mcp.tool() def cross_sections(object_name: str = "", axis: str = "Z", num_slices: int = 10) -> str: """Compute cross-sectional areas at evenly spaced planes along an axis. Returns a list of {position, area} pairs. axis: X, Y, or Z (default Z). num_slices: number of planes (default 10, minimum 2). Useful for detecting internal voids, wall-thickness variation, or verifying that a shape's cross-section profile matches a reference. object_name: named object from show() (default: current shape).""" return _session.cross_sections(object_name, axis, num_slices) - src/build123d_mcp/worker.py:82-84 (registration)Worker dispatch routing the 'cross_sections' operation to the cross_sections handler.
if op == "cross_sections": from build123d_mcp.tools.cross_sections import cross_sections return cross_sections(session, **args) - src/build123d_mcp/worker.py:276-281 (helper)WorkerSession.cross_sections() proxy method — sends the cross_sections call to the worker subprocess via pipe.
def cross_sections(self, object_name: str = "", axis: str = "Z", num_slices: int = 10) -> str: return self._call( "cross_sections", {"object_name": object_name, "axis": axis, "num_slices": num_slices}, self._SHORT_TIMEOUT, )