#[serde(default)] pub centre: Option<[f64; 2]>,
#[serde(default)] pub flip: bool,
#[serde(default)] pub back: Option<Box <dyn PieceSpec>>,
- #[serde(default="num_traits::identities::One::one")] pub scale: f64,
+ #[serde(default)] pub scale: Option<ScaleDetails>,
#[serde(default)] pub colours: HashMap<String, RecolourData>,
pub desc_template: Option<String>,
pub occulted: Option<OccultationMethod>,
- #[serde(flatten)] pub outline: Box<dyn shapelib::OutlineDefn>,
+ #[serde(flatten)] pub outline: OutlineDetails,
+}
+
+#[derive(Debug,Deserialize,Copy,Clone)]
+#[serde(untagged)]
+pub enum ScaleDetails {
+ Fit(ScaleFitDetails),
+ Scale(f64),
+ Stretch([f64;2]),
+}
+
+#[derive(Debug,Deserialize,Copy,Clone)]
+pub enum ScaleFitDetails { Fit, Cover, Stretch }
+
+#[derive(Debug,Deserialize)]
+#[serde(untagged)]
+pub enum OutlineDetails {
+ Full(FullOutlineDetails), // introduced with mformat=2
+ Shape(Box<dyn shapelib::OutlineDefn>),
+}
+
+#[derive(Debug,Deserialize)]
+pub struct FullOutlineDetails {
+ shape: Box<dyn shapelib::OutlineDefn>,
+ #[serde(default)] size: Vec<f64>,
+ #[serde(default)] scale: Option<f64>,
+}
+
+impl OutlineDetails {
+ // enum_access could perhaps do this but controlling the serde
+ // would become confusing
+ pub fn shape(&self) -> &dyn shapelib::OutlineDefn { match self {
+ OutlineDetails::Full(full) => &*full.shape,
+ OutlineDetails::Shape(shape) => &**shape,
+ }}
+ pub fn size_scale(&self) -> (&[f64], Option<&f64>) { match self {
+ OutlineDetails::Full(full) => (&full.size, full.scale.as_ref()),
+ OutlineDetails::Shape(_) => default(),
+ }}
}
#[derive(Deserialize,Clone,Debug)]
.into_inner()
.unwrap()
} else {
- let s = d.scale;
+ let s = group.d.scale_mf1(group.mformat)?;
[s,s]
};
let centre = d.centre.map(Ok).unwrap_or_else(|| Ok::<_,LLE>({
#[throws(LibraryLoadError)]
fn load_shape(&self, svg_sz: PosC<f64>) -> (FaceTransform, Outline) {
let xform = FaceTransform::from_group_mf1(self)?;
- let outline = self.d.outline.load_mf1(&self, svg_sz)?;
+ let outline = self.d.outline.shape().load_mf1(&self, svg_sz)?;
(xform, outline)
}
}
+impl GroupDetails {
+ #[throws(materials_format::Incompat<LLMI>)]
+ fn scale_mf1(&self, mformat: materials_format::Version) -> f64 {
+ match self.scale {
+ None => 1.,
+ Some(ScaleDetails::Scale(s)) => s,
+ _ => throw!(mformat.incompat(LLMI::Scale)),
+ }
+ }
+}
+
//---------- RectShape ----------
#[derive(Clone,Copy,Debug,Serialize,Deserialize)]
let gdefn = resolve_inherit(INHERIT_DEPTH_LIMIT,
groups, groupname, gdefn)?;
let gdefn: GroupDefn = TV::Table(gdefn.into_owned()).try_into()?;
- let d = GroupDetails {
- size: gdefn.d.size.iter().map(|s| s * gdefn.d.scale).collect(),
- ..gdefn.d
+ let d = if mformat == 1 {
+ let scale = gdefn.d.scale_mf1(mformat)?;
+ GroupDetails {
+ size: gdefn.d.size.iter().map(|s| s * scale).collect(),
+ ..gdefn.d
+ }
+ } else {
+ gdefn.d // v2 isn't going to do this, do this right now
};
let group = Arc::new(GroupData {
groupname: groupname.clone(),