diff options
| author | Laurenz <laurmaedje@gmail.com> | 2020-10-10 22:19:36 +0200 |
|---|---|---|
| committer | Laurenz <laurmaedje@gmail.com> | 2020-10-10 22:19:36 +0200 |
| commit | 92c01da36016e94ff20163806ddcbcf7e33d4031 (patch) | |
| tree | 1a900b3c11edcc93e9153fada3ce92310db5768b /src/library | |
| parent | 42500d5ed85539c5ab04dd3544beaf802da29be9 (diff) | |
Switch back to custom geometry types, unified with layout primitives 🏞
Diffstat (limited to 'src/library')
| -rw-r--r-- | src/library/align.rs | 96 | ||||
| -rw-r--r-- | src/library/boxed.rs | 4 | ||||
| -rw-r--r-- | src/library/font.rs | 4 | ||||
| -rw-r--r-- | src/library/page.rs | 7 | ||||
| -rw-r--r-- | src/library/spacing.rs | 2 |
5 files changed, 91 insertions, 22 deletions
diff --git a/src/library/align.rs b/src/library/align.rs index acd3a85c..d6b14692 100644 --- a/src/library/align.rs +++ b/src/library/align.rs @@ -1,4 +1,5 @@ use crate::prelude::*; +use std::fmt::{self, Display, Formatter}; /// `align`: Align content along the layouting axes. /// @@ -18,10 +19,10 @@ pub fn align(mut args: Args, ctx: &mut EvalContext) -> Value { let snapshot = ctx.state.clone(); let body = args.find::<SynTree>(); - let first = args.get::<_, Spanned<SpecAlign>>(ctx, 0); - let second = args.get::<_, Spanned<SpecAlign>>(ctx, 1); - let hor = args.get::<_, Spanned<SpecAlign>>(ctx, "horizontal"); - let ver = args.get::<_, Spanned<SpecAlign>>(ctx, "vertical"); + let first = args.get::<_, Spanned<AlignArg>>(ctx, 0); + let second = args.get::<_, Spanned<AlignArg>>(ctx, 1); + let hor = args.get::<_, Spanned<AlignArg>>(ctx, "horizontal"); + let ver = args.get::<_, Spanned<AlignArg>>(ctx, "vertical"); args.done(ctx); let iter = first @@ -50,10 +51,10 @@ pub fn align(mut args: Args, ctx: &mut EvalContext) -> Value { /// Deduplicate alignments and deduce to which axes they apply. fn dedup_aligns( ctx: &mut EvalContext, - iter: impl Iterator<Item = (Option<SpecAxis>, Spanned<SpecAlign>)>, -) -> Gen2<GenAlign> { + iter: impl Iterator<Item = (Option<SpecAxis>, Spanned<AlignArg>)>, +) -> Gen<Align> { let mut aligns = ctx.state.aligns; - let mut had = Gen2::new(false, false); + let mut had = Gen::new(false, false); let mut had_center = false; for (axis, Spanned { v: align, span }) in iter { @@ -77,15 +78,15 @@ fn dedup_aligns( } else { // We don't know the axis: This has to be a `center` alignment for a // positional argument. - debug_assert_eq!(align, SpecAlign::Center); + debug_assert_eq!(align, AlignArg::Center); if had.main && had.cross { ctx.diag(error!(span, "duplicate alignment")); } else if had_center { // Both this and the previous one are unspecified `center` // alignments. Both axes should be centered. - aligns = Gen2::new(GenAlign::Center, GenAlign::Center); - had = Gen2::new(true, true); + aligns = Gen::new(Align::Center, Align::Center); + had = Gen::new(true, true); } else { had_center = true; } @@ -95,10 +96,10 @@ fn dedup_aligns( // alignment. if had_center && (had.main || had.cross) { if had.main { - aligns.cross = GenAlign::Center; + aligns.cross = Align::Center; had.cross = true; } else { - aligns.main = GenAlign::Center; + aligns.main = Align::Center; had.main = true; } had_center = false; @@ -108,8 +109,77 @@ fn dedup_aligns( // If center has not been flushed by now, it is the only argument and then // we default to applying it to the cross axis. if had_center { - aligns.cross = GenAlign::Center; + aligns.cross = Align::Center; } aligns } + +/// An alignment argument. +#[derive(Debug, Copy, Clone, Eq, PartialEq, Ord, PartialOrd)] +enum AlignArg { + Left, + Right, + Top, + Bottom, + Center, +} + +impl AlignArg { + /// The specific axis this alignment refers to. + /// + /// Returns `None` if this is `Center` since the axis is unknown. + pub fn axis(self) -> Option<SpecAxis> { + match self { + Self::Left => Some(SpecAxis::Horizontal), + Self::Right => Some(SpecAxis::Horizontal), + Self::Top => Some(SpecAxis::Vertical), + Self::Bottom => Some(SpecAxis::Vertical), + Self::Center => None, + } + } +} + +impl Switch for AlignArg { + type Other = Align; + + fn switch(self, dirs: Gen<Dir>) -> Self::Other { + let get = |dir: Dir, at_positive_start| { + if dir.is_positive() == at_positive_start { + Align::Start + } else { + Align::End + } + }; + + let dirs = dirs.switch(dirs); + match self { + Self::Left => get(dirs.horizontal, true), + Self::Right => get(dirs.horizontal, false), + Self::Top => get(dirs.vertical, true), + Self::Bottom => get(dirs.vertical, false), + Self::Center => Align::Center, + } + } +} + +convert_ident!(AlignArg, "alignment", |v| match v { + "left" => Some(Self::Left), + "right" => Some(Self::Right), + "top" => Some(Self::Top), + "bottom" => Some(Self::Bottom), + "center" => Some(Self::Center), + _ => None, +}); + +impl Display for AlignArg { + fn fmt(&self, f: &mut Formatter) -> fmt::Result { + f.pad(match self { + Self::Left => "left", + Self::Right => "right", + Self::Top => "top", + Self::Bottom => "bottom", + Self::Center => "center", + }) + } +} diff --git a/src/library/boxed.rs b/src/library/boxed.rs index 6edb3b17..0c1ed30a 100644 --- a/src/library/boxed.rs +++ b/src/library/boxed.rs @@ -1,5 +1,5 @@ use crate::geom::Linear; -use crate::layout::nodes::{Fixed, Stack}; +use crate::layout::{Fixed, Stack}; use crate::prelude::*; /// `box`: Layouts its contents into a box. @@ -33,7 +33,7 @@ pub fn boxed(mut args: Args, ctx: &mut EvalContext) -> Value { dirs, children, aligns, - expand: Spec2::new(width.is_some(), height.is_some()), + expand: Spec::new(width.is_some(), height.is_some()), }), }); diff --git a/src/library/font.rs b/src/library/font.rs index be6823c3..e6d9cd12 100644 --- a/src/library/font.rs +++ b/src/library/font.rs @@ -57,9 +57,9 @@ pub fn font(mut args: Args, ctx: &mut EvalContext) -> Value { let body = args.find::<SynTree>(); if let Some(linear) = args.find::<Linear>() { - if linear.rel == 0.0 { + if linear.is_absolute() { ctx.state.text.font_size.base = linear.abs; - ctx.state.text.font_size.scale = Linear::rel(1.0); + ctx.state.text.font_size.scale = Relative::ONE.into(); } else { ctx.state.text.font_size.scale = linear; } diff --git a/src/library/page.rs b/src/library/page.rs index 3c6703bc..570dbb10 100644 --- a/src/library/page.rs +++ b/src/library/page.rs @@ -1,7 +1,6 @@ use std::mem; -use crate::eval::Absolute; -use crate::geom::Linear; +use crate::geom::{Length, Linear}; use crate::paper::{Paper, PaperClass}; use crate::prelude::*; @@ -25,12 +24,12 @@ pub fn page(mut args: Args, ctx: &mut EvalContext) -> Value { ctx.state.page.size = paper.size(); } - if let Some(Absolute(width)) = args.get::<_, Absolute>(ctx, "width") { + if let Some(width) = args.get::<_, Length>(ctx, "width") { ctx.state.page.class = PaperClass::Custom; ctx.state.page.size.width = width; } - if let Some(Absolute(height)) = args.get::<_, Absolute>(ctx, "height") { + if let Some(height) = args.get::<_, Length>(ctx, "height") { ctx.state.page.class = PaperClass::Custom; ctx.state.page.size.height = height; } diff --git a/src/library/spacing.rs b/src/library/spacing.rs index 6d00bd1c..a2b21e93 100644 --- a/src/library/spacing.rs +++ b/src/library/spacing.rs @@ -1,5 +1,5 @@ use crate::geom::Linear; -use crate::layout::nodes::{Softness, Spacing}; +use crate::layout::{Softness, Spacing}; use crate::prelude::*; /// `h`: Add horizontal spacing. |
