diff --git a/implementations/Crafter.Graphics-FontAtlas.cpp b/implementations/Crafter.Graphics-FontAtlas.cpp index 180a402..c3479a7 100644 --- a/implementations/Crafter.Graphics-FontAtlas.cpp +++ b/implementations/Crafter.Graphics-FontAtlas.cpp @@ -74,8 +74,12 @@ bool FontAtlas::ShelfPlace(int w, int h, int& outX, int& outY) { } bool FontAtlas::Ensure(Font& font, std::uint32_t codepoint) { + return EnsureAndGet(font, codepoint) != nullptr; +} + +const Glyph* FontAtlas::EnsureAndGet(Font& font, std::uint32_t codepoint) { Key key{&font, codepoint}; - if (cache_.contains(key)) return true; + if (auto it = cache_.find(key); it != cache_.end()) return &it->second; float fontScale = stbtt_ScaleForPixelHeight(&font.font, kBaseSize); @@ -98,7 +102,7 @@ bool FontAtlas::Ensure(Font& font, std::uint32_t codepoint) { int px = 0, py = 0; if (!ShelfPlace(sw, sh, px, py)) { stbtt_FreeSDF(sdf, nullptr); - return false; + return nullptr; } std::uint8_t* dst = PixelPtr(); for (int row = 0; row < sh; ++row) { @@ -119,8 +123,7 @@ bool FontAtlas::Ensure(Font& font, std::uint32_t codepoint) { MarkDirty(px, py, sw, sh); } - cache_.emplace(key, g); - return true; + return &cache_.emplace(key, g).first->second; } const Glyph* FontAtlas::Lookup(Font& font, std::uint32_t codepoint) const { diff --git a/implementations/Crafter.Graphics-UI-Shared.cpp b/implementations/Crafter.Graphics-UI-Shared.cpp index 9e75653..6ac2c62 100644 --- a/implementations/Crafter.Graphics-UI-Shared.cpp +++ b/implementations/Crafter.Graphics-UI-Shared.cpp @@ -75,8 +75,7 @@ std::uint32_t UIRenderer::ShapeText(Font& font, float pxSize, if (cp == 0) break; if (cp == '\n') { continue; } - fontAtlas->Ensure(font, cp); - const Glyph* g = fontAtlas->Lookup(font, cp); + const Glyph* g = fontAtlas->EnsureAndGet(font, cp); if (g == nullptr) continue; if (g->w > 0 && g->h > 0) { diff --git a/interfaces/Crafter.Graphics-FontAtlas.cppm b/interfaces/Crafter.Graphics-FontAtlas.cppm index c695f65..105f011 100644 --- a/interfaces/Crafter.Graphics-FontAtlas.cppm +++ b/interfaces/Crafter.Graphics-FontAtlas.cppm @@ -115,6 +115,11 @@ export namespace Crafter { std::uint8_t* PixelPtr() noexcept; bool Ensure(Font& font, std::uint32_t codepoint); + // Ensure the glyph is in the atlas and return a pointer to it in one + // hash+probe. Returns nullptr only when a brand-new glyph cannot be + // placed (ShelfPlace failure); a glyph with no SDF coverage (e.g. + // space) still returns a valid pointer. + const Glyph* EnsureAndGet(Font& font, std::uint32_t codepoint); const Glyph* Lookup(Font& font, std::uint32_t codepoint) const; void Update(GraphicsCommandBuffer cmd);