diff --git a/modules/juce_graphics/native/juce_mac_Fonts.mm b/modules/juce_graphics/native/juce_mac_Fonts.mm index 4802dc492c..0a9e4f6a01 100644 --- a/modules/juce_graphics/native/juce_mac_Fonts.mm +++ b/modules/juce_graphics/native/juce_mac_Fonts.mm @@ -208,15 +208,51 @@ namespace CoreTextTypeLayout } //============================================================================== + // A flatmap that properly retains/releases font refs + class FontMap + { + public: + void emplace (CTFontRef ctFontRef, Font value) + { + pairs.emplace (std::lower_bound (pairs.begin(), pairs.end(), ctFontRef), ctFontRef, std::move (value)); + } + + const Font* find (CTFontRef ctFontRef) const + { + const auto iter = std::lower_bound (pairs.begin(), pairs.end(), ctFontRef); + + if (iter == pairs.end()) + return nullptr; + + if (iter->key.get() != ctFontRef) + return nullptr; + + return &iter->value; + } + + private: + struct Pair + { + Pair (CTFontRef ref, Font font) : key (ref), value (std::move (font)) { CFRetain (ref); } + + auto operator< (CTFontRef other) const { return key.get() < other; } + + CFUniquePtr key; + Font value; + }; + + std::vector pairs; + }; + struct AttributedStringAndFontMap { CFUniquePtr string; - std::map fontMap; + FontMap fontMap; }; static AttributedStringAndFontMap createCFAttributedString (const AttributedString& text) { - std::map fontMap; + FontMap fontMap; const detail::ColorSpacePtr rgbColourSpace { CGColorSpaceCreateWithName (kCGColorSpaceSRGB) }; @@ -300,7 +336,7 @@ namespace CoreTextTypeLayout struct FramesetterAndFontMap { CFUniquePtr framesetter; - std::map fontMap; + FontMap fontMap; }; static FramesetterAndFontMap createCTFramesetter (const AttributedString& text) @@ -324,7 +360,7 @@ namespace CoreTextTypeLayout struct FrameAndFontMap { CFUniquePtr frame; - std::map fontMap; + FontMap fontMap; }; static FrameAndFontMap createCTFrame (const AttributedString& text, CGRect bounds) @@ -476,10 +512,8 @@ namespace CoreTextTypeLayout { glyphRun->font = [&] { - auto it = frameAndMap.fontMap.find (ctRunFont); - - if (it != frameAndMap.fontMap.end()) - return it->second; + if (auto* it = frameAndMap.fontMap.find (ctRunFont)) + return *it; CFUniquePtr cfsFontName (CTFontCopyPostScriptName (ctRunFont)); CFUniquePtr ctFontRef (CTFontCreateWithName (cfsFontName.get(), referenceFontSize, nullptr));