fix(specctra-core): Fix boundary parsing

see also https://gitlab.com/kicad/code/kicad/-/blob/master/pcbnew/specctra_import_export/specctra.h, class BOUNDARY
This commit is contained in:
Ellen Emilia Anna Zscheile 2025-06-07 09:57:10 +02:00
parent 3c807b5078
commit 33eb593fe9
1 changed files with 49 additions and 6 deletions

View File

@ -3,13 +3,12 @@
// SPDX-License-Identifier: MIT // SPDX-License-Identifier: MIT
use super::read::{ListTokenizer, ReadDsn}; use super::read::{ListTokenizer, ReadDsn};
use super::write::ListWriter; use super::write::{ListWriter, WriteSes};
use super::write::WriteSes;
use crate::error::{ParseError, ParseErrorContext}; use crate::error::{ParseError, ParseErrorContext};
use crate::math::PointWithRotation; use crate::math::PointWithRotation;
use crate::ListToken; use crate::ListToken;
use specctra_derive::ReadDsn; use specctra_derive::{ReadDsn, WriteSes};
use specctra_derive::WriteSes; use std::borrow::Cow;
#[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)] #[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)]
pub struct Dummy {} pub struct Dummy {}
@ -89,6 +88,7 @@ pub struct Structure {
#[vec("layer")] #[vec("layer")]
pub layers: Vec<Layer>, pub layers: Vec<Layer>,
pub boundary: Boundary, pub boundary: Boundary,
pub place_boundary: Option<Boundary>,
#[vec("plane")] #[vec("plane")]
pub planes: Vec<Plane>, pub planes: Vec<Plane>,
#[vec("keepout")] #[vec("keepout")]
@ -109,6 +109,7 @@ impl<R: std::io::BufRead> ReadDsn<R> for Structure {
let mut value = Self { let mut value = Self {
layers: tokenizer.read_named_array(&["layer"])?, layers: tokenizer.read_named_array(&["layer"])?,
boundary: tokenizer.read_named(&["boundary"])?, boundary: tokenizer.read_named(&["boundary"])?,
place_boundary: tokenizer.read_optional(&["place_boundary"])?,
planes: tokenizer.read_named_array(&["plane"])?, planes: tokenizer.read_named_array(&["plane"])?,
keepouts: tokenizer.read_named_array(&["keepout"])?, keepouts: tokenizer.read_named_array(&["keepout"])?,
via: tokenizer.read_named(&["via"])?, via: tokenizer.read_named(&["via"])?,
@ -138,8 +139,27 @@ pub struct Property {
} }
#[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)] #[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)]
pub struct Boundary { pub enum Boundary {
pub path: Path, Path(Path),
Rect(Rect),
}
impl Boundary {
/// * For the `.structure.boundary`, it is expected that `.layer() == "pcb"`;
/// * Another special value which could be encountered is `"signal"`, for the boundary of the area available for routing.
pub fn layer(&self) -> &str {
match self {
Self::Path(x) => &x.layer,
Self::Rect(x) => &x.layer,
}
}
pub fn coords(&self) -> Cow<'_, [Point]> {
match self {
Self::Path(x) => Cow::Borrowed(&x.coords[..]),
Self::Rect(x) => Cow::Owned(x.coords()),
}
}
} }
#[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)] #[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)]
@ -466,6 +486,29 @@ pub struct Rect {
pub y2: f64, pub y2: f64,
} }
impl Rect {
fn coords(&self) -> Vec<Point> {
vec![
Point {
x: self.x1,
y: self.y1,
},
Point {
x: self.x2,
y: self.y1,
},
Point {
x: self.x2,
y: self.y2,
},
Point {
x: self.x1,
y: self.y2,
},
]
}
}
#[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)] #[derive(ReadDsn, WriteSes, Debug, Clone, PartialEq)]
pub struct Via { pub struct Via {
#[anon] #[anon]