Skip to main content

Rasterizer

Struct Rasterizer 

Source
pub struct Rasterizer { /* private fields */ }
Expand description

CPU glyph rasterization, on swash. One per renderer — swash’s context caches scaling state, and the stroker its segment buffers.

Implementations§

Source§

impl Rasterizer

Source

pub fn new() -> Self

Examples found in repository?
examples/raster_bench.rs (line 45)
16fn main() {
17    let dir = concat!(env!("CARGO_MANIFEST_DIR"), "/../../assets/fonts");
18    // A CJK face is 20k+ glyphs and too big to vendor: point VALO_CJK_FONT
19    // at one to get the CJK column, otherwise the bench runs latin only.
20    let cjk_file = std::env::var("VALO_CJK_FONT").unwrap_or_default();
21    let mut fonts = FaceSet::default();
22    let latin = fonts
23        .register(
24            "Latin",
25            std::fs::read(format!("{dir}/fira_sans.ttf")).unwrap(),
26        )
27        .unwrap();
28    let cjk = std::fs::read(cjk_file)
29        .ok()
30        .and_then(|bytes| fonts.register("CJK", bytes));
31
32    let mut sets = vec![("latin", latin, glyphs(&fonts, latin, LATIN))];
33    if let Some(id) = cjk {
34        sets.push(("cjk", id, glyphs(&fonts, id, CJK)));
35    }
36
37    println!(
38        "{:>6} {:>6}  {:>12} {:>12}  (µs/glyph, n={})",
39        "set",
40        "px",
41        "alpha",
42        "sdf",
43        LATIN.len()
44    );
45    let mut raster = Rasterizer::new();
46    for (label, font, ids) in &sets {
47        for px in SIZES {
48            let alpha = time_per_glyph(ids, |g| {
49                raster.alpha(fonts.get(*font), g, px, 0.0);
50            });
51            let mut raster2 = Rasterizer::new();
52            let sdf = time_per_glyph(ids, |g| {
53                raster2.sdf(fonts.get(*font), g, px);
54            });
55            println!("{label:>6} {px:>6.0}  {alpha:>10.1}µs {sdf:>10.1}µs");
56        }
57    }
58}
Source

pub fn alpha( &mut self, font: &Font, glyph: u32, px: f32, dx: f32, ) -> Option<GlyphImage>

Plain alpha coverage at px — the mask tier. dx is the subpixel x-phase (0/¼/½/¾ px) baked into the raster, Skia/Impeller’s quarter-pixel positioning.

Examples found in repository?
examples/raster_bench.rs (line 49)
16fn main() {
17    let dir = concat!(env!("CARGO_MANIFEST_DIR"), "/../../assets/fonts");
18    // A CJK face is 20k+ glyphs and too big to vendor: point VALO_CJK_FONT
19    // at one to get the CJK column, otherwise the bench runs latin only.
20    let cjk_file = std::env::var("VALO_CJK_FONT").unwrap_or_default();
21    let mut fonts = FaceSet::default();
22    let latin = fonts
23        .register(
24            "Latin",
25            std::fs::read(format!("{dir}/fira_sans.ttf")).unwrap(),
26        )
27        .unwrap();
28    let cjk = std::fs::read(cjk_file)
29        .ok()
30        .and_then(|bytes| fonts.register("CJK", bytes));
31
32    let mut sets = vec![("latin", latin, glyphs(&fonts, latin, LATIN))];
33    if let Some(id) = cjk {
34        sets.push(("cjk", id, glyphs(&fonts, id, CJK)));
35    }
36
37    println!(
38        "{:>6} {:>6}  {:>12} {:>12}  (µs/glyph, n={})",
39        "set",
40        "px",
41        "alpha",
42        "sdf",
43        LATIN.len()
44    );
45    let mut raster = Rasterizer::new();
46    for (label, font, ids) in &sets {
47        for px in SIZES {
48            let alpha = time_per_glyph(ids, |g| {
49                raster.alpha(fonts.get(*font), g, px, 0.0);
50            });
51            let mut raster2 = Rasterizer::new();
52            let sdf = time_per_glyph(ids, |g| {
53                raster2.sdf(fonts.get(*font), g, px);
54            });
55            println!("{label:>6} {px:>6.0}  {alpha:>10.1}µs {sdf:>10.1}µs");
56        }
57    }
58}
Source

pub fn stroked( &mut self, font: &Font, glyph: u32, px: f32, dx: f32, stroke: &GlyphStroke, ) -> Option<GlyphImage>

Alpha coverage of the glyph’s STROKED outline — the stroked mask tier. Stroking happens before rasterizing, which is what lets the result be an ordinary cached atlas entry (Skia’s scaler strokes inside the strike for the same reason).

This does NOT go through swash. swash rasterizes with zeno, and zeno’s miter join short-circuits to a bevel whenever the two segment normals point apart (stroke.rs’s dot < 0.0), which caps its miter ratio at √2 and silently flattens every join sharper than a right angle — the apex of A, M, W, and most of what a stroked headline is made of. tiny-skia, already here for COLRv1, ports Skia’s stroker and honours miter_limit, and it hands back a real path whose tight bounds size the atlas cell. That measurement is the point: Impeller sizes its slot the same way, by handing the stroking paint to SkFont::getBounds.

Source

pub fn sdf(&mut self, font: &Font, glyph: u32, px: f32) -> Option<GlyphImage>

Signed distance field at px: the 1× AA coverage seeds the exact EDT directly (mapbox TinySDF’s shape — partial alpha carries the sub-pixel edge, so no supersample; ~7× the old 2×-8SSEDT pipeline). 128 = edge, ±SDF_PAD px span the range.

Examples found in repository?
examples/raster_bench.rs (line 53)
16fn main() {
17    let dir = concat!(env!("CARGO_MANIFEST_DIR"), "/../../assets/fonts");
18    // A CJK face is 20k+ glyphs and too big to vendor: point VALO_CJK_FONT
19    // at one to get the CJK column, otherwise the bench runs latin only.
20    let cjk_file = std::env::var("VALO_CJK_FONT").unwrap_or_default();
21    let mut fonts = FaceSet::default();
22    let latin = fonts
23        .register(
24            "Latin",
25            std::fs::read(format!("{dir}/fira_sans.ttf")).unwrap(),
26        )
27        .unwrap();
28    let cjk = std::fs::read(cjk_file)
29        .ok()
30        .and_then(|bytes| fonts.register("CJK", bytes));
31
32    let mut sets = vec![("latin", latin, glyphs(&fonts, latin, LATIN))];
33    if let Some(id) = cjk {
34        sets.push(("cjk", id, glyphs(&fonts, id, CJK)));
35    }
36
37    println!(
38        "{:>6} {:>6}  {:>12} {:>12}  (µs/glyph, n={})",
39        "set",
40        "px",
41        "alpha",
42        "sdf",
43        LATIN.len()
44    );
45    let mut raster = Rasterizer::new();
46    for (label, font, ids) in &sets {
47        for px in SIZES {
48            let alpha = time_per_glyph(ids, |g| {
49                raster.alpha(fonts.get(*font), g, px, 0.0);
50            });
51            let mut raster2 = Rasterizer::new();
52            let sdf = time_per_glyph(ids, |g| {
53                raster2.sdf(fonts.get(*font), g, px);
54            });
55            println!("{label:>6} {px:>6.0}  {alpha:>10.1}µs {sdf:>10.1}µs");
56        }
57    }
58}
Source

pub fn color(&mut self, font: &Font, glyph: u32, px: f32) -> Option<GlyphImage>

Color glyph (COLR outlines / CBDT-sbix bitmaps) at px: premultiplied RGBA, or None when the glyph has no color form — the caller falls back to the mask tiers. Mini rendered emoji through Canvas2D; swash is the native replacement.

Trait Implementations§

Source§

impl Default for Rasterizer

Source§

fn default() -> Rasterizer

Returns the “default value” for a type. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.