@@ -20,10 +20,22 @@ use graphene_std::vector::{PointId, SegmentId, Vector};
2020use kurbo:: { self , BezPath , ParamCurve } ;
2121use kurbo:: { Affine , PathSeg } ;
2222use std:: collections:: HashMap ;
23- use std:: sync:: { Arc , Mutex , MutexGuard } ;
23+ use std:: sync:: { Arc , LazyLock , Mutex , MutexGuard } ;
2424use vello:: Scene ;
2525use vello:: peniko;
2626
27+ // Global lazy initialized font cache and text context
28+ static GLOBAL_FONT_CACHE : LazyLock < FontCache > = LazyLock :: new ( || {
29+ let mut font_cache = FontCache :: default ( ) ;
30+ // Initialize with the hardcoded font used by overlay text
31+ const FONT_DATA : & [ u8 ] = include_bytes ! ( "source-sans-pro-regular.ttf" ) ;
32+ let font = Font :: new ( "Source Sans Pro" . to_string ( ) , "Regular" . to_string ( ) ) ;
33+ font_cache. insert ( font, String :: new ( ) , FONT_DATA . to_vec ( ) ) ;
34+ font_cache
35+ } ) ;
36+
37+ static GLOBAL_TEXT_CONTEXT : LazyLock < Mutex < TextContext > > = LazyLock :: new ( || Mutex :: new ( TextContext :: default ( ) ) ) ;
38+
2739pub type OverlayProvider = fn ( OverlayContext ) -> Message ;
2840
2941pub fn empty_provider ( ) -> OverlayProvider {
@@ -412,8 +424,6 @@ pub(super) struct OverlayContextInternal {
412424 size : DVec2 ,
413425 device_pixel_ratio : f64 ,
414426 visibility_settings : OverlaysVisibilitySettings ,
415- font_cache : FontCache ,
416- thread_text : TextContext ,
417427}
418428
419429impl Default for OverlayContextInternal {
@@ -424,19 +434,11 @@ impl Default for OverlayContextInternal {
424434
425435impl OverlayContextInternal {
426436 pub ( super ) fn new ( size : DVec2 , device_pixel_ratio : f64 , visibility_settings : OverlaysVisibilitySettings ) -> Self {
427- let mut font_cache = FontCache :: default ( ) ;
428- // Initialize with the hardcoded font used by overlay text
429- const FONT_DATA : & [ u8 ] = include_bytes ! ( "source-sans-pro-regular.ttf" ) ;
430- let font = Font :: new ( "Source Sans Pro" . to_string ( ) , "Regular" . to_string ( ) ) ;
431- font_cache. insert ( font, String :: new ( ) , FONT_DATA . to_vec ( ) ) ;
432-
433437 Self {
434438 scene : Scene :: new ( ) ,
435439 size,
436440 device_pixel_ratio,
437441 visibility_settings,
438- font_cache,
439- thread_text : TextContext :: default ( ) ,
440442 }
441443 }
442444
@@ -1031,7 +1033,8 @@ impl OverlayContextInternal {
10311033 // TODO: Grab this from the node_modules folder (either with `include_bytes!` or ideally at runtime) instead of checking the font file into the repo.
10321034 // TODO: And maybe use the WOFF2 version (if it's supported) for its smaller, compressed file size.
10331035 let font = Font :: new ( "Source Sans Pro" . to_string ( ) , "Regular" . to_string ( ) ) ;
1034- let bounds = self . thread_text . bounding_box ( text, & font, & self . font_cache , typesetting, false ) ;
1036+ let mut text_context = GLOBAL_TEXT_CONTEXT . lock ( ) . expect ( "Failed to lock global text context" ) ;
1037+ let bounds = text_context. bounding_box ( text, & font, & GLOBAL_FONT_CACHE , typesetting, false ) ;
10351038 bounds. x
10361039 }
10371040
@@ -1056,14 +1059,15 @@ impl OverlayContextInternal {
10561059 let font = Font :: new ( "Source Sans Pro" . to_string ( ) , "Regular" . to_string ( ) ) ;
10571060
10581061 // Get text dimensions directly from layout
1059- let text_size = self . thread_text . bounding_box ( text, & font, & self . font_cache , typesetting, false ) ;
1062+ let mut text_context = GLOBAL_TEXT_CONTEXT . lock ( ) . expect ( "Failed to lock global text context" ) ;
1063+ let text_size = text_context. bounding_box ( text, & font, & GLOBAL_FONT_CACHE , typesetting, false ) ;
10601064 let text_width = text_size. x ;
10611065 let text_height = text_size. y ;
10621066 // Create a rect from the size (assuming text starts at origin)
10631067 let text_bounds = kurbo:: Rect :: new ( 0.0 , 0.0 , text_width, text_height) ;
10641068
10651069 // Convert text to vector paths for rendering
1066- let text_table = self . thread_text . to_path ( text, & font, & self . font_cache , typesetting, false ) ;
1070+ let text_table = text_context . to_path ( text, & font, & GLOBAL_FONT_CACHE , typesetting, false ) ;
10671071
10681072 // Calculate position based on pivot
10691073 let mut position = DVec2 :: ZERO ;
0 commit comments