use crate::geometry::DTransformation;
use crate::geometry::geo_traits::Transformable;
use crate::geometry::primitives::{Point, Rect, SPolygon};
use crate::geometry::shape_modification::{
ShapeModifyConfig, ShapeModifyMode, close_narrow_concavities, offset_shape,
shape_modification_valid, simplify_shape,
};
use anyhow::Result;
#[derive(Clone, Debug)]
pub struct OriginalShape {
pub shape: SPolygon,
pub pre_transform: DTransformation,
pub modify_mode: ShapeModifyMode,
pub modify_config: ShapeModifyConfig,
}
impl OriginalShape {
pub fn convert_to_internal(&self) -> Result<SPolygon> {
let mut internal = self.shape.transform_clone(&self.pre_transform.compose());
if let Some(offset) = self.modify_config.offset {
if offset != 0.0 {
internal = offset_shape(&internal, self.modify_mode, offset)?;
}
}
if let Some(tolerance) = self.modify_config.simplify_tolerance {
let pre_simplified = internal.clone();
internal = simplify_shape(&internal, self.modify_mode, tolerance);
if let Some(narrow_concavity_cutoff) = self.modify_config.narrow_concavity_cutoff {
internal =
close_narrow_concavities(&internal, self.modify_mode, narrow_concavity_cutoff);
internal = simplify_shape(&internal, self.modify_mode, tolerance / 10.0);
}
debug_assert!(shape_modification_valid(
&pre_simplified,
&internal,
self.modify_mode
));
}
Ok(internal)
}
pub fn centroid(&self) -> Point {
self.shape.centroid()
}
pub fn area(&self) -> f32 {
self.shape.area
}
pub fn bbox(&self) -> Rect {
self.shape.bbox
}
pub fn diameter(&self) -> f32 {
self.shape.diameter
}
}