From ba3f5256244bdba1067944f611b9c047c3c73cae Mon Sep 17 00:00:00 2001 From: mkorje Date: Fri, 25 Apr 2025 22:36:21 +1000 Subject: [PATCH] Allow a function as an argument to size in `accent` The short fall is now only applied in the default for `accent` (`x => x - 0.5em`). --- crates/typst-layout/src/math/accent.rs | 12 +++------ crates/typst-library/src/math/accent.rs | 30 ++++++++++++++++++----- tests/ref/math-accent-sized-function.png | Bin 0 -> 417 bytes tests/suite/math/accent.typ | 12 ++++++--- 4 files changed, 36 insertions(+), 18 deletions(-) create mode 100644 tests/ref/math-accent-sized-function.png diff --git a/crates/typst-layout/src/math/accent.rs b/crates/typst-layout/src/math/accent.rs index e7f051ace..32937c52b 100644 --- a/crates/typst-layout/src/math/accent.rs +++ b/crates/typst-layout/src/math/accent.rs @@ -1,6 +1,6 @@ use typst_library::diag::SourceResult; use typst_library::foundations::{Packed, StyleChain}; -use typst_library::layout::{Em, Frame, Point, Size}; +use typst_library::layout::{Frame, Point, Size}; use typst_library::math::AccentElem; use super::{ @@ -8,9 +8,6 @@ use super::{ MathFragment, }; -/// How much the accent can be shorter than the base. -const ACCENT_SHORT_FALL: Em = Em::new(0.5); - /// Lays out an [`AccentElem`]. #[typst_macros::time(name = "math.accent", span = elem.span())] pub fn layout_accent( @@ -45,11 +42,8 @@ pub fn layout_accent( let mut glyph = GlyphFragment::new_char(ctx.font, accent_styles, accent.0, elem.span())?; - // Forcing the accent to be at least as large as the base makes it too wide - // in many cases. - let width = elem.size.resolve(styles).relative_to(base.width()); - let short_fall = ACCENT_SHORT_FALL.at(glyph.item.size); - glyph.stretch_horizontal(ctx, width - short_fall); + let width = elem.size.get_ref(styles).resolve(ctx.engine, styles, base.width())?; + glyph.stretch_horizontal(ctx, width); let accent_attach = glyph.accent_attach.0; let accent = glyph.into_frame(); diff --git a/crates/typst-library/src/math/accent.rs b/crates/typst-library/src/math/accent.rs index 5a9c47aea..2921c95ac 100644 --- a/crates/typst-library/src/math/accent.rs +++ b/crates/typst-library/src/math/accent.rs @@ -6,9 +6,21 @@ use icu_provider::AsDeserializingBufferProvider; use icu_provider_blob::BlobDataProvider; use crate::diag::bail; -use crate::foundations::{cast, elem, func, Content, NativeElement, SymbolElem}; -use crate::layout::{Length, Rel}; -use crate::math::Mathy; +use crate::foundations::{ + cast, elem, func, Content, NativeElement, NativeFunc, SymbolElem, +}; +use crate::layout::{Em, Length, Ratio, Rel}; +use crate::math::{Mathy, StretchSize}; + +const ACCENT_SHORT_FALL: Em = Em::new(-0.5); + +#[func(name = "x => x - 0.5em")] +const fn default_accent_size(base: Length) -> Rel { + Rel { + rel: Ratio::zero(), + abs: Length { abs: base.abs, em: ACCENT_SHORT_FALL }, + } +} /// Attaches an accent to a base. /// @@ -59,11 +71,14 @@ pub struct AccentElem { /// The size of the accent, relative to the width of the base. /// + /// See the [stretch documentation]($math.stretch.size) for more + /// information on sizes. + /// /// ```example /// $dash(A, size: #150%)$ /// ``` - #[default(Rel::one())] - pub size: Rel, + #[default(::data().into())] + pub size: StretchSize, /// Whether to remove the dot on top of lowercase i and j when adding a top /// accent. @@ -140,8 +155,11 @@ macro_rules! accents { /// The base to which the accent is applied. base: Content, /// The size of the accent, relative to the width of the base. + /// + /// See the [stretch documentation]($math.stretch.size) for + /// more information on sizes. #[named] - size: Option>, + size: Option, /// Whether to remove the dot on top of lowercase i and j when /// adding a top accent. #[named] diff --git a/tests/ref/math-accent-sized-function.png b/tests/ref/math-accent-sized-function.png new file mode 100644 index 0000000000000000000000000000000000000000..9bd52a6e72aa76c5c5d481bc93fecec24637de1b GIT binary patch literal 417 zcmV;S0bc%zP)adD!gD3XJNhl2?xdCJ3T2enOEEf1Grd7SoJN!nA| z+FCTNv9X7upX|+F@ul_q`~$DP-^1rq#vi3jgEhFs;h4!}iUD~Ka4&sv(PrH-z^d^= z5`F~Wqrhi|gdptK10nrjoNRx~ks!QO1<;%VMt6~e4-=KZYZHL(Sq{!yXm|m~Fpz0L z4&K@_H~L`24(t!Y-Mb9zJA>Y1(4~Me8|pM7u)Ez&sC&Gyu6Kg7WpS;0PwVQEgX4 x - 0.1em) +$dash(A) arrow(I) hat(L)$ --- math-accent-dotless --- // Test dotless glyph variants. @@ -85,7 +91,7 @@ $ accent(integral, \u{20EC}), accent(integral, \u{20EC})_a^b, accent(integral_a^ --- math-accent-bottom-sized --- // Test bottom accent size. -$accent(sum, \u{0330}), accent(sum, \u{0330}, size: #50%), accent(H, \u{032D}, size: #200%)$ +$accent(sum, \u{0330}), accent(sum, \u{0330}, size: #25%), accent(H, \u{032D}, size: #125%)$ --- math-accent-nested --- // Test nested top and bottom accents.