summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorLaurenz <laurmaedje@gmail.com>2020-02-04 21:36:29 +0100
committerLaurenz <laurmaedje@gmail.com>2020-02-04 21:36:29 +0100
commit751812f45141a7b2022d0dba138457f3c21950b0 (patch)
tree8f5125f5c475313c460f4a98ec174c11cb0e9c02 /src
parente63ce52ae0d929506a1fa238477f039d14d53813 (diff)
Serialize layouts with serde 🔠
Diffstat (limited to 'src')
-rw-r--r--src/func.rs10
-rw-r--r--src/layout/actions.rs37
-rw-r--r--src/layout/mod.rs33
-rw-r--r--src/lib.rs7
-rw-r--r--src/size.rs10
-rw-r--r--src/syntax/func/values.rs6
6 files changed, 50 insertions, 53 deletions
diff --git a/src/func.rs b/src/func.rs
index 215de60f..88d08d2d 100644
--- a/src/func.rs
+++ b/src/func.rs
@@ -53,16 +53,16 @@ pub trait ParseFunc {
/// body: Option<SyntaxModel>,
/// }
///
-/// parse(header, body, ctx, errors, decos) {
-/// let body = body!(opt: body, ctx, errors, decos);
-/// let hidden = header.args.pos.get::<bool>(errors)
-/// .or_missing(errors, header.name.span, "hidden")
+/// parse(header, body, ctx, f) {
+/// let body = body!(opt: body, ctx, f);
+/// let hidden = header.args.pos.get::<bool>(&mut f.errors)
+/// .or_missing(&mut f.errors, header.name.span, "hidden")
/// .unwrap_or(false);
///
/// HiderFunc { body: if hidden { None } else { body } }
/// }
///
-/// layout(self, ctx, errors) {
+/// layout(self, ctx, f) {
/// match &self.body {
/// Some(model) => vec![LayoutSyntaxModel(model)],
/// None => vec![],
diff --git a/src/layout/actions.rs b/src/layout/actions.rs
index 314084e5..0abef5f9 100644
--- a/src/layout/actions.rs
+++ b/src/layout/actions.rs
@@ -1,11 +1,11 @@
//! Drawing and configuration actions composing layouts.
-use std::io::{self, Write};
use std::fmt::{self, Debug, Formatter};
+use serde::ser::{Serialize, Serializer, SerializeTuple};
use toddle::query::FontIndex;
use crate::size::{Size, Size2D};
-use super::{Layout, Serialize};
+use super::Layout;
use self::LayoutAction::*;
@@ -24,12 +24,33 @@ pub enum LayoutAction {
}
impl Serialize for LayoutAction {
- fn serialize<W: Write>(&self, f: &mut W) -> io::Result<()> {
+ fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> where S: Serializer {
match self {
- MoveAbsolute(s) => write!(f, "m {:.4} {:.4}", s.x.to_pt(), s.y.to_pt()),
- SetFont(i, s) => write!(f, "f {} {} {}", i.id, i.variant, s.to_pt()),
- WriteText(s) => write!(f, "w {}", s),
- DebugBox(s) => write!(f, "b {} {}", s.x.to_pt(), s.y.to_pt()),
+ LayoutAction::MoveAbsolute(pos) => {
+ let mut tup = serializer.serialize_tuple(2)?;
+ tup.serialize_element(&0u8)?;
+ tup.serialize_element(&pos)?;
+ tup.end()
+ }
+ LayoutAction::SetFont(index, size) => {
+ let mut tup = serializer.serialize_tuple(4)?;
+ tup.serialize_element(&1u8)?;
+ tup.serialize_element(index)?;
+ tup.serialize_element(size)?;
+ tup.end()
+ }
+ LayoutAction::WriteText(text) => {
+ let mut tup = serializer.serialize_tuple(2)?;
+ tup.serialize_element(&2u8)?;
+ tup.serialize_element(text)?;
+ tup.end()
+ }
+ LayoutAction::DebugBox(size) => {
+ let mut tup = serializer.serialize_tuple(2)?;
+ tup.serialize_element(&3u8)?;
+ tup.serialize_element(&size)?;
+ tup.end()
+ }
}
}
}
@@ -40,7 +61,7 @@ impl Debug for LayoutAction {
match self {
MoveAbsolute(s) => write!(f, "move {} {}", s.x, s.y),
SetFont(i, s) => write!(f, "font {}_{} {}", i.id, i.variant, s),
- WriteText(s) => write!(f, "write \"{}\"", s),
+ WriteText(s) => write!(f, "write {:?}", s),
DebugBox(s) => write!(f, "box {} {}", s.x, s.y),
}
}
diff --git a/src/layout/mod.rs b/src/layout/mod.rs
index b29d87e3..01d402db 100644
--- a/src/layout/mod.rs
+++ b/src/layout/mod.rs
@@ -1,8 +1,8 @@
//! Layouting types and engines.
-use std::io::{self, Write};
use std::fmt::{self, Display, Formatter};
use smallvec::SmallVec;
+use serde::Serialize;
use toddle::query::FontIndex;
use crate::size::{Size, Size2D, SizeBox};
@@ -32,11 +32,12 @@ pub mod prelude {
pub type MultiLayout = Vec<Layout>;
/// A finished box with content at fixed positions.
-#[derive(Debug, Clone, PartialEq)]
+#[derive(Debug, Clone, PartialEq, Serialize)]
pub struct Layout {
/// The size of the box.
pub dimensions: Size2D,
/// How to align this layout in a parent container.
+ #[serde(skip)]
pub alignment: LayoutAlignment,
/// The actions composing this layout.
pub actions: Vec<LayoutAction>,
@@ -57,34 +58,6 @@ impl Layout {
}
}
-/// Layout components that can be serialized.
-pub trait Serialize {
- /// Serialize the data structure into an output writable.
- fn serialize<W: Write>(&self, f: &mut W) -> io::Result<()>;
-}
-
-impl Serialize for Layout {
- fn serialize<W: Write>(&self, f: &mut W) -> io::Result<()> {
- writeln!(f, "{:.4} {:.4}", self.dimensions.x.to_pt(), self.dimensions.y.to_pt())?;
- writeln!(f, "{}", self.actions.len())?;
- for action in &self.actions {
- action.serialize(f)?;
- writeln!(f)?;
- }
- Ok(())
- }
-}
-
-impl Serialize for MultiLayout {
- fn serialize<W: Write>(&self, f: &mut W) -> io::Result<()> {
- writeln!(f, "{}", self.len())?;
- for layout in self {
- layout.serialize(f)?;
- }
- Ok(())
- }
-}
-
/// A vector of layout spaces, that is stack allocated as long as it only
/// contains at most 2 spaces.
pub type LayoutSpaces = SmallVec<[LayoutSpace; 2]>;
diff --git a/src/lib.rs b/src/lib.rs
index b74837fe..7136b2bd 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -24,7 +24,8 @@ use async_trait::async_trait;
use smallvec::smallvec;
use toddle::{Font, OwnedData};
-use toddle::query::{FontLoader, FontProvider, SharedFontLoader, FontDescriptor};
+use toddle::query::{FontLoader, SharedFontLoader};
+use toddle::query::{FontProvider, FontIndex, FontDescriptor};
use crate::error::Error;
use crate::layout::MultiLayout;
@@ -223,8 +224,8 @@ where P: FontProvider, P::Error: Debug + 'static {
type Data = P::Data;
type Error = Box<dyn Debug>;
- async fn load(&self, index: usize, variant: usize) -> Result<Font<P::Data>, Self::Error> {
- self.provider.load(index, variant).await
+ async fn load(&self, index: FontIndex) -> Result<Font<P::Data>, Self::Error> {
+ self.provider.load(index).await
.map_err(|d| Box::new(d) as Box<dyn Debug>)
}
}
diff --git a/src/size.rs b/src/size.rs
index 79b98774..e97b9248 100644
--- a/src/size.rs
+++ b/src/size.rs
@@ -4,12 +4,14 @@ use std::fmt::{self, Debug, Display, Formatter};
use std::iter::Sum;
use std::ops::*;
use std::str::FromStr;
+use serde::Serialize;
use crate::layout::prelude::*;
/// A general spacing type.
-#[derive(Default, Copy, Clone, PartialEq, PartialOrd)]
+#[derive(Default, Copy, Clone, PartialEq, PartialOrd, Serialize)]
+#[serde(transparent)]
pub struct Size {
/// The size in typographic points (1/72 inches).
pub points: f32,
@@ -137,7 +139,7 @@ pub type FSize = ScaleSize;
pub type PSize = ScaleSize;
/// A value in two dimensions.
-#[derive(Default, Copy, Clone, Eq, PartialEq)]
+#[derive(Default, Copy, Clone, Eq, PartialEq, Serialize)]
pub struct Value2D<T> {
/// The horizontal component.
pub x: T,
@@ -299,7 +301,7 @@ impl Neg for Size2D {
/// A value that is stretchable in an interval from a minimal through an optimal
/// to a maximal value.
-#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
+#[derive(Debug, Default, Copy, Clone, Eq, PartialEq, Serialize)]
pub struct StretchValue<T> {
/// The minimum this value can be stretched to.
pub min: T,
@@ -320,7 +322,7 @@ impl<T> StretchValue<T> {
pub type StretchSize = StretchValue<Size>;
/// A value in four dimensions.
-#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
+#[derive(Debug, Default, Copy, Clone, Eq, PartialEq, Serialize)]
pub struct ValueBox<T> {
/// The left extent.
pub left: T,
diff --git a/src/syntax/func/values.rs b/src/syntax/func/values.rs
index d2b54a0b..8e0c24b4 100644
--- a/src/syntax/func/values.rs
+++ b/src/syntax/func/values.rs
@@ -100,9 +100,9 @@ impl From<StringLike> for String {
}
}
-/// A value type that matches the string `"default"` or a value type `V` and
-/// returns `Option::Some(V::Output)` for a value and `Option::None` for
-/// `"default"`.
+/// A value type that matches the identifier `default` or a value type `V` and
+/// implements `Into<Option>` yielding `Option::Some(V)` for a value and
+/// `Option::None` for `default`.
///
/// # Example
/// ```