summaryrefslogtreecommitdiff
path: root/src/doc.rs
diff options
context:
space:
mode:
authorLaurenz <laurmaedje@gmail.com>2019-03-13 18:42:33 +0100
committerLaurenz <laurmaedje@gmail.com>2019-03-13 18:42:33 +0100
commit0c87c0c5a5b7379e938ef9f37673f9c9c0bff051 (patch)
tree6310996dd92bcf50999ae2f3ce7641d08ef36986 /src/doc.rs
parent107450ee5ca8e7e0bc03cf6ce9f59268aa20e9f6 (diff)
Basic multiline support 📜
Diffstat (limited to 'src/doc.rs')
-rw-r--r--src/doc.rs108
1 files changed, 97 insertions, 11 deletions
diff --git a/src/doc.rs b/src/doc.rs
index bff4926a..3e060f6e 100644
--- a/src/doc.rs
+++ b/src/doc.rs
@@ -1,6 +1,5 @@
//! Abstract representation of a typesetted document.
-use std::ops;
use crate::font::Font;
@@ -23,8 +22,10 @@ pub struct Style {
/// A fallback list of font families to use.
pub font_families: Vec<String>,
- /// The default font size.
+ /// The font size.
pub font_size: f32,
+ /// The line spacing (as a multiple of the font size).
+ pub line_spacing: f32,
}
impl Default for Style {
@@ -39,6 +40,7 @@ impl Default for Style {
"NotoSans", "NotoSansMath"
]).iter().map(ToString::to_string).collect(),
font_size: 12.0,
+ line_spacing: 1.25,
}
}
}
@@ -78,6 +80,10 @@ pub struct Size {
}
impl Size {
+ /// Create an zeroed size.
+ #[inline]
+ pub fn zero() -> Size { Size { points: 0.0 } }
+
/// Create a size from a number of points.
#[inline]
pub fn from_points(points: f32) -> Size { Size { points } }
@@ -111,18 +117,98 @@ impl Size {
pub fn to_cm(&self) -> f32 { self.points * 0.0352778 }
}
-impl ops::Add for Size {
- type Output = Size;
+mod size {
+ use super::Size;
+ use std::cmp::Ordering;
+ use std::fmt;
+ use std::iter::Sum;
+ use std::ops::*;
- fn add(self, other: Size) -> Size {
- Size { points: self.points + other.points }
+ impl fmt::Display for Size {
+ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+ write!(f, "{}pt", self.points)
+ }
}
-}
-impl ops::Sub for Size {
- type Output = Size;
+ macro_rules! impl_reflexive {
+ ($trait:ident, $func:ident, $assign_trait:ident, $assign_func:ident) => {
+ impl $trait for Size {
+ type Output = Size;
+
+ #[inline]
+ fn $func(self, other: Size) -> Size {
+ Size { points: $trait::$func(self.points, other.points) }
+ }
+ }
+
+ impl $assign_trait for Size {
+ #[inline]
+ fn $assign_func(&mut self, other: Size) {
+ $assign_trait::$assign_func(&mut self.points, other.points);
+ }
+ }
+ };
+ }
+
+ macro_rules! impl_num_back {
+ ($trait:ident, $func:ident, $assign_trait:ident, $assign_func:ident, $ty:ty) => {
+ impl $trait<$ty> for Size {
+ type Output = Size;
+
+ #[inline]
+ fn $func(self, other: $ty) -> Size {
+ Size { points: $trait::$func(self.points, other as f32) }
+ }
+ }
+
+ impl $assign_trait<$ty> for Size {
+ #[inline]
+ fn $assign_func(&mut self, other: $ty) {
+ $assign_trait::$assign_func(&mut self.points, other as f32);
+ }
+ }
+ };
+ }
+
+ macro_rules! impl_num_both {
+ ($trait:ident, $func:ident, $assign_trait:ident, $assign_func:ident, $ty:ty) => {
+ impl_num_back!($trait, $func, $assign_trait, $assign_func, $ty);
+
+ impl $trait<Size> for $ty {
+ type Output = Size;
+
+ #[inline]
+ fn $func(self, other: Size) -> Size {
+ Size { points: $trait::$func(self as f32, other.points) }
+ }
+ }
+ };
+ }
+
+ impl Neg for Size {
+ type Output = Size;
+
+ fn neg(self) -> Size {
+ Size { points: -self.points }
+ }
+ }
- fn sub(self, other: Size) -> Size {
- Size { points: self.points - other.points }
+ impl_reflexive!(Add, add, AddAssign, add_assign);
+ impl_reflexive!(Sub, sub, SubAssign, sub_assign);
+ impl_num_both!(Mul, mul, MulAssign, mul_assign, f32);
+ impl_num_both!(Mul, mul, MulAssign, mul_assign, i32);
+ impl_num_back!(Div, div, DivAssign, div_assign, f32);
+ impl_num_back!(Div, div, DivAssign, div_assign, i32);
+
+ impl PartialOrd for Size {
+ fn partial_cmp(&self, other: &Size) -> Option<Ordering> {
+ self.points.partial_cmp(&other.points)
+ }
+ }
+
+ impl Sum for Size {
+ fn sum<I>(iter: I) -> Size where I: Iterator<Item=Size> {
+ iter.fold(Size::zero(), Add::add)
+ }
}
}