diff --git a/solitaire_app/src/main.rs b/solitaire_app/src/main.rs index 076c860..47ff8d3 100644 --- a/solitaire_app/src/main.rs +++ b/solitaire_app/src/main.rs @@ -100,6 +100,19 @@ fn main() { .set(bevy::asset::AssetPlugin { file_path: "../assets".to_string(), ..default() + }) + // The bundled hayeah card SVGs declare `font-family="Arial"` + // for rank/suit text. usvg compares family names exactly, + // so on systems without Arial installed (every Linux + // distro by default) it bridges a `log::warn!` per text + // node into our tracing output — 50+ lines per game on + // launch. The substitution path in `svg_loader::shared_fontdb` + // already resolves the glyphs to whatever sans-serif the + // user does have; the warn is purely informational and + // dropping it leaves real errors visible. + .set(bevy::log::LogPlugin { + filter: format!("{},usvg::text=error", bevy::log::DEFAULT_FILTER), + ..default() }), ) .add_plugins(AssetSourcesPlugin) diff --git a/solitaire_engine/src/assets/svg_loader.rs b/solitaire_engine/src/assets/svg_loader.rs index 1455aed..ec977ab 100644 --- a/solitaire_engine/src/assets/svg_loader.rs +++ b/solitaire_engine/src/assets/svg_loader.rs @@ -19,6 +19,8 @@ //! loading via `load_with_settings(...)`. The default of 512×768 is a //! safe fallback that fits a typical 2:3 playing card. +use std::sync::{Arc, OnceLock}; + use bevy::asset::io::Reader; use bevy::asset::{AssetLoader, LoadContext, RenderAssetUsages}; use bevy::image::Image; @@ -27,6 +29,7 @@ use bevy::reflect::TypePath; use bevy::render::render_resource::{Extent3d, TextureDimension, TextureFormat}; use serde::{Deserialize, Serialize}; use thiserror::Error; +use usvg::fontdb; /// Per-asset settings consumed by [`SvgLoader::load`]. /// @@ -102,7 +105,10 @@ impl AssetLoader for SvgLoader { /// thumbnail generators) can rasterise without going through the /// asset graph. pub fn rasterize_svg(svg_bytes: &[u8], target: UVec2) -> Result { - let opt = usvg::Options::default(); + let opt = usvg::Options { + fontdb: shared_fontdb(), + ..Default::default() + }; let tree = usvg::Tree::from_data(svg_bytes, &opt)?; let svg_size = tree.size(); @@ -140,6 +146,27 @@ pub fn rasterize_svg(svg_bytes: &[u8], target: UVec2) -> Result Arc { + static DB: OnceLock> = OnceLock::new(); + DB.get_or_init(|| { + let mut db = fontdb::Database::new(); + db.load_system_fonts(); + Arc::new(db) + }) + .clone() +} + #[cfg(test)] mod tests { use super::*;