| 95 | } |
| 96 | |
| 97 | std::vector<ShapedGlyph> NativeTextShaper::Shape(const std::string& text, |
| 98 | std::shared_ptr<tgfx::Typeface> typeface) { |
| 99 | std::vector<Info> infos = {}; |
| 100 | auto textStart = text.data(); |
| 101 | auto textStop = textStart + text.size(); |
| 102 | while (textStart < textStop) { |
| 103 | auto cluster = static_cast<uint32_t>(textStart - text.data()); |
| 104 | infos.emplace_back(Info{tgfx::UTF::NextUTF8(&textStart, textStop), cluster}); |
| 105 | } |
| 106 | |
| 107 | CheckContinuations(infos); |
| 108 | MergeClusters(infos); |
| 109 | |
| 110 | std::vector<ShapedGlyph> glyphs = {}; |
| 111 | auto fallbackTypefaces = FontManager::GetFallbackTypefaces(); |
| 112 | for (size_t i = 0; i < infos.size(); ++i) { |
| 113 | auto length = (i + 1 == infos.size() ? text.length() : infos[i + 1].cluster) - infos[i].cluster; |
| 114 | if (length == 0) { |
| 115 | continue; |
| 116 | } |
| 117 | auto str = text.substr(infos[i].cluster, length); |
| 118 | auto glyphID = typeface ? typeface->getGlyphID(str) : 0; |
| 119 | if (glyphID == 0) { |
| 120 | for (const auto& faceHolder : fallbackTypefaces) { |
| 121 | auto face = faceHolder->getTypeface(); |
| 122 | glyphID = face->getGlyphID(str); |
| 123 | if (glyphID != 0) { |
| 124 | glyphs.emplace_back(std::move(face), glyphID, infos[i].cluster); |
| 125 | break; |
| 126 | } |
| 127 | } |
| 128 | } else { |
| 129 | glyphs.emplace_back(typeface, typeface->getGlyphID(str), infos[i].cluster); |
| 130 | } |
| 131 | } |
| 132 | return glyphs; |
| 133 | } |
| 134 | } // namespace pag |
nothing calls this directly
no test coverage detected