void GlyphArrangement::addCurtailedLineOfText (const Font& font, const String& text, const float xOffset, const float yOffset, const float maxWidthPixels, const bool useEllipsis) { if (text.isNotEmpty()) { Array<int> newGlyphs; Array<float> xOffsets; font.getGlyphPositions (text, newGlyphs, xOffsets); const int textLen = newGlyphs.size(); glyphs.ensureStorageAllocated (glyphs.size() + textLen); String::CharPointerType t (text.getCharPointer()); for (int i = 0; i < textLen; ++i) { const float nextX = xOffsets.getUnchecked (i + 1); if (nextX > maxWidthPixels + 1.0f) { // curtail the string if it's too wide.. if (useEllipsis && textLen > 3 && glyphs.size() >= 3) insertEllipsis (font, xOffset + maxWidthPixels, 0, glyphs.size()); break; } else { const float thisX = xOffsets.getUnchecked (i); const bool isWhitespace = t.isWhitespace(); glyphs.add (PositionedGlyph (font, t.getAndAdvance(), newGlyphs.getUnchecked(i), xOffset + thisX, yOffset, nextX - thisX, isWhitespace)); } } } }
int GlyphArrangement::insertEllipsis (const Font& font, const float maxXPos, const int startIndex, int endIndex) { int numDeleted = 0; if (glyphs.size() > 0) { Array<int> dotGlyphs; Array<float> dotXs; font.getGlyphPositions ("..", dotGlyphs, dotXs); const float dx = dotXs[1]; float xOffset = 0.0f, yOffset = 0.0f; while (endIndex > startIndex) { const PositionedGlyph& pg = glyphs.getReference (--endIndex); xOffset = pg.x; yOffset = pg.y; glyphs.remove (endIndex); ++numDeleted; if (xOffset + dx * 3 <= maxXPos) break; } for (int i = 3; --i >= 0;) { glyphs.insert (endIndex++, PositionedGlyph (font, '.', dotGlyphs.getFirst(), xOffset, yOffset, dx, false)); --numDeleted; xOffset += dx; if (xOffset > maxXPos) break; } } return numDeleted; }