brep_kernel/io/step_import/
trim_readings.rs1use super::*;
12
13#[derive(Clone, Debug)]
15pub struct StepTrimReadings {
16 pub stated_precisions_mm: Vec<f64>,
19 pub has_structure: bool,
24 pub bodies: Vec<StepBodyTrimReadings>,
25}
26
27#[derive(Clone, Debug)]
28pub struct StepBodyTrimReadings {
29 pub body_ref: usize,
32 pub solid: Result<BrepSolid, String>,
34 pub edges: Vec<StepEdgeReading>,
35 pub faces: Vec<StepFaceReading>,
36}
37
38#[derive(Clone, Debug)]
39pub struct StepEdgeReading {
40 pub edge_id: u64,
42 pub curve_ref: Option<usize>,
44 pub written: Option<(NurbsCurve, [f64; 2])>,
48 pub stages: Vec<String>,
52}
53
54#[derive(Clone, Debug)]
55pub struct StepFaceReading {
56 pub face_id: u64,
58 pub face_ref: usize,
59 pub surface_ref: usize,
61 pub supplied: Vec<StepSuppliedTrim>,
64}
65
66#[derive(Clone, Debug)]
68pub struct StepSuppliedTrim {
69 pub edge_id: u64,
70 pub forward: bool,
71 pub stations: Vec<Vec3>,
74}
75
76const STATIONS: usize = 64;
78
79pub fn import_step_trim_readings(text: &str) -> Result<StepTrimReadings, String> {
81 if !text.contains("ISO-10303-21") {
82 return Err("step_import: not an ISO-10303-21 Part 21 file".into());
83 }
84 let entities = parse_data_section(text)?;
85 let resolver = Resolver::new(&entities, derive_length_scale_mm(&entities));
86 let stated_precisions_mm = stated_precisions_mm(&entities);
87 let has_structure = !structure_edges(&entities, &resolver).is_empty();
88 let mut bodies = Vec::new();
89 for body in flat_step_bodies(&resolver, &entities) {
90 let body_ref = match body {
91 StepBody::SolidBrep(entity_ref) | StepBody::BrepWithVoids(entity_ref) => entity_ref,
92 StepBody::SurfaceModelShell { shell_ref, .. } => shell_ref,
93 };
94 let (solid, capture) = match build_step_body_captured(&resolver, body) {
95 Ok((solid, capture)) => (Ok(solid), capture.unwrap_or_default()),
96 Err(error) => (Err(error), Default::default()),
97 };
98 let mut edges: Vec<StepEdgeReading> = Vec::new();
99 let mut faces: Vec<StepFaceReading> = Vec::new();
100 if let Ok(solid) = &solid {
101 for edge in &solid.edges {
102 let written = capture.written.get(&edge.id);
103 edges.push(StepEdgeReading {
104 edge_id: edge.id,
105 curve_ref: written.and_then(|written| written.curve_ref),
106 written: written.map(|written| (written.curve.clone(), [written.t0, written.t1])),
107 stages: capture.stages.get(&edge.id).cloned().unwrap_or_default(),
108 });
109 }
110 for face in solid.shells.iter().flat_map(|shell| &shell.faces) {
111 let Some(&(_, face_ref, surface_ref)) =
112 capture.faces.iter().find(|(id, _, _)| *id == face.id)
113 else {
114 continue;
115 };
116 let mut supplied = Vec::new();
117 for coedge in face.loops.iter().flat_map(|loop_record| &loop_record.coedges) {
118 let Some(written) = capture.written.get(&coedge.edge_id) else {
119 continue;
120 };
121 let Some(curve_ref) = written.curve_ref else {
122 continue;
123 };
124 let bundle = resolver.supplied_pcurves(curve_ref);
125 let Some(pcurve) = bundle.iter().find(|pcurve| pcurve.basis_ref == surface_ref)
126 else {
127 continue;
128 };
129 let mut stations = Vec::with_capacity(STATIONS + 1);
130 let mut cursor = None;
131 let mut readable = true;
132 for index in 0..=STATIONS {
133 let fraction = index as f64 / STATIONS as f64;
134 let along = if coedge.forward { fraction } else { 1.0 - fraction };
135 let Ok(point) =
136 written.curve.evaluate(written.t0 + (written.t1 - written.t0) * along)
137 else {
138 readable = false;
139 break;
140 };
141 let Ok((uv, on_trim)) = pcurve.snap(point, cursor) else {
142 readable = false;
143 break;
144 };
145 cursor = Some(uv);
146 stations.push(on_trim);
147 }
148 if readable {
149 supplied.push(StepSuppliedTrim {
150 edge_id: coedge.edge_id,
151 forward: coedge.forward,
152 stations,
153 });
154 }
155 }
156 faces.push(StepFaceReading {
157 face_id: face.id,
158 face_ref,
159 surface_ref,
160 supplied,
161 });
162 }
163 }
164 bodies.push(StepBodyTrimReadings {
165 body_ref,
166 solid,
167 edges,
168 faces,
169 });
170 }
171 Ok(StepTrimReadings {
172 stated_precisions_mm,
173 has_structure,
174 bodies,
175 })
176}