use azul_core::{
dom::{Dom, NodeType},
styled_dom::StyledDom,
xml::{
ComponentDataField, ComponentDataModel, ComponentDef, ComponentFieldType, ComponentId,
ComponentLibrary, ComponentMap, ComponentSource, ComponentDefaultValue,
CompileTarget, OptionComponentDefaultValue, RenderDomError,
ResultStringCompileError, ResultStyledDomRenderDomError,
},
};
use azul_css::{css::Css, AzString};
fn data_field(
name: &str,
ft: ComponentFieldType,
default: Option<ComponentDefaultValue>,
description: &str,
) -> ComponentDataField {
let required = default.is_none();
ComponentDataField {
name: AzString::from(name),
field_type: ft,
default_value: match default {
Some(d) => OptionComponentDefaultValue::Some(d),
None => OptionComponentDefaultValue::None,
},
required,
description: AzString::from(description),
}
}
fn img_render_fn(
_def: &ComponentDef,
_data: &ComponentDataModel,
_component_map: &ComponentMap,
) -> ResultStyledDomRenderDomError {
let mut dom = Dom::create_node(NodeType::Div);
let r: Result<StyledDom, RenderDomError> = Ok(StyledDom::create(&mut dom, Css::empty()));
r.into()
}
fn img_compile_fn(
_def: &ComponentDef,
target: &CompileTarget,
_data: &ComponentDataModel,
_indent: usize,
) -> ResultStringCompileError {
let code = match target {
CompileTarget::Rust => "Dom::create_node(NodeType::Div) /* img */",
CompileTarget::C => "AzDom_createDiv() /* img */",
CompileTarget::Cpp => "Dom::div() /* img */",
CompileTarget::Python => "Dom.div() # img",
};
let r: Result<AzString, _> = Ok(AzString::from(code));
r.into()
}
pub fn img_component_def() -> ComponentDef {
ComponentDef {
id: ComponentId::new("printpdf", "img"),
display_name: AzString::from("Image"),
description: AzString::from("HTML <img> element (embeds an image into the PDF)"),
css: AzString::from(""),
source: ComponentSource::Compiled,
data_model: ComponentDataModel {
name: AzString::from("ImgData"),
description: AzString::from("Data model for <img>"),
fields: vec![
data_field(
"src",
ComponentFieldType::String,
None,
"Image source (URL or embedded image id)",
),
data_field(
"alt",
ComponentFieldType::String,
Some(ComponentDefaultValue::String(AzString::from(""))),
"Alternate text",
),
]
.into(),
},
render_fn: img_render_fn,
compile_fn: img_compile_fn,
render_fn_source: None.into(),
compile_fn_source: None.into(),
}
}
fn dynamic_xml_render_fn(
_def: &ComponentDef,
_data: &ComponentDataModel,
_component_map: &ComponentMap,
) -> ResultStyledDomRenderDomError {
let mut dom = Dom::create_node(NodeType::Div);
let r: Result<StyledDom, RenderDomError> = Ok(StyledDom::create(&mut dom, Css::empty()));
r.into()
}
fn dynamic_xml_compile_fn(
_def: &ComponentDef,
target: &CompileTarget,
_data: &ComponentDataModel,
_indent: usize,
) -> ResultStringCompileError {
let code = match target {
CompileTarget::Rust => "Dom::create_node(NodeType::Div) /* component */",
CompileTarget::C => "AzDom_createDiv() /* component */",
CompileTarget::Cpp => "Dom::div() /* component */",
CompileTarget::Python => "Dom.div() # component",
};
let r: Result<AzString, _> = Ok(AzString::from(code));
r.into()
}
pub fn dynamic_xml_component_def() -> ComponentDef {
ComponentDef {
id: ComponentId::new("printpdf", "component"),
display_name: AzString::from("Component"),
description: AzString::from("User-defined reusable XML component (<component name=\"…\" />)"),
css: AzString::from(""),
source: ComponentSource::UserDefined,
data_model: ComponentDataModel {
name: AzString::from("ComponentData"),
description: AzString::from("Data model for a user-defined <component>"),
fields: vec![
data_field(
"name",
ComponentFieldType::String,
None,
"Name of the component, e.g. \"test\" for <component name=\"test\" />",
),
data_field(
"args",
ComponentFieldType::String,
Some(ComponentDefaultValue::String(AzString::from(""))),
"Raw component argument string, e.g. \"a: String\"",
),
]
.into(),
},
render_fn: dynamic_xml_render_fn,
compile_fn: dynamic_xml_compile_fn,
render_fn_source: None.into(),
compile_fn_source: None.into(),
}
}
pub fn printpdf_component_library() -> ComponentLibrary {
ComponentLibrary {
name: AzString::from("printpdf"),
version: AzString::from("1.0.0"),
description: AzString::from("printpdf custom components (img, component)"),
exportable: false,
modifiable: false,
data_models: Vec::new().into(),
enum_models: Vec::new().into(),
components: vec![img_component_def(), dynamic_xml_component_def()].into(),
}
}
pub fn printpdf_default_components() -> ComponentMap {
let mut map = ComponentMap::with_builtin();
let mut libs = std::mem::replace(&mut map.libraries, Vec::new().into()).into_library_owned_vec();
libs.push(printpdf_component_library());
map.libraries = libs.into();
map
}