diff options
author | Minh Nguyễn <mxn@1ec5.org> | 2018-02-22 02:04:09 -0800 |
---|---|---|
committer | Minh Nguyễn <mxn@1ec5.org> | 2018-02-22 02:04:09 -0800 |
commit | b3ba998e20ed75c734d21fbcbc02dd7681061a91 (patch) | |
tree | d6975ac3f00d7ac45f053de8942863e32a4b5b82 | |
parent | cf597ab1a157f613e128c74fbd4a30d904f44a8b (diff) | |
download | qtlocation-mapboxgl-b3ba998e20ed75c734d21fbcbc02dd7681061a91.tar.gz |
[core, ios, macos] Restore text-font support in Core Text backend
-rw-r--r-- | platform/darwin/src/local_glyph_rasterizer.mm | 2 | ||||
-rw-r--r-- | platform/darwin/src/shaping.mm | 47 | ||||
-rw-r--r-- | src/mbgl/layout/symbol_layout.cpp | 5 | ||||
-rw-r--r-- | src/mbgl/text/shaping.cpp | 10 | ||||
-rw-r--r-- | src/mbgl/text/shaping.hpp | 7 |
5 files changed, 43 insertions, 28 deletions
diff --git a/platform/darwin/src/local_glyph_rasterizer.mm b/platform/darwin/src/local_glyph_rasterizer.mm index 27276a9495..e0b83f7938 100644 --- a/platform/darwin/src/local_glyph_rasterizer.mm +++ b/platform/darwin/src/local_glyph_rasterizer.mm @@ -66,7 +66,7 @@ public: if (fontHandles.find(fontName) == fontHandles.end()) { // TODO: Make sure these are the right attributes - NSDictionary *fontAttributes = @{ + NSDictionary *fontAttributes = @{ (NSString *)kCTFontSizeAttribute: [NSNumber numberWithFloat:24.0], (NSString *)kCTFontFamilyNameAttribute: [NSString stringWithCharacters:(UniChar*)fontName.data() length:fontName.length()] }; diff --git a/platform/darwin/src/shaping.mm b/platform/darwin/src/shaping.mm index b408752288..203100d078 100644 --- a/platform/darwin/src/shaping.mm +++ b/platform/darwin/src/shaping.mm @@ -17,25 +17,38 @@ using CTLineRefHandle = CFHandle<CTLineRef, CFTypeRef, CFRelease>; #define PTR_OR_ARRAY(name) (name##Ptr ?: name) -float shapeLine(Shaping& shaping, const std::u16string& text, const float y) { +NSDictionary *getAttributes(const FontStack& fontStack) { + NSDictionary *baseFontAttributes = @{ + (NSString *)kCTFontNameAttribute: @(fontStack.front().c_str()), + }; + CTFontDescriptorRef baseDescriptor = CTFontDescriptorCreateWithAttributes((CFDictionaryRef)baseFontAttributes); +// CTFontRef baseFont = CTFontCreateWithFontDescriptor(baseDescriptor, 0.0, NULL); + CTFontRef font = CTFontCreateWithFontDescriptor(baseDescriptor, 0.0, NULL); + return @{ + (NSString *)kCTFontSizeAttribute: @24.0, + (NSString *)kCTFontAttributeName: (__bridge NSFont *)font, + // TODO: Fall back to the rest of the font stack, then the default cascade list. +// (NSString *)kCTFontCascadeListAttribute: (__bridge NSArray *)CTFontCopyDefaultCascadeListForLanguages(baseFont, NULL), + }; +} + +float shapeLine(Shaping& shaping, const std::u16string& text, const float y, const FontStack& fontStack) { float maxLineLength = 0; - NSDictionary *fontAttributes = @{ - (NSString *)kCTFontSizeAttribute: @24.0 - }; + NSDictionary *attrs = getAttributes(fontStack); CFStringRefHandle string(CFStringCreateWithCharacters(NULL, reinterpret_cast<UniChar*>(const_cast<char16_t*>(text.c_str())), text.length())); - CFAttributedStringRef attrStr = CFAttributedStringCreate(NULL, *string, (CFDictionaryRef)fontAttributes); + CFAttributedStringRef attrStr = CFAttributedStringCreate(NULL, *string, (CFDictionaryRef)attrs); CTLineRef line = CTLineCreateWithAttributedString(attrStr); CFArrayRef runs = CTLineGetGlyphRuns(line); CGSize runAdvance = CGSizeZero; - for (CFIndex i = 0; i < CFArrayGetCount(runs); i++) { + for (CFIndex i = 0; i < CFArrayGetCount(runs); i++) { CTRunRef run = (CTRunRef)CFArrayGetValueAtIndex(runs, i); - CFDictionaryRef attrs = CTRunGetAttributes(run); + CFDictionaryRef runAttrs = CTRunGetAttributes(run); - CTFontRef fontRef = (CTFontRef)CFDictionaryGetValue(attrs, CFSTR("NSFont")); + CTFontRef fontRef = (CTFontRef)CFDictionaryGetValue(runAttrs, CFSTR("NSFont")); CFStringRef fontNameRef = CTFontCopyName(fontRef, kCTFontFamilyNameKey); CFIndex length = CFStringGetLength(fontNameRef); UniChar* buffer = (UniChar*)malloc(length * sizeof(UniChar)); @@ -52,7 +65,7 @@ float shapeLine(Shaping& shaping, const std::u16string& text, const float y) { CTRunGetGlyphs(run, CFRangeMake(0, 0), runGlyphs); } - NSDictionary* nsAttrs = (__bridge NSDictionary*)attrs; + NSDictionary* nsAttrs = (__bridge NSDictionary*)runAttrs; CTFontRef runFont = CTFontCreateWithName(fontNameRef, [nsAttrs[@"NSFontSizeAttribute"] doubleValue], NULL); CGRect boundingRects[runGlyphCount]; @@ -67,7 +80,7 @@ float shapeLine(Shaping& shaping, const std::u16string& text, const float y) { shaping.positionedGlyphs.emplace_back(GlyphID(fontName, PTR_OR_ARRAY(runGlyphs)[j]), runAdvance.width, y - CGRectGetHeight(frame), false); runAdvance.width += advances[j].width; runAdvance.height += advances[j].height; - maxLineLength = std::max<float>(maxLineLength, frame.origin.x + frame.size.width); + maxLineLength = std::max<float>(maxLineLength, CGRectGetMaxX(frame)); } free(runGlyphs); @@ -75,23 +88,21 @@ float shapeLine(Shaping& shaping, const std::u16string& text, const float y) { return maxLineLength; } -GlyphIDs getGlyphDependencies(const std::u16string& text) { +GlyphIDs getGlyphDependencies(const FontStack& fontStack, const std::u16string& text) { GlyphIDs dependencies; - NSDictionary *fontAttributes = @{ - (NSString *)kCTFontSizeAttribute: @24.0 - }; + NSDictionary *attrs = getAttributes(fontStack); CFStringRefHandle string(CFStringCreateWithCharacters(NULL, reinterpret_cast<UniChar*>(const_cast<char16_t*>(text.c_str())), text.length())); - CFAttributedStringRef attrStr = CFAttributedStringCreate(NULL, *string, (CFDictionaryRef)fontAttributes); + CFAttributedStringRef attrStr = CFAttributedStringCreate(NULL, *string, (CFDictionaryRef)attrs); CTLineRef line = CTLineCreateWithAttributedString(attrStr); CFArrayRef runs = CTLineGetGlyphRuns(line); - for (CFIndex i = 0; i < CFArrayGetCount(runs); i++) { + for (CFIndex i = 0; i < CFArrayGetCount(runs); i++) { CTRunRef run = (CTRunRef)CFArrayGetValueAtIndex(runs, i); - CFDictionaryRef attrs = CTRunGetAttributes(run); + CFDictionaryRef runAttrs = CTRunGetAttributes(run); - CTFontRef fontRef = (CTFontRef)CFDictionaryGetValue(attrs, CFSTR("NSFont")); + CTFontRef fontRef = (CTFontRef)CFDictionaryGetValue(runAttrs, CFSTR("NSFont")); CFStringRef fontNameRef = CTFontCopyName(fontRef, kCTFontFamilyNameKey); CFIndex length = CFStringGetLength(fontNameRef); UniChar* buffer = (UniChar*)malloc(length * sizeof(UniChar)); diff --git a/src/mbgl/layout/symbol_layout.cpp b/src/mbgl/layout/symbol_layout.cpp index edda3b9a8d..37a295341c 100644 --- a/src/mbgl/layout/symbol_layout.cpp +++ b/src/mbgl/layout/symbol_layout.cpp @@ -145,7 +145,7 @@ SymbolLayout::SymbolLayout(const BucketParameters& parameters, FontStack fontStack = layout.evaluate<TextFont>(zoom, ft); GlyphIDs& dependencies = glyphDependencies[fontStack]; - for (GlyphID glyph : getGlyphDependencies(*ft.text)) { + for (GlyphID glyph : getGlyphDependencies(fontStack, *ft.text)) { dependencies.insert(glyph); } @@ -222,7 +222,8 @@ void SymbolLayout::prepare(const GlyphMap& glyphMap, const GlyphPositions& glyph /* verticalHeight */ oneEm, /* writingMode */ writingMode, /* bidirectional algorithm object */ bidi, - /* glyphs */ glyphs); + /* glyphs */ glyphs, + /* fontStack */ fontStack); return result; }; diff --git a/src/mbgl/text/shaping.cpp b/src/mbgl/text/shaping.cpp index ea55e17377..d81e590464 100644 --- a/src/mbgl/text/shaping.cpp +++ b/src/mbgl/text/shaping.cpp @@ -257,7 +257,8 @@ void shapeLines(Shaping& shaping, const style::TextJustifyType textJustify, const float, const WritingModeType, - const Glyphs& glyphs) { + const Glyphs& glyphs, + const FontStack& fontStack) { // the y offset *should* be part of the font metadata const int32_t yOffset = 0;//-17; @@ -281,7 +282,7 @@ void shapeLines(Shaping& shaping, } std::size_t lineStartIndex = shaping.positionedGlyphs.size(); - const float lineLength = shapeLine(shaping, line, y); + const float lineLength = shapeLine(shaping, line, y, fontStack); // Only justify if we placed at least one glyph if (shaping.positionedGlyphs.size() != lineStartIndex) { @@ -318,7 +319,8 @@ const Shaping getShaping(const std::u16string& logicalInput, const float verticalHeight, const WritingModeType writingMode, BiDi& bidi, - const Glyphs& glyphs) { + const Glyphs& glyphs, + const FontStack& fontStack) { Shaping shaping(translate.x, translate.y, writingMode); std::vector<std::u16string> reorderedLines = @@ -326,7 +328,7 @@ const Shaping getShaping(const std::u16string& logicalInput, determineLineBreaks(logicalInput, spacing, maxWidth, writingMode, glyphs)); shapeLines(shaping, reorderedLines, spacing, lineHeight, textAnchor, - textJustify, verticalHeight, writingMode, glyphs); + textJustify, verticalHeight, writingMode, glyphs, fontStack); return shaping; } diff --git a/src/mbgl/text/shaping.hpp b/src/mbgl/text/shaping.hpp index 33f851dc9b..f62a1aa5b4 100644 --- a/src/mbgl/text/shaping.hpp +++ b/src/mbgl/text/shaping.hpp @@ -55,10 +55,11 @@ const Shaping getShaping(const std::u16string& string, float verticalHeight, const WritingModeType, BiDi& bidi, - const Glyphs& glyphs); + const Glyphs& glyphs, + const FontStack& fontStack); // implemented in shaping.mm -GlyphIDs getGlyphDependencies(const std::u16string& string); -float shapeLine(Shaping&, const std::u16string&, const float y); +GlyphIDs getGlyphDependencies(const FontStack& fontStack, const std::u16string& string); +float shapeLine(Shaping&, const std::u16string&, const float y, const FontStack& fontStack); } // namespace mbgl |