Ver Fonte

Fonts: ClearCache(), ImFontAtlasBuildGetTextureSizeEstimate(), tweak clearing functions.

ocornut há 8 meses atrás
pai
commit
4399599de9
3 ficheiros alterados com 47 adições e 28 exclusões
  1. 4 4
      imgui.h
  2. 42 24
      imgui_draw.cpp
  3. 1 0
      imgui_internal.h

+ 4 - 4
imgui.h

@@ -3523,12 +3523,12 @@ struct ImFontAtlas
     IMGUI_API ImFont*           AddFontFromMemoryCompressedBase85TTF(const char* compressed_font_data_base85, float size_pixels, const ImFontConfig* font_cfg = NULL, const ImWchar* glyph_ranges = NULL);              // 'compressed_font_data_base85' still owned by caller. Compress with binary_to_compressed_c.cpp with -base85 parameter.
 
     // FIXME-NEWATLAS: Clarify meaning/purpose
-    IMGUI_API void              ClearInputData();           // Clear input data (all ImFontConfig structures including sizes, TTF data, glyph ranges, etc.) = all the data used to build the texture and fonts.
-    IMGUI_API void              ClearFonts();               // Clear input+output font data (same as ClearInputData() + glyphs storage, UV coordinates).
-    IMGUI_API void              ClearTexData();             // Clear output texture data (CPU side). Saves RAM once the texture has been copied to graphics memory.
     IMGUI_API void              Clear();                    // Clear all input and output.
-
     IMGUI_API void              ClearCache();               // Clear cached glyphs
+    // As we are transitioning toward a new font system, we expect to obsolete those soon:
+    IMGUI_API void              ClearInputData();           // [OBSOLETE] Clear input data (all ImFontConfig structures including sizes, TTF data, glyph ranges, etc.) = all the data used to build the texture and fonts.
+    IMGUI_API void              ClearFonts();               // [OBSOLETE] Clear input+output font data (same as ClearInputData() + glyphs storage, UV coordinates).
+    IMGUI_API void              ClearTexData();             // [OBSOLETE] Clear output texture data (CPU side). Saves RAM once the texture has been copied to graphics memory.
 
     // Build atlas, retrieve pixel data.
     // User is in charge of copying the pixels into graphics memory (e.g. create a texture with your engine). Then store your texture handle with SetTexID().

+ 42 - 24
imgui_draw.cpp

@@ -2569,8 +2569,9 @@ static const ImVec2 FONT_ATLAS_DEFAULT_TEX_CURSOR_DATA[ImGuiMouseCursor_COUNT][3
     { ImVec2(109,0),ImVec2(13,15), ImVec2( 6, 7) }, // ImGuiMouseCursor_NotAllowed
 };
 
-#define IM_FONTGLYPH_INDEX_UNUSED        ((ImU16)-1) // 0xFFFF
-#define IM_FONTGLYPH_INDEX_NOT_FOUND     ((ImU16)-2) // 0xFFFE
+#define IM_FONTGLYPH_INDEX_UNUSED           ((ImU16)-1) // 0xFFFF
+#define IM_FONTGLYPH_INDEX_NOT_FOUND        ((ImU16)-2) // 0xFFFE
+#define IM_FONTATLAS_DEFAULT_TEXTURE_SIZE   ImVec2i(512, 128)
 
 ImFontAtlas::ImFontAtlas()
 {
@@ -2600,11 +2601,14 @@ void ImFontAtlas::ClearInputData()
 
     // When clearing this we lose access to the font name and other information used to build the font.
     for (ImFont* font : Fonts)
+    {
         if (font->Sources >= Sources.Data && font->Sources < Sources.Data + Sources.Size)
         {
             font->Sources = NULL;
             font->SourcesCount = 0;
         }
+        font->LockDisableLoading = true;
+    }
     Sources.clear();
     //CustomRects.clear();
     // Important: we leave TexReady untouched
@@ -2616,15 +2620,14 @@ void ImFontAtlas::ClearTexData()
     TexList.clear();
     IM_DELETE(TexData);
     TexData = NULL;
-    //    TexData.Destroy();
-        //IM_ASSERT(0);
-        // Important: we leave TexReady untouched
+    // Important: we leave TexReady untouched
 }
 
 void ImFontAtlas::ClearFonts()
 {
     // FIXME-NEWATLAS: Illegal to remove currently bound font.
     IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas!");
+    ImFontAtlasBuildDestroy(this);
     ClearInputData();
     Fonts.clear_delete();
     TexIsBuilt = false;
@@ -2637,7 +2640,7 @@ void ImFontAtlas::ClearFonts()
 
 void ImFontAtlas::Clear()
 {
-    //IM_DELETE(Builder); // FIXME-NEW-ATLAS: ClearXXX functions
+    //IM_DELETE(Builder); // FIXME-NEW-ATLAS: Clarify ClearXXX functions
     const ImFontLoader* font_loader = FontLoader;
     ImFontAtlasBuildSetupFontLoader(this, NULL);
     ClearInputData();
@@ -2649,11 +2652,9 @@ void ImFontAtlas::Clear()
 // FIXME-NEWATLAS: Too widespread purpose. Clarify each call site in current WIP demo.
 void ImFontAtlas::ClearCache()
 {
-    int tex_w = (TexData && TexData->Status != ImTextureStatus_WantDestroy) ? TexData->Width : 0;
-    int tex_h = (TexData && TexData->Status != ImTextureStatus_WantDestroy) ? TexData->Height : 0;
+    ImVec2i new_tex_size = ImFontAtlasBuildGetTextureSizeEstimate(this);
     ImFontAtlasBuildDestroy(this);
-    if (tex_w != 0 && tex_h != 0)
-        ImFontAtlasBuildAddTexture(this, tex_w, tex_h);
+    ImFontAtlasBuildAddTexture(this, new_tex_size.x, new_tex_size.y);
     ImFontAtlasBuildInit(this);
 }
 
@@ -3139,6 +3140,13 @@ bool ImFontAtlas::Build()
 {
     IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas!");
 
+    if (TexData && TexData->Format != TexDesiredFormat)
+    {
+        ImVec2i new_tex_size = ImFontAtlasBuildGetTextureSizeEstimate(this);
+        ImFontAtlasBuildDestroy(this);
+        ImFontAtlasBuildAddTexture(this, new_tex_size.x, new_tex_size.y);
+    }
+
     if (Builder == NULL)
         ImFontAtlasBuildInit(this);
 
@@ -3168,7 +3176,10 @@ void ImFontAtlasBuildSetupFontLoader(ImFontAtlas* atlas, const ImFontLoader* fon
         return;
     IM_ASSERT(!atlas->Locked && "Cannot modify a locked ImFontAtlas!");
 
+    // Note that texture size estimate is likely incorrect in this situation, as Freetype backend doesn't use oversampling.
+    ImVec2i new_tex_size = ImFontAtlasBuildGetTextureSizeEstimate(atlas);
     ImFontAtlasBuildDestroy(atlas);
+
     if (atlas->FontLoader && atlas->FontLoader->LoaderShutdown)
     {
         atlas->FontLoader->LoaderShutdown(atlas);
@@ -3178,8 +3189,9 @@ void ImFontAtlasBuildSetupFontLoader(ImFontAtlas* atlas, const ImFontLoader* fon
     atlas->FontLoaderName = font_loader ? font_loader->Name : "NULL";
     if (atlas->FontLoader && atlas->FontLoader->LoaderInit)
         atlas->FontLoader->LoaderInit(atlas);
-    if (atlas->Builder && font_loader != NULL)
-        atlas->ClearCache();
+
+    ImFontAtlasBuildAddTexture(atlas, new_tex_size.x, new_tex_size.y);
+    ImFontAtlasBuildInit(atlas);
 }
 
 // Preload all glyph ranges for legacy backends.
@@ -3684,17 +3696,13 @@ void ImFontAtlasBuildGrowTexture(ImFontAtlas* atlas, int old_tex_w, int old_tex_
     ImFontAtlasBuildRepackTexture(atlas, new_tex_w, new_tex_h);
 }
 
-// You should not need to call this manually!
-// If you think you do, let us know and we can advise about policies auto-compact.
-void ImFontAtlasBuildCompactTexture(ImFontAtlas* atlas)
+// FIXME-NEWATLAS: Expose atlas->TexMinWidth etc.
+ImVec2i ImFontAtlasBuildGetTextureSizeEstimate(ImFontAtlas* atlas)
 {
-    ImFontAtlasBuilder* builder = atlas->Builder;
-
-    ImTextureData* old_tex = atlas->TexData;
-    int old_tex_w = old_tex->Width;
-    int old_tex_h = old_tex->Height;
+    if (atlas->Builder == NULL || atlas->TexData == NULL || atlas->TexData->Status == ImTextureStatus_WantDestroy)
+        return IM_FONTATLAS_DEFAULT_TEXTURE_SIZE;
 
-    // FIXME-NEWATLAS: Expose atlas->TexMinWidth etc.
+    ImFontAtlasBuilder* builder = atlas->Builder;
     const int min_w = ImMax(builder->MaxRectSize.x, 512);
     const int min_h = builder->MaxRectSize.y;
     const int surface_approx = atlas->_PackedSurface - builder->RectsDiscardedSurface; // Expected surface after repack
@@ -3716,11 +3724,21 @@ void ImFontAtlasBuildCompactTexture(ImFontAtlas* atlas)
             new_tex_h = ImUpperPowerOfTwo(new_tex_h);
         new_tex_w = ImMax(min_w, (int)((surface_approx + new_tex_h - 1) / new_tex_h));
     }
+    return ImVec2i(new_tex_w, new_tex_h);
+}
 
-    if (builder->RectsDiscardedCount == 0 && new_tex_w == old_tex_w && new_tex_h == old_tex_h)
+// You should not need to call this manually!
+// If you think you do, let us know and we can advise about policies auto-compact.
+void ImFontAtlasBuildCompactTexture(ImFontAtlas* atlas)
+{
+    ImFontAtlasBuilder* builder = atlas->Builder;
+    ImTextureData* old_tex = atlas->TexData;
+    ImVec2i old_tex_size = ImVec2i(old_tex->Width, old_tex->Height);
+    ImVec2i new_tex_size = ImFontAtlasBuildGetTextureSizeEstimate(atlas);
+    if (builder->RectsDiscardedCount == 0 && new_tex_size.x == old_tex_size.x && new_tex_size.y == old_tex_size.y)
         return;
 
-    ImFontAtlasBuildRepackTexture(atlas, new_tex_w, new_tex_h);
+    ImFontAtlasBuildRepackTexture(atlas, new_tex_size.x, new_tex_size.y);
 }
 
 // Start packing over current empty texture
@@ -3745,7 +3763,7 @@ void ImFontAtlasBuildInit(ImFontAtlas* atlas)
     }
     // Create initial texture size
     if (atlas->TexData == NULL)
-        ImFontAtlasBuildAddTexture(atlas, 512, 128);
+        ImFontAtlasBuildAddTexture(atlas, IM_FONTATLAS_DEFAULT_TEXTURE_SIZE.x, IM_FONTATLAS_DEFAULT_TEXTURE_SIZE.y);
 
     const bool builder_is_new = (builder == NULL);
     if (builder_is_new)

+ 1 - 0
imgui_internal.h

@@ -3712,6 +3712,7 @@ IMGUI_API ImTextureData*    ImFontAtlasBuildAddTexture(ImFontAtlas* atlas, int w
 IMGUI_API void              ImFontAtlasBuildRepackTexture(ImFontAtlas* atlas, int w, int h);
 IMGUI_API void              ImFontAtlasBuildGrowTexture(ImFontAtlas* atlas, int old_w = -1, int old_h = -1);
 IMGUI_API void              ImFontAtlasBuildCompactTexture(ImFontAtlas* atlas);
+IMGUI_API ImVec2i           ImFontAtlasBuildGetTextureSizeEstimate(ImFontAtlas* atlas);
 
 IMGUI_API bool              ImFontAtlasBuildAddFont(ImFontAtlas* atlas, ImFontConfig* src);
 IMGUI_API void              ImFontAtlasBuildSetupFontSpecialGlyphs(ImFontAtlas* atlas, ImFontConfig* src);