From b670f799d5e3078477843a044e6fb99a383bbf6f Mon Sep 17 00:00:00 2001 From: ocornut Date: Fri, 29 Nov 2024 15:16:22 +0100 Subject: [PATCH] Fonts: use TexGlyphPadding. Fixed packing issues. Removed old code. --- imgui_draw.cpp | 51 +++++++++++++----------------------------------- imgui_internal.h | 3 +-- 2 files changed, 15 insertions(+), 39 deletions(-) diff --git a/imgui_draw.cpp b/imgui_draw.cpp index 3a9290296..089fc0c5d 100644 --- a/imgui_draw.cpp +++ b/imgui_draw.cpp @@ -3582,7 +3582,6 @@ void ImFontAtlasBuildRepackTexture(ImFontAtlas* atlas, int w, int h) // FIXME-NEWATLAS-TESTS: Test calling RepackTexture with size too small to fits existing rects. -#if 1 // Repack + copy pixels // FIXME-NEWATLAS-V2: Repacking in batch would be beneficial to packing heuristic. ImFontAtlasPackInit(atlas); @@ -3623,27 +3622,6 @@ void ImFontAtlasBuildRepackTexture(ImFontAtlas* atlas, int w, int h) ImFontAtlasBuildUpdateLinesTexData(atlas, false); ImFontAtlasBuildUpdateBasicTexData(atlas, false); -#else - // Copy previous pixels - ImFontAtlasTextureCopyBlock(atlas, old_tex, 0, 0, new_tex, 0, 0, ImMin(old_tex->Width, new_tex->Width), ImMin(old_tex->Height, new_tex->Height)); - - // Scale UV coordinates - // FIXME-NEWATLAS: Probably lossy? - ImVec2 uv_scale((float)old_tex->Width / new_tex->Width, (float)old_tex->Height / new_tex->Height); - for (ImFont* font : atlas->Fonts) - for (ImFontGlyph& glyph : font->Glyphs) - { - glyph.U0 *= uv_scale.x; - glyph.U1 *= uv_scale.x; - glyph.V0 *= uv_scale.y; - glyph.V1 *= uv_scale.y; - } - ImVec4 uv_scale4(uv_scale.x, uv_scale.y, uv_scale.x, uv_scale.y); - atlas->TexUvWhitePixel *= uv_scale; - for (ImVec4& uv : atlas->TexUvLines) - uv = uv * uv_scale4; -#endif - builder->LockDisableResize = false; ImFontAtlasUpdateDrawListsSharedData(atlas); } @@ -3666,8 +3644,9 @@ void ImFontAtlasBuildGrowTexture(ImFontAtlas* atlas, int old_tex_w, int old_tex_ int new_tex_h = (old_tex_h < old_tex_w) ? old_tex_h * 2 : old_tex_h; // Handle minimum size first (for pathologically large packed rects) - new_tex_w = ImMax(new_tex_w, ImUpperPowerOfTwo(builder->MaxRectSize.x + builder->PackPadding)); - new_tex_h = ImMax(new_tex_h, ImUpperPowerOfTwo(builder->MaxRectSize.y + builder->PackPadding)); + const int pack_padding = atlas->TexGlyphPadding; + new_tex_w = ImMax(new_tex_w, ImUpperPowerOfTwo(builder->MaxRectSize.x + pack_padding)); + new_tex_h = ImMax(new_tex_h, ImUpperPowerOfTwo(builder->MaxRectSize.y + pack_padding)); ImFontAtlasBuildRepackTexture(atlas, new_tex_w, new_tex_h); } @@ -3717,10 +3696,7 @@ void ImFontAtlasBuildInit(ImFontAtlas* atlas) const bool builder_is_new = (builder == NULL); if (builder_is_new) - { builder = atlas->Builder = IM_NEW(ImFontAtlasBuilder)(); - builder->PackPadding = 1; - } ImFontAtlasPackInit(atlas); @@ -3762,11 +3738,12 @@ void ImFontAtlasPackInit(ImFontAtlas* atlas) // FIXME-NEWATLAS-V2: Expose other glyph padding settings for custom alteration (e.g. drop shadows). See #7962 // FIXME-NEWATLAS-V2: Experiment with number of nodes. 2024-11-05: Seems to be quite fine to reduce this. - int pack_node_count = tex->Width - builder->PackPadding; + //int pack_padding = atlas->TexGlyphPadding; + int pack_node_count = tex->Width; //pack_node_count *= atlas->_PackNodesFactor; builder->PackNodes.resize(pack_node_count); IM_STATIC_ASSERT(sizeof(stbrp_context) <= sizeof(stbrp_context_opaque)); - stbrp_init_target((stbrp_context*)(void*)&builder->PackContext, tex->Width - builder->PackPadding, tex->Height - builder->PackPadding, builder->PackNodes.Data, builder->PackNodes.Size); + stbrp_init_target((stbrp_context*)(void*)&builder->PackContext, tex->Width, tex->Height, builder->PackNodes.Data, builder->PackNodes.Size); atlas->_PackedSurface = atlas->_PackedRects = 0; builder->MaxRectSize = ImVec2i(0, 0); builder->MaxRectBounds = ImVec2i(0, 0); @@ -3779,6 +3756,7 @@ ImFontAtlasRectId ImFontAtlasPackAddRect(ImFontAtlas* atlas, int w, int h) IM_ASSERT(h > 0 && h <= 0xFFFF); ImFontAtlasBuilder* builder = (ImFontAtlasBuilder*)atlas->Builder; + const int pack_padding = atlas->TexGlyphPadding; builder->MaxRectSize.x = ImMax(builder->MaxRectSize.x, w); builder->MaxRectSize.y = ImMax(builder->MaxRectSize.y, h); @@ -3788,11 +3766,11 @@ ImFontAtlasRectId ImFontAtlasPackAddRect(ImFontAtlas* atlas, int w, int h) { // Try packing stbrp_rect pack_r = {}; - pack_r.w = r.w + builder->PackPadding; - pack_r.h = r.h + builder->PackPadding; + pack_r.w = w + pack_padding; + pack_r.h = h + pack_padding; stbrp_pack_rects((stbrp_context*)(void*)&builder->PackContext, &pack_r, 1); - r.x = (unsigned short)(pack_r.x + builder->PackPadding); - r.y = (unsigned short)(pack_r.y + builder->PackPadding); + r.x = (unsigned short)pack_r.x; + r.y = (unsigned short)pack_r.y; if (pack_r.was_packed) break; @@ -3809,9 +3787,9 @@ ImFontAtlasRectId ImFontAtlasPackAddRect(ImFontAtlas* atlas, int w, int h) ImFontAtlasBuildGrowTexture(atlas); } - builder->MaxRectBounds.x = ImMax(builder->MaxRectBounds.x, r.x + r.w); - builder->MaxRectBounds.y = ImMax(builder->MaxRectBounds.y, r.y + r.h); - atlas->_PackedSurface += w * h; + builder->MaxRectBounds.x = ImMax(builder->MaxRectBounds.x, r.x + r.w + pack_padding); + builder->MaxRectBounds.y = ImMax(builder->MaxRectBounds.y, r.y + r.h + pack_padding); + atlas->_PackedSurface += (w + pack_padding) * (h + pack_padding); atlas->_PackedRects++; builder->Rects.push_back(r); @@ -3986,7 +3964,6 @@ static bool ImGui_ImplStbTrueType_FontAddGlyph(ImFontAtlas* atlas, ImFont* font, if (glyph_index == 0) return false; // Not found - // FIXME-NEWATLAS: Handling of atlas->TexGlyphPadding? const float scale_for_layout = bd_font_data->ScaleForLayout; // ~ (font units to pixels) const float scale_for_raster_x = bd_font_data->ScaleForRasterX; // ~ (font units to pixels) * RasterizationDensity * OversampleH const float scale_for_raster_y = bd_font_data->ScaleForRasterY; // ~ (font units to pixels) * RasterizationDensity * OversampleV diff --git a/imgui_internal.h b/imgui_internal.h index 27d1ca8e1..4e8384bee 100644 --- a/imgui_internal.h +++ b/imgui_internal.h @@ -3654,10 +3654,9 @@ struct ImFontAtlasBuilder { stbrp_context_opaque PackContext; // Actually 'stbrp_context' but we don't want to define this in the header file. ImVector PackNodes; - int PackPadding; // Generally 1 to avoid bilinear filtering issues. ImVector Rects; ImVector TempBuffer; // Misc scratch buffer - ImVec2i MaxRectSize; // Largest rectangle to pack (defacto used as a "minimum texture size") + ImVec2i MaxRectSize; // Largest rectangle to pack (de-facto used as a "minimum texture size") ImVec2i MaxRectBounds; // Bottom-right most used pixels bool LockDisableResize; // Disable resizing texture bool PreloadedAllGlyphsRanges; // Set when missing ImGuiBackendFlags_RendererHasTextures features forces atlas to preload everything.