1
0
Fork 0
mirror of https://github.com/ocornut/imgui.git synced 2026-01-11 00:04:24 +00:00

Fonts: use a structure for post-processing - easier to pass things around and iterate on.

This commit is contained in:
ocornut 2024-12-11 19:21:10 +01:00
parent 553b1c301d
commit a51a26e2aa
3 changed files with 40 additions and 31 deletions

View file

@ -2460,8 +2460,8 @@ void ImTextureData::DestroyPixels()
// - ImFontAtlas::BuildCompactTexture() // - ImFontAtlas::BuildCompactTexture()
// - ImFontAtlasUpdateTextures() // - ImFontAtlasUpdateTextures()
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// - ImFontAtlasTextureBlockConvertAndPostProcess()
// - ImFontAtlasTextureBlockConvert() // - ImFontAtlasTextureBlockConvert()
// - ImFontAtlasTextureBlockPostProcess()
// - ImFontAtlasTextureBlockPostProcessMultiply() // - ImFontAtlasTextureBlockPostProcessMultiply()
// - ImFontAtlasTextureBlockCopy() // - ImFontAtlasTextureBlockCopy()
// - ImFontAtlasTextureBlockQueueUpload() // - ImFontAtlasTextureBlockQueueUpload()
@ -2734,17 +2734,11 @@ void ImFontAtlasUpdateNewFrame(ImFontAtlas* atlas)
// Source buffer may be written to (used for in-place mods). // Source buffer may be written to (used for in-place mods).
// Post-process hooks may eventually be added here. // Post-process hooks may eventually be added here.
void ImFontAtlasTextureBlockConvertAndPostProcess(ImFontAtlas* atlas, ImFont* font, ImFontConfig* src, ImFontGlyph* glyph, unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst, ImTextureFormat dst_fmt, int dst_pitch, int w, int h) void ImFontAtlasTextureBlockPostProcess(ImFontAtlasPostProcessData* data)
{ {
IM_UNUSED(atlas);
IM_UNUSED(font);
IM_UNUSED(glyph);
// Multiply operator (legacy) // Multiply operator (legacy)
if (src->RasterizerMultiply != 1.0f) if (data->FontSrc->RasterizerMultiply != 1.0f)
ImFontAtlasTextureBlockPostProcessMultiply(atlas, font, src, glyph, src_pixels, src_fmt, w, h, src_pitch, src->RasterizerMultiply); ImFontAtlasTextureBlockPostProcessMultiply(data, data->FontSrc->RasterizerMultiply);
ImFontAtlasTextureBlockConvert(src_pixels, src_fmt, src_pitch, dst, dst_fmt, dst_pitch, w, h);
} }
void ImFontAtlasTextureBlockConvert(const unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst_pixels, ImTextureFormat dst_fmt, int dst_pitch, int w, int h) void ImFontAtlasTextureBlockConvert(const unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst_pixels, ImTextureFormat dst_fmt, int dst_pitch, int w, int h)
@ -2782,34 +2776,30 @@ void ImFontAtlasTextureBlockConvert(const unsigned char* src_pixels, ImTextureFo
} }
} }
void ImFontAtlasTextureBlockPostProcessMultiply(ImFontAtlas* atlas, ImFont* font, ImFontConfig* src, ImFontGlyph* glyph, unsigned char* pixels, ImTextureFormat format, int w, int h, int pitch, float in_multiply_factor) void ImFontAtlasTextureBlockPostProcessMultiply(ImFontAtlasPostProcessData* data, float multiply_factor)
{ {
IM_UNUSED(atlas); unsigned char* pixels = data->Pixels;
IM_UNUSED(font); int pitch = data->Pitch;
IM_UNUSED(src); if (data->Format == ImTextureFormat_Alpha8)
IM_UNUSED(glyph);
IM_ASSERT(in_multiply_factor >= 0.0f);
IM_ASSERT_PARANOID(w <= pitch);
if (format == ImTextureFormat_Alpha8)
{ {
for (int ny = h; ny > 0; ny--, pixels += pitch) for (int ny = data->Height; ny > 0; ny--, pixels += pitch)
{ {
ImU8* p = (ImU8*)pixels; ImU8* p = (ImU8*)pixels;
for (int nx = w; nx > 0; nx--, p++) for (int nx = data->Width; nx > 0; nx--, p++)
{ {
unsigned int v = ImMin((unsigned int)(*p * in_multiply_factor), (unsigned int)255); unsigned int v = ImMin((unsigned int)(*p * multiply_factor), (unsigned int)255);
*p = (unsigned char)v; *p = (unsigned char)v;
} }
} }
} }
else if (format == ImTextureFormat_RGBA32) else if (data->Format == ImTextureFormat_RGBA32)
{ {
for (int ny = h; ny > 0; ny--, pixels += pitch) for (int ny = data->Height; ny > 0; ny--, pixels += pitch)
{ {
ImU32* p = (ImU32*)(void*)pixels; ImU32* p = (ImU32*)(void*)pixels;
for (int nx = w; nx > 0; nx--, p++) for (int nx = data->Width; nx > 0; nx--, p++)
{ {
unsigned int a = ImMin((unsigned int)(((*p >> IM_COL32_A_SHIFT) & 0xFF) * in_multiply_factor), (unsigned int)255); unsigned int a = ImMin((unsigned int)(((*p >> IM_COL32_A_SHIFT) & 0xFF) * multiply_factor), (unsigned int)255);
*p = IM_COL32((*p >> IM_COL32_R_SHIFT) & 0xFF, (*p >> IM_COL32_G_SHIFT) & 0xFF, (*p >> IM_COL32_B_SHIFT) & 0xFF, a); *p = IM_COL32((*p >> IM_COL32_R_SHIFT) & 0xFF, (*p >> IM_COL32_G_SHIFT) & 0xFF, (*p >> IM_COL32_B_SHIFT) & 0xFF, a);
} }
} }
@ -4156,8 +4146,9 @@ static bool ImGui_ImplStbTrueType_FontAddGlyph(ImFontAtlas* atlas, ImFont* font,
// Copy to texture, post-process and queue update for backend // Copy to texture, post-process and queue update for backend
ImTextureData* tex = atlas->TexData; ImTextureData* tex = atlas->TexData;
IM_ASSERT(r->x + r->w <= tex->Width && r->y + r->h <= tex->Height); IM_ASSERT(r->x + r->w <= tex->Width && r->y + r->h <= tex->Height);
ImFontAtlasTextureBlockConvertAndPostProcess(atlas, font, src, &font->Glyphs.back(), ImFontAtlasTextureBlockConvert(bitmap_pixels, ImTextureFormat_Alpha8, w, tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h);
bitmap_pixels, ImTextureFormat_Alpha8, w, tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h); ImFontAtlasPostProcessData pp_data = { atlas, font, src, &font->Glyphs.back(), tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h };
ImFontAtlasTextureBlockPostProcess(&pp_data);
ImFontAtlasTextureBlockQueueUpload(atlas, tex, r->x, r->y, r->w, r->h); ImFontAtlasTextureBlockQueueUpload(atlas, tex, r->x, r->y, r->w, r->h);
} }
else else

View file

@ -144,6 +144,7 @@ struct ImDrawListSharedData; // Data shared between all ImDrawList instan
struct ImFontAtlasRect; // Packed rectangle (same as ImTextureRect) struct ImFontAtlasRect; // Packed rectangle (same as ImTextureRect)
struct ImFontAtlasRectEntry; // Packed rectangle lookup entry struct ImFontAtlasRectEntry; // Packed rectangle lookup entry
struct ImFontAtlasBuilder; // Internal storage for incrementally packing and building a ImFontAtlas struct ImFontAtlasBuilder; // Internal storage for incrementally packing and building a ImFontAtlas
struct ImFontAtlasPostProcessData; // Data available to potential post-process functions
// ImGui // ImGui
struct ImGuiBoxSelectState; // Box-selection state (currently used by multi-selection, could potentially be used by others) struct ImGuiBoxSelectState; // Box-selection state (currently used by multi-selection, could potentially be used by others)
@ -3658,6 +3659,22 @@ struct ImFontAtlasRectEntry
unsigned int Used : 1; unsigned int Used : 1;
}; };
// Data available to potential post-process functions
struct ImFontAtlasPostProcessData
{
ImFontAtlas* FontAtlas;
ImFont* Font;
ImFontConfig* FontSrc;
ImFontGlyph* Glyph;
// Pixel data
unsigned char* Pixels;
ImTextureFormat Format;
int Pitch;
int Width;
int Height;
};
// Internal storage for incrementally packing and building a ImFontAtlas // Internal storage for incrementally packing and building a ImFontAtlas
struct stbrp_context_opaque { char data[80]; }; struct stbrp_context_opaque { char data[80]; };
struct stbrp_node; struct stbrp_node;
@ -3714,9 +3731,9 @@ IMGUI_API void ImFontAtlasUpdateDrawListsSharedData(ImFontAtlas* at
IMGUI_API void ImFontAtlasUpdateNewFrame(ImFontAtlas* atlas); IMGUI_API void ImFontAtlasUpdateNewFrame(ImFontAtlas* atlas);
IMGUI_API void ImFontAtlasTextureBlockConvertAndPostProcess(ImFontAtlas* atlas, ImFont* font, ImFontConfig* src, ImFontGlyph* glyph, unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst, ImTextureFormat dst_fmt, int dst_pitch, int w, int h);
IMGUI_API void ImFontAtlasTextureBlockConvert(const unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst_pixels, ImTextureFormat dst_fmt, int dst_pitch, int w, int h); IMGUI_API void ImFontAtlasTextureBlockConvert(const unsigned char* src_pixels, ImTextureFormat src_fmt, int src_pitch, unsigned char* dst_pixels, ImTextureFormat dst_fmt, int dst_pitch, int w, int h);
IMGUI_API void ImFontAtlasTextureBlockPostProcessMultiply(ImFontAtlas* atlas, ImFont* font, ImFontConfig* src, ImFontGlyph* glyph, unsigned char* pixels, ImTextureFormat format, int w, int h, int pitch, float in_multiply_factor); IMGUI_API void ImFontAtlasTextureBlockPostProcess(ImFontAtlasPostProcessData* data);
IMGUI_API void ImFontAtlasTextureBlockPostProcessMultiply(ImFontAtlasPostProcessData* data, float multiply_factor);
IMGUI_API void ImFontAtlasTextureBlockCopy(ImTextureData* src_tex, int src_x, int src_y, ImTextureData* dst_tex, int dst_x, int dst_y, int w, int h); IMGUI_API void ImFontAtlasTextureBlockCopy(ImTextureData* src_tex, int src_x, int src_y, ImTextureData* dst_tex, int dst_x, int dst_y, int w, int h);
IMGUI_API void ImFontAtlasTextureBlockQueueUpload(ImFontAtlas* atlas, ImTextureData* tex, int x, int y, int w, int h); IMGUI_API void ImFontAtlasTextureBlockQueueUpload(ImFontAtlas* atlas, ImTextureData* tex, int x, int y, int w, int h);

View file

@ -541,8 +541,9 @@ bool ImGui_ImplFreeType_FontAddGlyph(ImFontAtlas* atlas, ImFont* font, ImFontCon
// Copy to texture, post-process and queue update for backend // Copy to texture, post-process and queue update for backend
ImTextureData* tex = atlas->TexData; ImTextureData* tex = atlas->TexData;
IM_ASSERT(r->x + r->w <= tex->Width && r->y + r->h <= tex->Height); IM_ASSERT(r->x + r->w <= tex->Width && r->y + r->h <= tex->Height);
ImFontAtlasTextureBlockConvertAndPostProcess(atlas, font, src, &font->Glyphs.back(), ImFontAtlasTextureBlockConvert(temp_buffer, ImTextureFormat_RGBA32, w * 4, tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h);
temp_buffer, ImTextureFormat_RGBA32, w * 4, tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h); ImFontAtlasPostProcessData pp_data = { atlas, font, src, &font->Glyphs.back(), tex->GetPixelsAt(r->x, r->y), tex->Format, tex->GetPitch(), w, h };
ImFontAtlasTextureBlockPostProcess(&pp_data);
ImFontAtlasTextureBlockQueueUpload(atlas, tex, r->x, r->y, r->w, r->h); ImFontAtlasTextureBlockQueueUpload(atlas, tex, r->x, r->y, r->w, r->h);
} }
else else