mirror of
https://github.com/zed-industries/zed.git
synced 2025-01-11 13:10:54 +00:00
Implement font fallback in layout_line
Co-authored-by: Max Brunsfeld <max@zed.dev>
This commit is contained in:
parent
6cc9306f00
commit
4249b5687e
1 changed files with 30 additions and 20 deletions
|
@ -13,13 +13,12 @@ use core_foundation::{
|
||||||
array::CFIndex,
|
array::CFIndex,
|
||||||
attributed_string::{CFAttributedStringRef, CFMutableAttributedString},
|
attributed_string::{CFAttributedStringRef, CFMutableAttributedString},
|
||||||
base::{CFRange, TCFType},
|
base::{CFRange, TCFType},
|
||||||
number::CFNumber,
|
|
||||||
string::CFString,
|
string::CFString,
|
||||||
};
|
};
|
||||||
use core_graphics::{
|
use core_graphics::{
|
||||||
base::CGGlyph, color_space::CGColorSpace, context::CGContext, geometry::CGAffineTransform,
|
base::CGGlyph, color_space::CGColorSpace, context::CGContext, geometry::CGAffineTransform,
|
||||||
};
|
};
|
||||||
use core_text::{line::CTLine, string_attributes::kCTFontAttributeName};
|
use core_text::{font::CTFont, line::CTLine, string_attributes::kCTFontAttributeName};
|
||||||
use font_kit::{
|
use font_kit::{
|
||||||
canvas::RasterizationOptions, handle::Handle, hinting::HintingOptions, source::SystemSource,
|
canvas::RasterizationOptions, handle::Handle, hinting::HintingOptions, source::SystemSource,
|
||||||
sources::mem::MemSource,
|
sources::mem::MemSource,
|
||||||
|
@ -91,7 +90,7 @@ impl platform::FontSystem for FontSystem {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn layout_line(&self, text: &str, font_size: f32, runs: &[(usize, RunStyle)]) -> LineLayout {
|
fn layout_line(&self, text: &str, font_size: f32, runs: &[(usize, RunStyle)]) -> LineLayout {
|
||||||
self.0.read().layout_line(text, font_size, runs)
|
self.0.write().layout_line(text, font_size, runs)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn wrap_line(&self, text: &str, font_id: FontId, font_size: f32, width: f32) -> Vec<usize> {
|
fn wrap_line(&self, text: &str, font_id: FontId, font_size: f32, width: f32) -> Vec<usize> {
|
||||||
|
@ -149,6 +148,19 @@ impl FontSystemState {
|
||||||
self.fonts[font_id.0].glyph_for_char(ch)
|
self.fonts[font_id.0].glyph_for_char(ch)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn id_for_font(&mut self, requested_font: font_kit::font::Font) -> FontId {
|
||||||
|
// TODO: don't allocate the postscript name
|
||||||
|
// Note: Coretext always returns a Some option for postscript_name
|
||||||
|
let requested_font_name = requested_font.postscript_name();
|
||||||
|
for (id, font) in self.fonts.iter().enumerate() {
|
||||||
|
if font.postscript_name() == requested_font_name {
|
||||||
|
return FontId(id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
self.fonts.push(requested_font);
|
||||||
|
FontId(self.fonts.len() - 1)
|
||||||
|
}
|
||||||
|
|
||||||
fn rasterize_glyph(
|
fn rasterize_glyph(
|
||||||
&self,
|
&self,
|
||||||
font_id: FontId,
|
font_id: FontId,
|
||||||
|
@ -217,9 +229,12 @@ impl FontSystemState {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn layout_line(&self, text: &str, font_size: f32, runs: &[(usize, RunStyle)]) -> LineLayout {
|
fn layout_line(
|
||||||
let font_id_attr_name = CFString::from_static_string("zed_font_id");
|
&mut self,
|
||||||
|
text: &str,
|
||||||
|
font_size: f32,
|
||||||
|
runs: &[(usize, RunStyle)],
|
||||||
|
) -> LineLayout {
|
||||||
// Construct the attributed string, converting UTF8 ranges to UTF16 ranges.
|
// Construct the attributed string, converting UTF8 ranges to UTF16 ranges.
|
||||||
let mut string = CFMutableAttributedString::new();
|
let mut string = CFMutableAttributedString::new();
|
||||||
{
|
{
|
||||||
|
@ -269,11 +284,6 @@ impl FontSystemState {
|
||||||
kCTFontAttributeName,
|
kCTFontAttributeName,
|
||||||
&font.native_font().clone_with_font_size(font_size as f64),
|
&font.native_font().clone_with_font_size(font_size as f64),
|
||||||
);
|
);
|
||||||
string.set_attribute(
|
|
||||||
cf_range,
|
|
||||||
font_id_attr_name.as_concrete_TypeRef(),
|
|
||||||
&CFNumber::from(font_id.0 as i64),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if utf16_end == utf16_line_len {
|
if utf16_end == utf16_line_len {
|
||||||
|
@ -287,15 +297,15 @@ impl FontSystemState {
|
||||||
|
|
||||||
let mut runs = Vec::new();
|
let mut runs = Vec::new();
|
||||||
for run in line.glyph_runs().into_iter() {
|
for run in line.glyph_runs().into_iter() {
|
||||||
let font_id = FontId(
|
let attributes = run.attributes().unwrap();
|
||||||
run.attributes()
|
let font = unsafe {
|
||||||
.unwrap()
|
let native_font = attributes
|
||||||
.get(&font_id_attr_name)
|
.get(kCTFontAttributeName)
|
||||||
.downcast::<CFNumber>()
|
.downcast::<CTFont>()
|
||||||
.unwrap()
|
.unwrap();
|
||||||
.to_i64()
|
font_kit::font::Font::from_native_font(native_font)
|
||||||
.unwrap() as usize,
|
};
|
||||||
);
|
let font_id = self.id_for_font(font);
|
||||||
|
|
||||||
let mut ix_converter = StringIndexConverter::new(text);
|
let mut ix_converter = StringIndexConverter::new(text);
|
||||||
let mut glyphs = Vec::new();
|
let mut glyphs = Vec::new();
|
||||||
|
|
Loading…
Reference in a new issue