svg-filters & basic parser #15
12 changed files with 94 additions and 108 deletions
|
@ -4,7 +4,10 @@ use svg_filters::{
|
||||||
codegen::SvgDocument,
|
codegen::SvgDocument,
|
||||||
types::{
|
types::{
|
||||||
graph::edge::Edge,
|
graph::edge::Edge,
|
||||||
nodes::{primitives::color_matrix::ColorMatrixType, standard_input::StandardInput},
|
nodes::{
|
||||||
|
primitives::{blend::BlendMode, color_matrix::ColorMatrixType},
|
||||||
|
standard_input::StandardInput,
|
||||||
|
},
|
||||||
},
|
},
|
||||||
Node,
|
Node,
|
||||||
};
|
};
|
||||||
|
@ -12,6 +15,12 @@ use svg_filters::{
|
||||||
fn main() {
|
fn main() {
|
||||||
let mut doc = SvgDocument::new();
|
let mut doc = SvgDocument::new();
|
||||||
|
|
||||||
|
let blend = doc.create_filter("blend");
|
||||||
|
|
||||||
|
let offset0 = blend.offset(StandardInput::SourceGraphic, 100., 0.);
|
||||||
|
let offset1 = blend.offset(StandardInput::SourceGraphic, -100., 0.);
|
||||||
|
blend.blend(offset0, offset1, BlendMode::Multiply);
|
||||||
|
|
||||||
eprintln!("{}", doc.generate_svg_pretty());
|
eprintln!("{}", doc.generate_svg_pretty());
|
||||||
println!("{}", doc.generate_svg());
|
println!("{}", doc.generate_svg());
|
||||||
}
|
}
|
||||||
|
|
|
@ -36,7 +36,7 @@ impl Default for Node {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Default, Debug, Clone, Copy)]
|
#[derive(Default, Debug, Clone, Copy)]
|
||||||
pub(crate) struct CommonAttrs {
|
pub struct CommonAttrs {
|
||||||
pub x: Coordinate,
|
pub x: Coordinate,
|
||||||
pub y: Coordinate,
|
pub y: Coordinate,
|
||||||
pub width: Length,
|
pub width: Length,
|
||||||
|
|
|
@ -4,6 +4,23 @@ use quick_xml::{events::attributes::Attribute, ElementWriter, Writer};
|
||||||
|
|
||||||
use super::CommonAttrs;
|
use super::CommonAttrs;
|
||||||
|
|
||||||
|
macro_rules! gen_attr {
|
||||||
|
($name:literal = $out:expr) => {
|
||||||
|
quick_xml::events::attributes::Attribute {
|
||||||
|
key: quick_xml::name::QName($name),
|
||||||
|
value: std::borrow::Cow::from(($out).to_string().into_bytes()),
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
macro_rules! gen_attrs {
|
||||||
|
($($name:literal = $out:expr),+) => {
|
||||||
|
vec![
|
||||||
|
$(gen_attr!($name = $out)),+
|
||||||
|
]
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
pub mod blend;
|
pub mod blend;
|
||||||
pub mod color_matrix;
|
pub mod color_matrix;
|
||||||
pub mod component_transfer;
|
pub mod component_transfer;
|
||||||
|
|
|
@ -29,10 +29,7 @@ impl WriteElement for Blend {
|
||||||
if let BlendMode::Normal = self.mode {
|
if let BlendMode::Normal = self.mode {
|
||||||
Vec::new()
|
Vec::new()
|
||||||
} else {
|
} else {
|
||||||
vec![Attribute {
|
gen_attrs![b"mode" = self.mode]
|
||||||
key: QName(b"mode"),
|
|
||||||
value: Cow::from(self.mode.to_string().into_bytes()),
|
|
||||||
}]
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,3 @@
|
||||||
use std::borrow::Cow;
|
|
||||||
|
|
||||||
use quick_xml::{events::attributes::Attribute, name::QName};
|
|
||||||
|
|
||||||
use super::WriteElement;
|
use super::WriteElement;
|
||||||
|
|
||||||
/// [feColorMatrix](https://www.w3.org/TR/SVG11/filters.html#feColorMatrixElement)
|
/// [feColorMatrix](https://www.w3.org/TR/SVG11/filters.html#feColorMatrixElement)
|
||||||
|
@ -19,24 +15,20 @@ impl ColorMatrix {
|
||||||
impl WriteElement for ColorMatrix {
|
impl WriteElement for ColorMatrix {
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
match &self.cm_type {
|
match &self.cm_type {
|
||||||
ColorMatrixType::Matrix(v) => vec![Attribute {
|
ColorMatrixType::Matrix(v) => gen_attrs![
|
||||||
key: QName(b"values"),
|
b"values" = v
|
||||||
value: Cow::from(
|
.iter()
|
||||||
v.iter()
|
|
||||||
.map(std::string::ToString::to_string)
|
.map(std::string::ToString::to_string)
|
||||||
.reduce(|mut acc, e| {
|
.reduce(|mut acc, e| {
|
||||||
acc.push(' ');
|
acc.push(' ');
|
||||||
acc.push_str(&e);
|
acc.push_str(&e);
|
||||||
acc
|
acc
|
||||||
})
|
})
|
||||||
.expect("Should be able to concatenate the thingies")
|
.expect("fixed length arr should always work")
|
||||||
.into_bytes(),
|
],
|
||||||
),
|
ColorMatrixType::Saturate(v) | ColorMatrixType::HueRotate(v) => {
|
||||||
}],
|
gen_attrs![b"values" = v]
|
||||||
ColorMatrixType::Saturate(v) | ColorMatrixType::HueRotate(v) => vec![Attribute {
|
}
|
||||||
key: QName(b"values"),
|
|
||||||
value: Cow::from(v.to_string().into_bytes()),
|
|
||||||
}],
|
|
||||||
ColorMatrixType::LuminanceToAlpha => Vec::new(),
|
ColorMatrixType::LuminanceToAlpha => Vec::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
use super::WriteElement;
|
||||||
|
|
||||||
/// [feComponentTransfer](https://www.w3.org/TR/SVG11/filters.html#feComponentTransferElement)
|
/// [feComponentTransfer](https://www.w3.org/TR/SVG11/filters.html#feComponentTransferElement)
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct ComponentTransfer {
|
pub struct ComponentTransfer {
|
||||||
|
@ -7,6 +9,16 @@ pub struct ComponentTransfer {
|
||||||
pub func_a: TransferFn,
|
pub func_a: TransferFn,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl WriteElement for ComponentTransfer {
|
||||||
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
|
Vec::new()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn tag_name(&self) -> &'static str {
|
||||||
|
"feComponentTransfer"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// [transfer functions](https://www.w3.org/TR/SVG11/filters.html#transferFuncElements)
|
/// [transfer functions](https://www.w3.org/TR/SVG11/filters.html#transferFuncElements)
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub enum TransferFn {
|
pub enum TransferFn {
|
||||||
|
|
|
@ -51,23 +51,29 @@ impl WriteElement for Composite {
|
||||||
}];
|
}];
|
||||||
|
|
||||||
if let Some([k1, k2, k3, k4]) = vals {
|
if let Some([k1, k2, k3, k4]) = vals {
|
||||||
r.append(&mut vec![
|
// r.append(&mut vec![
|
||||||
Attribute {
|
// Attribute {
|
||||||
key: QName(b"k1"),
|
// key: QName(b"k1"),
|
||||||
value: Cow::from(k1.to_string().into_bytes()),
|
// value: Cow::from(k1.to_string().into_bytes()),
|
||||||
},
|
// },
|
||||||
Attribute {
|
// Attribute {
|
||||||
key: QName(b"k2"),
|
// key: QName(b"k2"),
|
||||||
value: Cow::from(k2.to_string().into_bytes()),
|
// value: Cow::from(k2.to_string().into_bytes()),
|
||||||
},
|
// },
|
||||||
Attribute {
|
// Attribute {
|
||||||
key: QName(b"k3"),
|
// key: QName(b"k3"),
|
||||||
value: Cow::from(k3.to_string().into_bytes()),
|
// value: Cow::from(k3.to_string().into_bytes()),
|
||||||
},
|
// },
|
||||||
Attribute {
|
// Attribute {
|
||||||
key: QName(b"k4"),
|
// key: QName(b"k4"),
|
||||||
value: Cow::from(k4.to_string().into_bytes()),
|
// value: Cow::from(k4.to_string().into_bytes()),
|
||||||
},
|
// },
|
||||||
|
// ]);
|
||||||
|
r.append(&mut gen_attrs![
|
||||||
|
b"k1" = k1,
|
||||||
|
b"k2" = k2,
|
||||||
|
b"k3" = k3,
|
||||||
|
b"k4" = k4
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -14,15 +14,9 @@ pub struct Flood {
|
||||||
|
|
||||||
impl WriteElement for Flood {
|
impl WriteElement for Flood {
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
vec![
|
gen_attrs![
|
||||||
Attribute {
|
b"flood-color" = self.flood_color.to_hex_string(),
|
||||||
key: QName(b"flood-color"),
|
b"flood-opacity" = self.flood_opacity
|
||||||
value: Cow::from(self.flood_color.to_hex_string().into_bytes()),
|
|
||||||
},
|
|
||||||
Attribute {
|
|
||||||
key: QName(b"flood-opacity"),
|
|
||||||
value: Cow::from(self.flood_opacity.to_string().into_bytes()),
|
|
||||||
},
|
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -26,12 +26,7 @@ impl GaussianBlur {
|
||||||
|
|
||||||
impl WriteElement for GaussianBlur {
|
impl WriteElement for GaussianBlur {
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
vec![Attribute {
|
gen_attrs![b"stdDeviation" = format!("{} {}", self.std_deviation.0, self.std_deviation.1)]
|
||||||
key: QName(b"stdDeviation"),
|
|
||||||
value: Cow::from(
|
|
||||||
format!("{} {}", self.std_deviation.0, self.std_deviation.1).into_bytes(),
|
|
||||||
),
|
|
||||||
}]
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn tag_name(&self) -> &'static str {
|
fn tag_name(&self) -> &'static str {
|
||||||
|
|
|
@ -13,15 +13,9 @@ pub struct Morphology {
|
||||||
|
|
||||||
impl WriteElement for Morphology {
|
impl WriteElement for Morphology {
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
vec![
|
gen_attrs![
|
||||||
Attribute {
|
b"operator" = self.operator,
|
||||||
key: QName(b"operator"),
|
b"radius" = format!("{} {}", self.radius.0, self.radius.1)
|
||||||
value: Cow::from(self.operator.to_string().into_bytes()),
|
|
||||||
},
|
|
||||||
Attribute {
|
|
||||||
key: QName(b"radius"),
|
|
||||||
value: Cow::from(format!("{} {}", self.radius.0, self.radius.1).into_bytes()),
|
|
||||||
},
|
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -19,16 +19,7 @@ impl Offset {
|
||||||
|
|
||||||
impl WriteElement for Offset {
|
impl WriteElement for Offset {
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
vec![
|
gen_attrs![b"dx" = self.dx, b"dy" = self.dy]
|
||||||
Attribute {
|
|
||||||
key: QName(b"dx"),
|
|
||||||
value: Cow::from(self.dx.to_string().into_bytes()),
|
|
||||||
},
|
|
||||||
Attribute {
|
|
||||||
key: QName(b"dy"),
|
|
||||||
value: Cow::from(self.dy.to_string().into_bytes()),
|
|
||||||
},
|
|
||||||
]
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn tag_name(&self) -> &'static str {
|
fn tag_name(&self) -> &'static str {
|
||||||
|
|
|
@ -1,10 +1,3 @@
|
||||||
use std::borrow::Cow;
|
|
||||||
|
|
||||||
use quick_xml::{
|
|
||||||
events::attributes::{Attr, Attribute},
|
|
||||||
name::QName,
|
|
||||||
};
|
|
||||||
|
|
||||||
use super::WriteElement;
|
use super::WriteElement;
|
||||||
|
|
||||||
/// [feTurbulence](https://www.w3.org/TR/SVG11/filters.html#feTurbulenceElement)
|
/// [feTurbulence](https://www.w3.org/TR/SVG11/filters.html#feTurbulenceElement)
|
||||||
|
@ -19,40 +12,26 @@ pub struct Turbulence {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl WriteElement for Turbulence {
|
impl WriteElement for Turbulence {
|
||||||
|
#[allow(clippy::str_to_string, reason = "in macro invocation")]
|
||||||
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
fn attrs(&self) -> Vec<quick_xml::events::attributes::Attribute> {
|
||||||
let mut r = Vec::from([Attribute {
|
let mut r = gen_attrs!(
|
||||||
key: QName(b"baseFrequency"),
|
b"baseFrequency" = format!("{} {}", self.base_frequency.0, self.base_frequency.1)
|
||||||
value: Cow::from(
|
);
|
||||||
format!("{} {}", self.base_frequency.0, self.base_frequency.1).into_bytes(),
|
|
||||||
),
|
|
||||||
}]);
|
|
||||||
|
|
||||||
if self.num_octaves != 1 {
|
if self.num_octaves != 1 {
|
||||||
r.push(Attribute {
|
r.push(gen_attr!(b"numOctaves" = self.num_octaves));
|
||||||
key: QName(b"numOctaves"),
|
|
||||||
value: Cow::from(format!("{}", self.num_octaves).into_bytes()),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.seed != 0 {
|
if self.seed != 0 {
|
||||||
r.push(Attribute {
|
r.push(gen_attr!(b"seed" = self.seed));
|
||||||
key: QName(b"seed"),
|
|
||||||
value: Cow::from(self.seed.to_string().into_bytes()),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.stitch_tiles != StitchTiles::NoStitch {
|
if self.stitch_tiles != StitchTiles::NoStitch {
|
||||||
r.push(Attribute {
|
r.push(gen_attr!(b"stitchTiles" = "stitch"));
|
||||||
key: QName(b"stitchTiles"),
|
|
||||||
value: Cow::from(b"stitch".to_vec()),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.noise_type != NoiseType::Turbulence {
|
if self.noise_type != NoiseType::Turbulence {
|
||||||
r.push(Attribute {
|
r.push(gen_attr!(b"type" = "fractalNoise"));
|
||||||
key: QName(b"type"),
|
|
||||||
value: Cow::from(b"fractalNoise".to_vec()),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
r
|
r
|
||||||
|
|
Loading…
Reference in a new issue