### Rendering Text to an Image Buffer in Rust Source: https://context7.com/redox-os/rusttype/llms.txt A complete example demonstrating how to render text to a pixel buffer. It loads a font, calculates glyph positions, creates an RGBA image buffer, and draws each glyph with alpha blending. ```rust use rusttype::{Font, Scale, point}; fn render_text_to_image( font: &Font, text: &str, font_size: f32, ) -> (Vec, u32, u32) { let scale = Scale::uniform(font_size); let v_metrics = font.v_metrics(scale); // Layout glyphs let glyphs: Vec<_> = font .layout(text, scale, point(0.0, v_metrics.ascent)) .collect(); // Calculate dimensions let height = (v_metrics.ascent - v_metrics.descent).ceil() as u32; let width = glyphs.iter() .filter_map(|g| g.pixel_bounding_box()) .map(|bb| bb.max.x) .max() .unwrap_or(0) as u32; // Create RGBA buffer (white background) let mut pixels = vec![255u8; (width * height * 4) as usize]; // Render each glyph for glyph in glyphs { if let Some(bb) = glyph.pixel_bounding_box() { glyph.draw(|x, y, coverage| { let px = (x as i32 + bb.min.x) as u32; let py = (y as i32 + bb.min.y) as u32; if px < width && py < height { let idx = ((py * width + px) * 4) as usize; // Black text with alpha from coverage let alpha = (coverage * 255.0) as u8; // Simple alpha blending with white background let inv_alpha = 255 - alpha; pixels[idx] = (inv_alpha as u16 * 255 / 255) as u8; // R pixels[idx + 1] = (inv_alpha as u16 * 255 / 255) as u8; // G pixels[idx + 2] = (inv_alpha as u16 * 255 / 255) as u8; // B pixels[idx + 3] = 255; // A } }); } } (pixels, width, height) } // Usage let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let (pixels, width, height) = render_text_to_image(&font, "RustType!", 48.0); println!("Rendered {}x{} image ({} bytes)", width, height, pixels.len()); ``` -------------------------------- ### Get Vertical Font Metrics - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves vertical font metrics (ascent, descent, line gap) for a given scale using `Font::v_metrics`. These metrics are crucial for accurate text layout, especially for multi-line text. The ascent is the distance above the baseline, descent is below (negative), and line gap is the space between lines. ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let scale = Scale::uniform(24.0); let v_metrics = font.v_metrics(scale); println!("Ascent: {}", v_metrics.ascent); // Distance above baseline println!("Descent: {}", v_metrics.descent); // Distance below baseline (negative) println!("Line gap: {}", v_metrics.line_gap); // Calculate line height for multi-line text let line_height = v_metrics.ascent - v_metrics.descent + v_metrics.line_gap; println!("Total line height: {}", line_height); ``` -------------------------------- ### Get Units Per EM - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves the number of font units per EM square using `Font::units_per_em`. This value is essential for converting font-specific units to pixel values or other measurement systems, commonly used in font scaling calculations. ```rust use rusttype::Font; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let units_per_em = font.units_per_em(); println!("Units per EM: {}", units_per_em); // Typically 1000 or 2048 ``` -------------------------------- ### Get and Position Glyph - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves a glyph for a character or glyph ID using `Font::glyph`. Missing characters default to the `.notdef` glyph (ID 0). The glyph can then be scaled and positioned using `scaled` and `positioned` methods, respectively. Horizontal metrics like advance width and side bearing are accessible. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); // Get a glyph from a character let glyph = font.glyph('A'); println!("Glyph ID: {:?}", glyph.id()); // Scale and position the glyph let scaled_glyph = glyph.scaled(Scale::uniform(32.0)); let positioned_glyph = scaled_glyph.positioned(point(100.0, 100.0)); // Get horizontal metrics let h_metrics = positioned_glyph.unpositioned().h_metrics(); println!("Advance width: {}", h_metrics.advance_width); println!("Left side bearing: {}", h_metrics.left_side_bearing); ``` -------------------------------- ### Configure and Build GPU Glyph Cache Source: https://context7.com/redox-os/rusttype/llms.txt Demonstrates how to initialize a GPU cache using the builder pattern. It covers setting dimensions, tolerances, and performance options like multithreading. ```rust use rusttype::gpu_cache::Cache; let cache = Cache::builder() .dimensions(1024, 1024) .scale_tolerance(0.1) .position_tolerance(0.1) .pad_glyphs(true) .align_4x4(false) .multithread(true) .build(); println!("Cache dimensions: {:?}", cache.dimensions()); ``` -------------------------------- ### Queue Glyphs for GPU Caching Source: https://context7.com/redox-os/rusttype/llms.txt Shows how to layout text and queue individual glyphs into the cache. This step is required before processing the cache update. ```rust use rusttype::{Font, Scale, point}; use rusttype::gpu_cache::Cache; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let mut cache = Cache::builder().dimensions(512, 512).build(); let scale = Scale::uniform(24.0); let v_metrics = font.v_metrics(scale); for glyph in font.layout("Hello GPU!", scale, point(0.0, v_metrics.ascent)) { cache.queue_glyph(0, glyph); } println!("Glyphs queued for caching"); ``` -------------------------------- ### Manual Glyph Layout and Kerning Source: https://context7.com/redox-os/rusttype/llms.txt Demonstrates how to convert characters to glyphs and manually apply kerning adjustments between pairs while positioning them along a baseline. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); // Get glyphs for specific characters let chars = ['H', 'e', 'l', 'l', 'o']; let glyphs: Vec<_> = font.glyphs_for(chars.iter().copied()).collect(); // Manual layout with kerning let scale = Scale::uniform(32.0); let mut caret = 0.0; let mut last_glyph_id = None; for glyph in glyphs { let scaled = glyph.scaled(scale); // Apply kerning if let Some(last_id) = last_glyph_id { caret += font.pair_kerning(scale, last_id, scaled.id()); } let positioned = scaled.positioned(point(caret, 32.0)); caret += positioned.unpositioned().h_metrics().advance_width; last_glyph_id = Some(positioned.id()); println!("Glyph at x={:.1}", positioned.position().x); } ``` -------------------------------- ### Point and Vector Creation and Arithmetic in Rust Source: https://context7.com/redox-os/rusttype/llms.txt Demonstrates how to create and manipulate 2D points and vectors using the `point` and `vector` functions. Supports arithmetic operations between points and vectors, and vectors with scalars. ```rust use rusttype::{point, vector, Point, Vector}; // Create points let origin: Point = point(0.0, 0.0); let position: Point = point(100.5, 200.3); // Create vectors let offset: Vector = vector(10.0, -5.0); let scale_vec: Vector = vector(2.0, 2.0); // Point arithmetic let moved = position + offset; // Point + Vector = Point let difference = position - origin; // Point - Point = Vector // Vector arithmetic let doubled = offset * 2.0; // Vector * scalar let combined = offset + vector(5.0, 5.0); // Vector + Vector println!("Moved to: ({}, {})", moved.x, moved.y); println!("Distance vector: ({}, {})", difference.x, difference.y); ``` -------------------------------- ### Positioning a Scaled Glyph in RustType Source: https://context7.com/redox-os/rusttype/llms.txt Demonstrates how to scale a glyph and position it at specific coordinates. It also shows how to retrieve the pixel bounding box for the positioned glyph. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('g') .scaled(Scale::uniform(32.0)) .positioned(point(10.5, 25.0)); // Sub-pixel positioning supported // Get the pixel bounding box if let Some(bb) = glyph.pixel_bounding_box() { println!("Bounding box: ({}, {}) to ({}, {})", bb.min.x, bb.min.y, bb.max.x, bb.max.y); println!("Size: {}x{} pixels", bb.width(), bb.height()); } ``` -------------------------------- ### Laying Out Text with Font::layout Source: https://context7.com/redox-os/rusttype/llms.txt Shows how to lay out a string of text horizontally, accounting for font metrics and kerning. It returns an iterator of positioned glyphs ready for rendering. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let scale = Scale::uniform(24.0); let v_metrics = font.v_metrics(scale); // Position text with baseline at y=ascent (so top of text is at y=0) let start = point(20.0, 20.0 + v_metrics.ascent); let glyphs: Vec<_> = font.layout("Hello, World!", scale, start).collect(); // Calculate total text width let text_width = glyphs.iter() .filter_map(|g| g.pixel_bounding_box()) .map(|bb| bb.max.x) .max() .unwrap_or(0); println!("Laid out {} glyphs, width: {} pixels", glyphs.len(), text_width); ``` -------------------------------- ### Rectangle Type for Bounding Boxes in Rust Source: https://context7.com/redox-os/rusttype/llms.txt Illustrates the usage of the `Rect` type for defining rectangular areas using minimum and maximum corner points. Includes methods to calculate width and height. ```rust use rusttype::{point, Rect}; // Create a rectangle let rect: Rect = Rect { min: point(10, 20), max: point(100, 80), }; println!("Width: {}, Height: {}", rect.width(), rect.height()); println!("Top-left: ({}, {})", rect.min.x, rect.min.y); println!("Bottom-right: ({}, {})", rect.max.x, rect.max.y); ``` -------------------------------- ### Load Font from Vec - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Creates a font from owned `Vec` data using `Font::try_from_vec`. This allows the `Font` object to have a `'static` lifetime without borrowing from external data, making it suitable for fonts loaded at runtime. It returns `None` if the font data is invalid. ```rust use rusttype::Font; use std::fs; // Load font data at runtime let font_data: Vec = fs::read("path/to/font.ttf") .expect("Failed to read font file"); let font: Font<'static> = Font::try_from_vec(font_data) .expect("Error constructing Font from vector"); // Font owns its data and can be moved freely println!("Loaded font with {} glyphs", font.glyph_count()); ``` -------------------------------- ### Retrieving Exact Glyph Bounding Boxes Source: https://context7.com/redox-os/rusttype/llms.txt Calculates the precise floating-point bounding box for a glyph shape, useful for collision detection or advanced layout calculations. ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('Q').scaled(Scale::uniform(100.0)); if let Some(bb) = glyph.exact_bounding_box() { println!("Exact bounds: ({:.2}, {:.2}) to ({:.2}, {:.2})", bb.min.x, bb.min.y, bb.max.x, bb.max.y); println!("Exact size: {:.2} x {:.2}", bb.width(), bb.height()); } ``` -------------------------------- ### Font Loading API Source: https://context7.com/redox-os/rusttype/llms.txt APIs for loading font data from various sources like byte slices, vectors, or font collections. ```APIDOC ## Font Loading ### Font::try_from_bytes Loads a font from a byte slice, returning a `Font` that borrows from the input data. Returns `None` if the data is invalid. ### Method `Font::try_from_bytes` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::Font; // Load font from embedded bytes (compile-time) let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font: Font<'static> = Font::try_from_bytes(font_data) .expect("Error constructing Font from bytes"); // Font is now ready to use println!("Font has {} glyphs", font.glyph_count()); ``` ### Response #### Success Response (200) - **Font** (Font<'static>) - A loaded font object. #### Response Example None (returns `Font` object directly or `None` on failure) --- ### Font::try_from_vec Creates a font from owned data, allowing the font to have a `'static` lifetime without borrowing from external data. ### Method `Font::try_from_vec` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::Font; use std::fs; // Load font data at runtime let font_data: Vec = fs::read("path/to/font.ttf") .expect("Failed to read font file"); let font: Font<'static> = Font::try_from_vec(font_data) .expect("Error constructing Font from vector"); // Font owns its data and can be moved freely println!("Loaded font with {} glyphs", font.glyph_count()); ``` ### Response #### Success Response (200) - **Font** (Font<'static>) - A loaded font object. #### Response Example None (returns `Font` object directly or `None` on failure) --- ### Font::try_from_bytes_and_index Loads a specific font from a font collection file (`.ttc`) by index. ### Method `Font::try_from_bytes_and_index` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::Font; let font_collection_data: &[u8] = include_bytes!("path/to/fonts.ttc"); // Load the second font in the collection (index 1) let font = Font::try_from_bytes_and_index(font_collection_data, 1) .expect("Error loading font at index 1"); println!("Font glyph count: {}", font.glyph_count()); ``` ### Response #### Success Response (200) - **Font** (Font) - The font object at the specified index. #### Response Example None (returns `Font` object directly or `None` on failure) ``` -------------------------------- ### Process and Upload Cached Glyph Data Source: https://context7.com/redox-os/rusttype/llms.txt Processes the queue and provides a callback to upload pixel data to the GPU texture. This is the primary mechanism for updating the texture atlas. ```rust use rusttype::{Font, Scale, point, Rect}; use rusttype::gpu_cache::Cache; let mut cache = Cache::builder().dimensions(512, 512).build(); cache.cache_queued(|rect: Rect, data: &[u8]| { println!("Upload {}x{} pixels at ({}, {})", rect.width(), rect.height(), rect.min.x, rect.min.y); }).expect("Failed to cache glyphs"); ``` -------------------------------- ### Rasterizing Glyphs with PositionedGlyph::draw Source: https://context7.com/redox-os/rusttype/llms.txt Explains how to rasterize a positioned glyph by providing a closure that processes pixel coverage values. This is useful for generating alpha masks for font rendering. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('R') .scaled(Scale::uniform(48.0)) .positioned(point(0.0, 48.0)); if let Some(bb) = glyph.pixel_bounding_box() { let width = bb.width() as usize; let height = bb.height() as usize; let mut pixels = vec![0u8; width * height]; // Rasterize the glyph glyph.draw(|x, y, coverage| { let alpha = (coverage * 255.0) as u8; pixels[y as usize * width + x as usize] = alpha; }); // pixels now contains the alpha channel for the glyph println!("Rasterized {}x{} pixels", width, height); } ``` -------------------------------- ### Calculate Pixel Bounding Box for Glyph Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves the conservative pixel-aligned bounding box for a positioned glyph. This is essential for determining the exact pixel area required to rasterize a glyph on screen. ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('A') .scaled(Scale::uniform(48.0)) .positioned(point(10.3, 50.7)); // Sub-pixel position if let Some(bb) = glyph.pixel_bounding_box() { println!("Pixel bounds: ({}, {}) to ({}, {})", bb.min.x, bb.min.y, bb.max.x, bb.max.y); println!("Pixel size: {} x {}", bb.width(), bb.height()); } ``` -------------------------------- ### Load Font from Collection - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Loads a specific font from a font collection file (`.ttc`) by its index using `Font::try_from_bytes_and_index`. This is useful when a single collection file contains multiple fonts. Returns `None` if the index is out of bounds or the data is invalid. ```rust use rusttype::Font; let font_collection_data: &[u8] = include_bytes!("path/to/fonts.ttc"); // Load the second font in the collection (index 1) let font = Font::try_from_bytes_and_index(font_collection_data, 1) .expect("Error loading font at index 1"); println!("Font glyph count: {}", font.glyph_count()); ``` -------------------------------- ### Retrieve Texture Coordinates for Rendering Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves the UV texture coordinates and screen-space rectangles for cached glyphs. This data is used to construct vertex buffers for rendering. ```rust use rusttype::{Font, Scale, point}; use rusttype::gpu_cache::Cache; let mut cache = Cache::builder().dimensions(512, 512).build(); // ... queue and cache_queued steps ... for glyph in &glyphs { match cache.rect_for(0, glyph) { Ok(Some((uv_rect, screen_rect))) => { println!("UV: ({:.3}, {:.3}) to ({:.3}, {:.3})", uv_rect.min.x, uv_rect.min.y, uv_rect.max.x, uv_rect.max.y); } Ok(None) => println!("Empty glyph"), Err(e) => println!("Glyph not cached: {:?}", e), } } ``` -------------------------------- ### Glyph Operations API Source: https://context7.com/redox-os/rusttype/llms.txt APIs for retrieving and manipulating glyphs, including scaling and positioning. ```APIDOC ## Glyph Operations ### Font::glyph Retrieves a glyph for a character or glyph ID. Missing characters return the `.notdef` glyph (id 0). ### Method `Font::glyph` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::{Font, Scale, point}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); // Get a glyph from a character let glyph = font.glyph('A'); println!("Glyph ID: {:?}", glyph.id()); // Scale and position the glyph let scaled_glyph = glyph.scaled(Scale::uniform(32.0)); let positioned_glyph = scaled_glyph.positioned(point(100.0, 100.0)); // Get horizontal metrics let h_metrics = positioned_glyph.unpositioned().h_metrics(); println!("Advance width: {}", h_metrics.advance_width); println!("Left side bearing: {}", h_metrics.left_side_bearing); ``` ### Response #### Success Response (200) - **Glyph** (Glyph) - The requested glyph object. #### Response Example None (returns `Glyph` object directly) --- ### Glyph::scaled Augments a glyph with scaling information, enabling access to metrics that depend on size. ### Method `Glyph::scaled` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('W'); // Uniform scaling (same x and y) let scaled = glyph.clone().scaled(Scale::uniform(48.0)); println!("Scale: {:?}", scaled.scale()); // Non-uniform scaling (different x and y for stretched text) let stretched = glyph.scaled(Scale { x: 48.0, y: 32.0 }); let metrics = stretched.h_metrics(); println!("Advance width: {}", metrics.advance_width); ``` ### Response #### Success Response (200) - **ScaledGlyph** (ScaledGlyph) - The glyph with scaling information applied. #### Response Example None (returns `ScaledGlyph` object directly) ``` -------------------------------- ### Scale Glyph Metrics - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Augments a glyph with scaling information using `Glyph::scaled`. This allows access to metrics that are dependent on the font size, such as advance width and side bearings. Supports both uniform scaling (same factor for x and y) and non-uniform scaling (different factors for x and y). ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let glyph = font.glyph('W'); // Uniform scaling (same x and y) let scaled = glyph.clone().scaled(Scale::uniform(48.0)); println!("Scale: {:?}", scaled.scale()); // Non-uniform scaling (different x and y for stretched text) let stretched = glyph.scaled(Scale { x: 48.0, y: 32.0 }); let metrics = stretched.h_metrics(); println!("Advance width: {}", metrics.advance_width); ``` -------------------------------- ### Load Font from Bytes - RustType Source: https://context7.com/redox-os/rusttype/llms.txt Loads a font from a byte slice using `Font::try_from_bytes`. This method is suitable for embedded font data and requires the input data to remain valid for the lifetime of the `Font` object. It returns `None` if the font data is invalid. ```rust use rusttype::Font; // Load font from embedded bytes (compile-time) let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font: Font<'static> = Font::try_from_bytes(font_data) .expect("Error constructing Font from bytes"); // Font is now ready to use println!("Font has {} glyphs", font.glyph_count()); ``` -------------------------------- ### Calculating Pair Kerning Source: https://context7.com/redox-os/rusttype/llms.txt Retrieves the kerning adjustment value between two specific glyphs, which is essential for professional-looking text spacing. ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let scale = Scale::uniform(32.0); // Check kerning between character pairs let pairs = [('A', 'V'), ('T', 'o'), ('W', 'A'), ('H', 'I')]; for (a, b) in pairs { let kern = font.pair_kerning(scale, a, b); if kern != 0.0 { println!("Kerning '{}{}': {:.2} pixels", a, b, kern); } } ``` -------------------------------- ### Font Metrics API Source: https://context7.com/redox-os/rusttype/llms.txt APIs for retrieving font metrics such as vertical metrics and units per EM. ```APIDOC ## Font Metrics ### Font::v_metrics Returns vertical metrics (ascent, descent, line gap) for the font at a given scale, essential for proper text layout. ### Method `Font::v_metrics` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::{Font, Scale}; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let scale = Scale::uniform(24.0); let v_metrics = font.v_metrics(scale); println!("Ascent: {}", v_metrics.ascent); // Distance above baseline println!("Descent: {}", v_metrics.descent); // Distance below baseline (negative) println!("Line gap: {}", v_metrics.line_gap); // Calculate line height for multi-line text let line_height = v_metrics.ascent - v_metrics.descent + v_metrics.line_gap; println!("Total line height: {}", line_height); ``` ### Response #### Success Response (200) - **v_metrics** (VMetrics) - An object containing ascent, descent, and line_gap. #### Response Example ```json { "ascent": 19.0, "descent": -5.0, "line_gap": 2.0 } ``` --- ### Font::units_per_em Returns the units per EM square, useful for converting between font units and pixels. ### Method `Font::units_per_em` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Request Example ```rust use rusttype::Font; let font_data: &[u8] = include_bytes!("path/to/font.ttf"); let font = Font::try_from_bytes(font_data).unwrap(); let units_per_em = font.units_per_em(); println!("Units per EM: {}", units_per_em); // Typically 1000 or 2048 ``` ### Response #### Success Response (200) - **units_per_em** (u16) - The number of font units in the EM square. #### Response Example ```json { "units_per_em": 2048 } ``` ``` === COMPLETE CONTENT === This response contains all available snippets from this library. No additional content exists. Do not make further requests.