diff --git a/modules/juce_graphics/detail/juce_SimpleShapedText.cpp b/modules/juce_graphics/detail/juce_SimpleShapedText.cpp index cdc626ac31..2b115a4d2f 100644 --- a/modules/juce_graphics/detail/juce_SimpleShapedText.cpp +++ b/modules/juce_graphics/detail/juce_SimpleShapedText.cpp @@ -494,19 +494,19 @@ static auto makeSpan (T& array) return Span { array.getRawDataPointer(), (size_t) array.size() }; } -static std::vector findSuitableFontsForText (const Font& font, - const String& text, - const String& language = {}) +static detail::RangedValues findSuitableFontsForText (const Font& font, + const String& text, + const String& language = {}) { detail::RangedValues> fonts; fonts.set ({ 0, (int64) text.length() }, font); const auto getResult = [&] { - std::vector result; + detail::RangedValues result; for (const auto [r, v] : fonts) - result.emplace_back (r, v.value_or (font)); + result.set (r, v.value_or (font)); return result; }; @@ -540,7 +540,7 @@ static std::vector findSuitableFontsForText (const Font& font, // can't find any more suitable fonts or all codepoints have one for (auto numMissingGlyphs = markMissingGlyphs(); numMissingGlyphs > 0;) { - std::vector changes; + std::vector, Font>> changes; for (const auto [r, f] : fonts) { @@ -575,10 +575,8 @@ static RangedValues resolveFontsWithFallback (const String& string, const auto rf = findSuitableFontsForText (f, string.substring ((int) r.getStart(), (int) std::min (r.getEnd(), (int64) string.length()))); - for (auto& item : rf) - item.first += r.getStart(); - - resolved.setForEach (rf.begin(), rf.end()); + for (const auto [subRange, font] : rf) + resolved.set (subRange + r.getStart(), font); } return resolved; @@ -785,16 +783,11 @@ private: }; template -static auto createRangedValues (const std::vector, T>>& pairs, int64 offset = 0) +static auto rangedValuesWithOffset (detail::RangedValues rv, int64 offset = 0) { - detail::RangedValues result; - - for (const auto& [range, value] : pairs) - result.insert (range.movedToStartAt (range.getStart() - offset), value); - - result.eraseUpTo (0); - - return result; + rv.shift (std::numeric_limits::min(), -offset); + rv.eraseUpTo (0); + return rv; } struct Shaper @@ -819,8 +812,8 @@ struct Shaper const auto bidiLevels = bidiParagraph.getResolvedLevels(); const auto fonts = resolveFontsWithFallback (string, - createRangedValues (options.getFontsForRange(), - shapingRange.getStart())); + rangedValuesWithOffset (options.getFontsForRange(), + shapingRange.getStart())); for (Unicode::LineBreakIterator lineIter { makeSpan (analysis) }; auto lineRun = lineIter.next();) { diff --git a/modules/juce_graphics/detail/juce_SimpleShapedText.h b/modules/juce_graphics/detail/juce_SimpleShapedText.h index b2c59446a6..5c0b7efd33 100644 --- a/modules/juce_graphics/detail/juce_SimpleShapedText.h +++ b/modules/juce_graphics/detail/juce_SimpleShapedText.h @@ -35,8 +35,6 @@ namespace juce::detail { -using FontForRange = std::pair, Font>; - /** Types of text direction. This may also be applied to characters. */ enum class TextDirection { @@ -64,12 +62,13 @@ public: [[nodiscard]] ShapedTextOptions withFont (Font x) const { - return withMember (*this, &ShapedTextOptions::fontsForRange, - std::vector { { { 0, std::numeric_limits::max() }, - x } }); + RangedValues fonts; + fonts.set ({ 0, std::numeric_limits::max() }, x); + + return withMember (*this, &ShapedTextOptions::fontsForRange, std::move (fonts)); } - [[nodiscard]] ShapedTextOptions withFontsForRange (const std::vector& x) const + [[nodiscard]] ShapedTextOptions withFonts (const detail::RangedValues& x) const { return withMember (*this, &ShapedTextOptions::fontsForRange, x); } @@ -151,8 +150,14 @@ private: std::optional readingDir; std::optional maxWidth; std::optional height; - std::vector fontsForRange { { { 0, std::numeric_limits::max() }, - FontOptions { 15.0f } } }; + + detail::RangedValues fontsForRange = std::invoke ([&] + { + detail::RangedValues result; + result.set ({ 0, std::numeric_limits::max() }, FontOptions { 15.0f }); + return result; + }); + String language = SystemStats::getDisplayLanguage(); float firstLineIndent = 0.0f; float leading = 1.0f; diff --git a/modules/juce_graphics/fonts/juce_TextLayout.cpp b/modules/juce_graphics/fonts/juce_TextLayout.cpp index 2c6dd56422..58bf43d440 100644 --- a/modules/juce_graphics/fonts/juce_TextLayout.cpp +++ b/modules/juce_graphics/fonts/juce_TextLayout.cpp @@ -325,23 +325,6 @@ static auto castTo (const Range& r) return Range (static_cast (r.getStart()), static_cast (r.getEnd())); } -static auto getFontsForRange (const detail::RangedValues& fonts) -{ - using namespace detail; - - std::vector result; - result.reserve (fonts.size()); - - std::transform (fonts.begin(), - fonts.end(), - std::back_inserter (result), - [] (auto entry) { - return FontForRange { entry.range, entry.value }; - }); - - return result; -} - static Range getInputRange (const detail::ShapedText& st, Range glyphRange) { if (glyphRange.isEmpty()) @@ -425,7 +408,7 @@ void TextLayout::createStandardLayout (const AttributedString& text) colours.set (range, attribute.colour); } - auto shapedTextOptions = ShapedTextOptions{}.withFontsForRange (getFontsForRange (fonts)) + auto shapedTextOptions = ShapedTextOptions{}.withFonts (fonts) .withLanguage (SystemStats::getUserLanguage()) .withTrailingWhitespacesShouldFit (false) .withJustification (justification)