From db2fefdc8f5c329190c0e0f7de79c9b6fea9ec60 Mon Sep 17 00:00:00 2001 From: Arman Uguray Date: Mon, 10 Apr 2023 16:59:44 -0700 Subject: [PATCH] [vello_encoding] Move the encoding module into its own crate This change moves the vello encoding logic to a new crate under crates/encoding. Combined with the `vello_shaders` crate, this enables lightweight integration of the Vello pipelines into renderers that don't depend on wgpu (or perhaps written in languages other than Rust). The Scene/Fragment API currently remain the vello crate. --- Cargo.toml | 12 +++-- crates/encoding/Cargo.toml | 10 ++++ {src/encoding => crates/encoding/src}/draw.rs | 0 .../encoding/src}/encoding.rs | 6 +-- .../encoding => crates/encoding/src}/glyph.rs | 0 .../encoding/src}/glyph_cache.rs | 4 +- .../encoding/src}/image_cache.rs | 0 src/encoding.rs => crates/encoding/src/lib.rs | 0 {src/encoding => crates/encoding/src}/math.rs | 0 .../encoding/src}/monoid.rs | 0 {src/encoding => crates/encoding/src}/path.rs | 22 +++++++++ .../encoding/src}/ramp_cache.rs | 0 .../encoding/src}/resolve.rs | 4 +- examples/scenes/Cargo.toml | 1 + examples/scenes/src/simple_text.rs | 2 +- src/glyph.rs | 49 +++++-------------- src/render.rs | 14 +++--- src/scene.rs | 3 +- 18 files changed, 69 insertions(+), 58 deletions(-) create mode 100644 crates/encoding/Cargo.toml rename {src/encoding => crates/encoding/src}/draw.rs (100%) rename {src/encoding => crates/encoding/src}/encoding.rs (98%) rename {src/encoding => crates/encoding/src}/glyph.rs (100%) rename {src/encoding => crates/encoding/src}/glyph_cache.rs (96%) rename {src/encoding => crates/encoding/src}/image_cache.rs (100%) rename src/encoding.rs => crates/encoding/src/lib.rs (100%) rename {src/encoding => crates/encoding/src}/math.rs (100%) rename {src/encoding => crates/encoding/src}/monoid.rs (100%) rename {src/encoding => crates/encoding/src}/path.rs (95%) rename {src/encoding => crates/encoding/src}/ramp_cache.rs (100%) rename {src/encoding => crates/encoding/src}/resolve.rs (99%) diff --git a/Cargo.toml b/Cargo.toml index 78c5824..3b56fbb 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -2,6 +2,7 @@ resolver = "2" members = [ + "crates/encoding", "crates/shaders", "integrations/vello_svg", @@ -40,17 +41,20 @@ hot_reload = [] buffer_labels = [] [dependencies] +bytemuck = { workspace = true } +fello = { workspace = true } +peniko = { workspace = true } wgpu = { workspace = true } raw-window-handle = "0.5" futures-intrusive = "0.5.0" parking_lot = "0.12" -bytemuck = { version = "1.12.1", features = ["derive"] } smallvec = "1.8.0" -fello = { git = "https://github.com/dfrg/fount", rev = "58a284eaae67512fb61cf76177c5d33238d79cb1" } -peniko = { git = "https://github.com/linebender/peniko", rev = "cafdac9a211a0fb2fec5656bd663d1ac770bcc81" } -guillotiere = "0.6.2" +vello_encoding = { path = "crates/encoding" } [workspace.dependencies] +bytemuck = { version = "1.12.1", features = ["derive"] } +fello = { git = "https://github.com/dfrg/fount", rev = "58a284eaae67512fb61cf76177c5d33238d79cb1" } +peniko = { git = "https://github.com/linebender/peniko", rev = "cafdac9a211a0fb2fec5656bd663d1ac770bcc81" } wgpu = "0.15" # Used for examples diff --git a/crates/encoding/Cargo.toml b/crates/encoding/Cargo.toml new file mode 100644 index 0000000..f11c4bc --- /dev/null +++ b/crates/encoding/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "vello_encoding" +version = "0.1.0" +edition = "2021" + +[dependencies] +bytemuck = { workspace = true } +fello = { workspace = true } +peniko = { workspace = true } +guillotiere = "0.6.2" diff --git a/src/encoding/draw.rs b/crates/encoding/src/draw.rs similarity index 100% rename from src/encoding/draw.rs rename to crates/encoding/src/draw.rs diff --git a/src/encoding/encoding.rs b/crates/encoding/src/encoding.rs similarity index 98% rename from src/encoding/encoding.rs rename to crates/encoding/src/encoding.rs index 03ca730..3c140dc 100644 --- a/src/encoding/encoding.rs +++ b/crates/encoding/src/encoding.rs @@ -14,11 +14,9 @@ // // Also licensed under MIT license, at your choice. -use crate::encoding::DrawImage; - use super::{ - resolve::Patch, DrawColor, DrawLinearGradient, DrawRadialGradient, DrawTag, Glyph, GlyphRun, - PathEncoder, PathTag, Transform, + resolve::Patch, DrawColor, DrawImage, DrawLinearGradient, DrawRadialGradient, DrawTag, Glyph, + GlyphRun, PathEncoder, PathTag, Transform, }; use fello::NormalizedCoord; diff --git a/src/encoding/glyph.rs b/crates/encoding/src/glyph.rs similarity index 100% rename from src/encoding/glyph.rs rename to crates/encoding/src/glyph.rs diff --git a/src/encoding/glyph_cache.rs b/crates/encoding/src/glyph_cache.rs similarity index 96% rename from src/encoding/glyph_cache.rs rename to crates/encoding/src/glyph_cache.rs index f919afb..89de20a 100644 --- a/src/encoding/glyph_cache.rs +++ b/crates/encoding/src/glyph_cache.rs @@ -59,11 +59,11 @@ impl GlyphCache { Style::Fill(Fill::EvenOdd) => encoding_cache.encode_linewidth(-2.0), Style::Stroke(stroke) => encoding_cache.encode_linewidth(stroke.width), } - let mut path = crate::glyph::PathEncoderPen(encoding_cache.encode_path(is_fill)); + let mut path = encoding_cache.encode_path(is_fill); scaler .outline(GlyphId::new(key.glyph_id as u16), &mut path) .ok()?; - if path.0.finish(false) == 0 { + if path.finish(false) == 0 { return None; } let end = encoding_cache.stream_offsets(); diff --git a/src/encoding/image_cache.rs b/crates/encoding/src/image_cache.rs similarity index 100% rename from src/encoding/image_cache.rs rename to crates/encoding/src/image_cache.rs diff --git a/src/encoding.rs b/crates/encoding/src/lib.rs similarity index 100% rename from src/encoding.rs rename to crates/encoding/src/lib.rs diff --git a/src/encoding/math.rs b/crates/encoding/src/math.rs similarity index 100% rename from src/encoding/math.rs rename to crates/encoding/src/math.rs diff --git a/src/encoding/monoid.rs b/crates/encoding/src/monoid.rs similarity index 100% rename from src/encoding/monoid.rs rename to crates/encoding/src/monoid.rs diff --git a/src/encoding/path.rs b/crates/encoding/src/path.rs similarity index 95% rename from src/encoding/path.rs rename to crates/encoding/src/path.rs index 760eb32..5b01118 100644 --- a/src/encoding/path.rs +++ b/crates/encoding/src/path.rs @@ -381,3 +381,25 @@ impl<'a> PathEncoder<'a> { self.n_encoded_segments } } + +impl fello::scale::Pen for PathEncoder<'_> { + fn move_to(&mut self, x: f32, y: f32) { + self.move_to(x, y) + } + + fn line_to(&mut self, x: f32, y: f32) { + self.line_to(x, y) + } + + fn quad_to(&mut self, cx0: f32, cy0: f32, x: f32, y: f32) { + self.quad_to(cx0, cy0, x, y) + } + + fn curve_to(&mut self, cx0: f32, cy0: f32, cx1: f32, cy1: f32, x: f32, y: f32) { + self.cubic_to(cx0, cy0, cx1, cy1, x, y) + } + + fn close(&mut self) { + self.close() + } +} diff --git a/src/encoding/ramp_cache.rs b/crates/encoding/src/ramp_cache.rs similarity index 100% rename from src/encoding/ramp_cache.rs rename to crates/encoding/src/ramp_cache.rs diff --git a/src/encoding/resolve.rs b/crates/encoding/src/resolve.rs similarity index 99% rename from src/encoding/resolve.rs rename to crates/encoding/src/resolve.rs index 0077b5c..051f3ac 100644 --- a/src/encoding/resolve.rs +++ b/crates/encoding/src/resolve.rs @@ -25,7 +25,6 @@ use super::{ ramp_cache::{RampCache, Ramps}, DrawTag, Encoding, PathTag, StreamOffsets, Transform, }; -use crate::shaders; /// Layout of a packed encoding. #[derive(Clone, Copy, Debug, Default, Zeroable, Pod)] @@ -161,6 +160,7 @@ impl Resolver { &'a mut self, encoding: &Encoding, packed: &mut Vec, + workgroup_size: u32, ) -> (Layout, Ramps<'a>, Images<'a>) { let sizes = self.resolve_patches(encoding); self.resolve_pending_images(); @@ -172,7 +172,7 @@ impl Resolver { // Compute size of data buffer let n_path_tags = encoding.path_tags.len() + sizes.path_tags + encoding.n_open_clips as usize; - let path_tag_padded = align_up(n_path_tags, 4 * shaders::PATHTAG_REDUCE_WG); + let path_tag_padded = align_up(n_path_tags, 4 * workgroup_size); let capacity = path_tag_padded + slice_size_in_bytes(&encoding.path_data, sizes.path_data) + slice_size_in_bytes( diff --git a/examples/scenes/Cargo.toml b/examples/scenes/Cargo.toml index 7037d28..7118d77 100644 --- a/examples/scenes/Cargo.toml +++ b/examples/scenes/Cargo.toml @@ -12,6 +12,7 @@ repository.workspace = true [dependencies] vello = { path = "../../" } +vello_encoding = { path = "../../crates/encoding" } vello_svg = { path = "../../integrations/vello_svg" } anyhow = { workspace = true } clap = { workspace = true, features = ["derive"] } diff --git a/examples/scenes/src/simple_text.rs b/examples/scenes/src/simple_text.rs index c6371af..15ca0a2 100644 --- a/examples/scenes/src/simple_text.rs +++ b/examples/scenes/src/simple_text.rs @@ -17,7 +17,6 @@ use std::sync::Arc; use vello::{ - encoding::Glyph, fello::meta::MetadataProvider, fello::raw::FontRef, glyph::GlyphContext, @@ -25,6 +24,7 @@ use vello::{ peniko::{Blob, Brush, BrushRef, Font, StyleRef}, SceneBuilder, }; +use vello_encoding::Glyph; // This is very much a hack to get things working. // On Windows, can set this to "c:\\Windows\\Fonts\\seguiemj.ttf" to get color emoji diff --git a/src/glyph.rs b/src/glyph.rs index b398e6f..33f52eb 100644 --- a/src/glyph.rs +++ b/src/glyph.rs @@ -16,18 +16,17 @@ //! Support for glyph rendering. -use fello::scale::Pen; - -use crate::encoding::{Encoding, PathEncoder}; use crate::scene::{SceneBuilder, SceneFragment}; -use peniko::kurbo::Affine; -use peniko::{Brush, Color, Fill, Style}; - -use fello::{ - raw::types::GlyphId, - raw::FontRef, - scale::{Context, Scaler}, - FontKey, Setting, Size, +use { + fello::{ + raw::types::GlyphId, + raw::FontRef, + scale::{Context, Pen, Scaler}, + FontKey, Setting, Size, + }, + peniko::kurbo::Affine, + peniko::{Brush, Color, Fill, Style}, + vello_encoding::Encoding, }; /// General context for creating scene fragments for glyph outlines. @@ -105,9 +104,9 @@ impl<'a> GlyphProvider<'a> { Style::Fill(Fill::EvenOdd) => encoding.encode_linewidth(-2.0), Style::Stroke(stroke) => encoding.encode_linewidth(stroke.width), } - let mut path = PathEncoderPen(encoding.encode_path(matches!(style, Style::Fill(_)))); + let mut path = encoding.encode_path(matches!(style, Style::Fill(_))); self.scaler.outline(GlyphId::new(gid), &mut path).ok()?; - if path.0.finish(false) != 0 { + if path.finish(false) != 0 { Some(()) } else { None @@ -144,27 +143,3 @@ impl Pen for BezPathPen { self.0.close_path() } } - -pub(crate) struct PathEncoderPen<'a>(pub PathEncoder<'a>); - -impl Pen for PathEncoderPen<'_> { - fn move_to(&mut self, x: f32, y: f32) { - self.0.move_to(x, y) - } - - fn line_to(&mut self, x: f32, y: f32) { - self.0.line_to(x, y) - } - - fn quad_to(&mut self, cx0: f32, cy0: f32, x: f32, y: f32) { - self.0.quad_to(cx0, cy0, x, y) - } - - fn curve_to(&mut self, cx0: f32, cy0: f32, cx1: f32, cy1: f32, x: f32, y: f32) { - self.0.cubic_to(cx0, cy0, cx1, cy1, x, y) - } - - fn close(&mut self) { - self.0.close() - } -} diff --git a/src/render.rs b/src/render.rs index d96815e..893f82f 100644 --- a/src/render.rs +++ b/src/render.rs @@ -1,13 +1,15 @@ //! Take an encoded scene and create a graph to render it -use bytemuck::{Pod, Zeroable}; - use crate::{ - encoding::{Config, Encoding, Layout}, engine::{BufProxy, ImageFormat, ImageProxy, Recording, ResourceProxy}, shaders::{self, FullShaders, Shaders}, RenderParams, Scene, }; +use { + bytemuck::{Pod, Zeroable}, + vello_encoding::{Config, Encoding, Layout}, +}; + /// State for a render in progress. pub struct Render { @@ -213,11 +215,11 @@ impl Render { params: &RenderParams, robust: bool, ) -> Recording { - use crate::encoding::Resolver; + use vello_encoding::Resolver; let mut recording = Recording::default(); let mut resolver = Resolver::new(); let mut packed = vec![]; - let (layout, ramps, images) = resolver.resolve(encoding, &mut packed); + let (layout, ramps, images) = resolver.resolve(encoding, &mut packed, shaders::PATHTAG_REDUCE_WG); let gradient_image = if ramps.height == 0 { ResourceProxy::new_image(1, 1, ImageFormat::Rgba8) } else { @@ -245,7 +247,7 @@ impl Render { let new_height = next_multiple_of(params.height, 16); let info_size = layout.bin_data_start; - let config = crate::encoding::Config { + let config = vello_encoding::Config { width_in_tiles: new_width / 16, height_in_tiles: new_height / 16, target_width: params.width, diff --git a/src/scene.rs b/src/scene.rs index ce777b8..647bf89 100644 --- a/src/scene.rs +++ b/src/scene.rs @@ -17,8 +17,7 @@ use fello::NormalizedCoord; use peniko::kurbo::{Affine, Rect, Shape}; use peniko::{BlendMode, BrushRef, Color, Fill, Font, Image, Stroke, StyleRef}; - -use crate::encoding::{Encoding, Glyph, GlyphRun, Patch, Transform}; +use vello_encoding::{Encoding, Glyph, GlyphRun, Patch, Transform}; /// Encoded definition of a scene and associated resources. #[derive(Default)]