diff --git a/components/gfx/font_context.rs b/components/gfx/font_context.rs index 5621807827f..718e64c7e91 100644 --- a/components/gfx/font_context.rs +++ b/components/gfx/font_context.rs @@ -42,7 +42,7 @@ fn create_scaled_font(template: &Arc, pt_size: Au) -> ScaledFo #[cfg(target_os="macos")] fn create_scaled_font(template: &Arc, pt_size: Au) -> ScaledFont { - let cgfont = template.ctfont.as_ref().unwrap().copy_to_CGFont(); + let cgfont = template.ctfont().as_ref().unwrap().copy_to_CGFont(); ScaledFont::new(BackendType::Skia, &cgfont, pt_size.to_f32_px()) } diff --git a/components/gfx/platform/macos/font.rs b/components/gfx/platform/macos/font.rs index a6e431407e1..b8474aa6da9 100644 --- a/components/gfx/platform/macos/font.rs +++ b/components/gfx/platform/macos/font.rs @@ -64,7 +64,7 @@ impl FontHandleMethods for FontHandle { Some(s) => s.to_f64_px(), None => 0.0 }; - match *template.ctfont { + match template.ctfont() { Some(ref ctfont) => { Ok(FontHandle { font_data: template.clone(), diff --git a/components/gfx/platform/macos/font_template.rs b/components/gfx/platform/macos/font_template.rs index e5c0c9c194b..e84691971ac 100644 --- a/components/gfx/platform/macos/font_template.rs +++ b/components/gfx/platform/macos/font_template.rs @@ -11,6 +11,7 @@ use serde::de::{Error, Visitor}; use serde::{Deserialize, Deserializer, Serialize, Serializer}; use std::borrow::ToOwned; use std::ops::Deref; +use std::sync::Mutex; use string_cache::Atom; /// Platform specific font representation for mac. @@ -26,7 +27,7 @@ pub struct FontTemplateData { /// When sending a `FontTemplateData` instance across processes, this will be set to `None` on /// the other side, because `CTFont` instances cannot be sent across processes. This is /// harmless, however, because it can always be recreated. - pub ctfont: CachedCTFont, + ctfont: CachedCTFont, pub identifier: Atom, pub font_data: Option> @@ -52,18 +53,27 @@ impl FontTemplateData { }; FontTemplateData { - ctfont: CachedCTFont(ctfont), + ctfont: CachedCTFont(Mutex::new(ctfont)), identifier: identifier.to_owned(), font_data: font_data } } + + /// Retrieves the Core Text font instance, instantiating it if necessary. + pub fn ctfont(&self) -> Option { + let mut ctfont = self.ctfont.lock().unwrap(); + if ctfont.is_none() { + *ctfont = core_text::font::new_from_name(self.identifier.as_slice(), 0.0).ok() + } + ctfont.as_ref().map(|ctfont| (*ctfont).clone()) + } } -pub struct CachedCTFont(Option); +pub struct CachedCTFont(Mutex>); impl Deref for CachedCTFont { - type Target = Option; - fn deref(&self) -> &Option { + type Target = Mutex>; + fn deref(&self) -> &Mutex> { &self.0 } } @@ -84,7 +94,7 @@ impl Deserialize for CachedCTFont { #[inline] fn visit_none(&mut self) -> Result where E: Error { - Ok(CachedCTFont(None)) + Ok(CachedCTFont(Mutex::new(None))) } }