mod xml;
#[cfg(test)]
mod tests;
use crate::dml::effect::ShadowFormat;
use crate::dml::effect3d::{Scene3D, Shape3D};
use crate::dml::fill::FillFormat;
use crate::dml::line::LineFormat;
use crate::enums::shapes::PresetGeometry;
use crate::shapes::action::ActionSetting;
use crate::shapes::freeform::FreeformBuilder;
use crate::shapes::placeholder::PlaceholderFormat;
use crate::text::TextFrame;
use crate::units::{Emu, ShapeId};
#[derive(Debug, Clone, PartialEq)]
pub struct AutoShape {
pub shape_id: ShapeId,
pub name: String,
pub left: Emu,
pub top: Emu,
pub width: Emu,
pub height: Emu,
pub rotation: f64,
pub prst_geom: Option<PresetGeometry>,
pub is_textbox: bool,
pub placeholder: Option<PlaceholderFormat>,
pub tx_body_xml: Option<Vec<u8>>,
pub fill: Option<FillFormat>,
pub line: Option<LineFormat>,
pub text_frame: Option<TextFrame>,
pub click_action: Option<ActionSetting>,
pub hover_action: Option<ActionSetting>,
pub adjustments: Vec<f64>,
pub shadow: Option<ShadowFormat>,
pub custom_geometry: Option<FreeformBuilder>,
pub scene_3d: Option<Scene3D>,
pub shape_3d: Option<Shape3D>,
}
impl AutoShape {
pub fn new(
shape_id: ShapeId,
name: impl Into<String>,
left: Emu,
top: Emu,
width: Emu,
height: Emu,
) -> Self {
Self {
shape_id,
name: name.into(),
left,
top,
width,
height,
rotation: 0.0,
prst_geom: None,
is_textbox: false,
placeholder: None,
tx_body_xml: None,
fill: None,
line: None,
text_frame: None,
click_action: None,
hover_action: None,
adjustments: Vec::new(),
shadow: None,
custom_geometry: None,
scene_3d: None,
shape_3d: None,
}
}
pub fn textbox(
shape_id: ShapeId,
name: impl Into<String>,
left: Emu,
top: Emu,
width: Emu,
height: Emu,
) -> Self {
let mut shape = Self::new(shape_id, name, left, top, width, height);
shape.is_textbox = true;
shape.prst_geom = Some(PresetGeometry::Rect);
shape
}
pub fn with_geometry(
shape_id: ShapeId,
name: impl Into<String>,
left: Emu,
top: Emu,
width: Emu,
height: Emu,
prst_geom: PresetGeometry,
) -> Self {
let mut shape = Self::new(shape_id, name, left, top, width, height);
shape.prst_geom = Some(prst_geom);
shape
}
#[must_use]
pub const fn has_text_frame(&self) -> bool {
self.text_frame.is_some() || self.tx_body_xml.is_some()
}
pub fn set_fill(&mut self, fill: FillFormat) {
self.fill = Some(fill);
}
pub fn set_line(&mut self, line: LineFormat) {
self.line = Some(line);
}
#[must_use]
pub const fn text_frame(&self) -> Option<&TextFrame> {
self.text_frame.as_ref()
}
pub fn text_frame_mut(&mut self) -> Option<&mut TextFrame> {
self.text_frame.as_mut()
}
pub fn set_click_action(&mut self, action: ActionSetting) {
self.click_action = Some(action);
}
pub fn set_hover_action(&mut self, action: ActionSetting) {
self.hover_action = Some(action);
}
pub fn set_shadow(&mut self, shadow: ShadowFormat) {
self.shadow = Some(shadow);
}
pub fn set_custom_geometry(&mut self, geom: FreeformBuilder) {
self.custom_geometry = Some(geom);
}
#[must_use]
pub const fn scene_3d(&self) -> Option<&Scene3D> {
self.scene_3d.as_ref()
}
pub fn set_scene_3d(&mut self, scene: Scene3D) {
self.scene_3d = Some(scene);
}
#[must_use]
pub const fn shape_3d(&self) -> Option<&Shape3D> {
self.shape_3d.as_ref()
}
pub fn set_shape_3d(&mut self, shape3d: Shape3D) {
self.shape_3d = Some(shape3d);
}
}
impl std::fmt::Display for AutoShape {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "AutoShape(\"{}\")", self.name)
}
}