Browse Source

Moved IO.Font*** options to inside the IO.Font-> structure.. Added IO.FontGlobalScale setting (vs Font->Scale)

ocornut 10 years ago
parent
commit
e4a79e9fc8
4 changed files with 112 additions and 92 deletions
  1. 2 2
      examples/opengl_example/main.cpp
  2. 11 11
      extra_fonts/README.txt
  3. 44 29
      imgui.cpp
  4. 55 50
      imgui.h

+ 2 - 2
examples/opengl_example/main.cpp

@@ -233,11 +233,11 @@ void InitImGui()
     IM_ASSERT(tex_data != NULL);
     IM_ASSERT(tex_data != NULL);
     
     
     // Automatically find white pixel from the texture we just loaded
     // Automatically find white pixel from the texture we just loaded
-    // (io.FontTexUvForWhite needs to contains UV coordinates pointing to a white pixel in order to render solid objects)
+    // (io.Font->TexUvForWhite needs to contains UV coordinates pointing to a white pixel in order to render solid objects)
     for (int tex_data_off = 0; tex_data_off < tex_x*tex_y; tex_data_off++)
     for (int tex_data_off = 0; tex_data_off < tex_x*tex_y; tex_data_off++)
         if (((unsigned int*)tex_data)[tex_data_off] == 0xffffffff)
         if (((unsigned int*)tex_data)[tex_data_off] == 0xffffffff)
         {
         {
-            io.FontTexUvForWhite = ImVec2((float)(tex_data_off % tex_x)/(tex_x), (float)(tex_data_off / tex_x)/(tex_y));
+            io.Font->TexUvForWhite = ImVec2((float)(tex_data_off % tex_x)/(tex_x), (float)(tex_data_off / tex_x)/(tex_y));
             break;
             break;
         }
         }
 #endif
 #endif

+ 11 - 11
extra_fonts/README.txt

@@ -48,16 +48,16 @@ Configure bmfont:
 
 
 (B) Use fonts from external files
 (B) Use fonts from external files
 
 
-  You need to set io.FontTexUvForWhite to UV coordinates pointing to a white pixel in the texture.
+  You need to set io.Font->TexUvForWhite to UV coordinates pointing to a white pixel in the texture.
   You can either locate a white pixel manually or use code at runtime to find or write one.
   You can either locate a white pixel manually or use code at runtime to find or write one.
   The OpenGL example include sample code to find a white pixel given an uncompressed 32-bits texture:
   The OpenGL example include sample code to find a white pixel given an uncompressed 32-bits texture:
 
 
   	  // Automatically find white pixel from the texture we just loaded
   	  // Automatically find white pixel from the texture we just loaded
-	  // (io.FontTexUvForWhite needs to contains UV coordinates pointing to a white pixel in order to render solid objects)
+	  // (io.Font->TexUvForWhite needs to contains UV coordinates pointing to a white pixel in order to render solid objects)
 	  for (int tex_data_off = 0; tex_data_off < tex_x*tex_y; tex_data_off++)
 	  for (int tex_data_off = 0; tex_data_off < tex_x*tex_y; tex_data_off++)
 	      if (((unsigned int*)tex_data)[tex_data_off] == 0xffffffff)
 	      if (((unsigned int*)tex_data)[tex_data_off] == 0xffffffff)
 	      {
 	      {
-	          io.FontTexUvForWhite = ImVec2((float)(tex_data_off % tex_x)/(tex_x), (float)(tex_data_off / tex_x)/(tex_y));
+	          io.Font->TexUvForWhite = ImVec2((float)(tex_data_off % tex_x)/(tex_x), (float)(tex_data_off / tex_x)/(tex_y));
 	          break;
 	          break;
 	      }
 	      }
 
 
@@ -69,30 +69,30 @@ Configure bmfont:
     io.Font = new ImFont();
     io.Font = new ImFont();
     io.Font->LoadFromFile("proggy_clean_13.fnt");
     io.Font->LoadFromFile("proggy_clean_13.fnt");
     IM_ASSERT(io.Font->IsLoaded());
     IM_ASSERT(io.Font->IsLoaded());
-    io.FontTexUvForWhite = ImVec2(0.0f/256.0f,0.0f/128);
-    io.FontYOffset = +1;
+    io.Font->TexUvForWhite = ImVec2(0.0f/256.0f,0.0f/128);
+    io.Font->DisplayOffset = ImVec2(0.0f, +1.0f);
 
 
     // proggy_small_12
     // proggy_small_12
     io.Font = new ImFont();
     io.Font = new ImFont();
     io.Font->LoadFromFile("proggy_small_12.fnt");
     io.Font->LoadFromFile("proggy_small_12.fnt");
     IM_ASSERT(io.Font->IsLoaded());
     IM_ASSERT(io.Font->IsLoaded());
-    io.FontTexUvForWhite = ImVec2(84.0f/256.0f,20.0f/64);
-    io.FontYOffset = +2;
+    io.Font->TexUvForWhite = ImVec2(84.0f/256.0f,20.0f/64);
+    io.Font->DisplayOffset = ImVec2(0.0f, +2.0f);
     
     
     // proggy_small_14
     // proggy_small_14
     io.Font = new ImFont();
     io.Font = new ImFont();
     io.Font->LoadFromFile("proggy_small_14.fnt");
     io.Font->LoadFromFile("proggy_small_14.fnt");
     IM_ASSERT(io.Font->IsLoaded());
     IM_ASSERT(io.Font->IsLoaded());
-    io.FontTexUvForWhite = ImVec2(84.0f/256.0f,20.0f/64);
-    io.FontYOffset = +3;
+    io.Font->TexUvForWhite = ImVec2(84.0f/256.0f,20.0f/64);
+    io.Font->DisplayOffset = ImVec2(0.0f, +3.0f);
     
     
     // courier_new_16
     // courier_new_16
     io.Font->LoadFromFile("courier_new_16.fnt");
     io.Font->LoadFromFile("courier_new_16.fnt");
-    io.FontTexUvForWhite = ImVec2(1.0f/256.0f,4.0f/128);
+    io.Font->TexUvForWhite = ImVec2(1.0f/256.0f,4.0f/128);
     
     
     // courier_new_18
     // courier_new_18
     io.Font->LoadFromFile("courier_new_18.fnt");
     io.Font->LoadFromFile("courier_new_18.fnt");
-    io.FontTexUvForWhite = ImVec2(4.0f/256.0f,5.0f/256);
+    io.Font->TexUvForWhite = ImVec2(4.0f/256.0f,5.0f/256);
 
 
 
 
   2. Load the matching .PNG data into a texture
   2. Load the matching .PNG data into a texture

+ 44 - 29
imgui.cpp

@@ -111,6 +111,7 @@
  Occasionally introducing changes that are breaking the API. The breakage are generally minor and easy to fix.
  Occasionally introducing changes that are breaking the API. The breakage are generally minor and easy to fix.
  Here is a change-log of API breaking changes, if you are using one of the functions listed, expect to have to fix some code.
  Here is a change-log of API breaking changes, if you are using one of the functions listed, expect to have to fix some code.
 
 
+ - 2014/11/28 (1.17) moved IO.Font*** options to inside the IO.Font-> structure.
  - 2014/11/26 (1.17) reworked syntax of IMGUI_ONCE_UPON_A_FRAME helper macro to increase compiler compatibility
  - 2014/11/26 (1.17) reworked syntax of IMGUI_ONCE_UPON_A_FRAME helper macro to increase compiler compatibility
  - 2014/11/07 (1.15) renamed IsHovered() to IsItemHovered()
  - 2014/11/07 (1.15) renamed IsHovered() to IsItemHovered()
  - 2014/10/02 (1.14) renamed IMGUI_INCLUDE_IMGUI_USER_CPP to IMGUI_INCLUDE_IMGUI_USER_INL and imgui_user.cpp to imgui_user.inl (more IDE friendly)
  - 2014/10/02 (1.14) renamed IMGUI_INCLUDE_IMGUI_USER_CPP to IMGUI_INCLUDE_IMGUI_USER_INL and imgui_user.cpp to imgui_user.inl (more IDE friendly)
@@ -128,17 +129,13 @@
    - in your Render function, try translating your projection matrix by (0.5f,0.5f) or (0.375f,0.375f)
    - in your Render function, try translating your projection matrix by (0.5f,0.5f) or (0.375f,0.375f)
    - try adjusting ImGui::GetIO().PixelCenterOffset to 0.5f or 0.375f
    - try adjusting ImGui::GetIO().PixelCenterOffset to 0.5f or 0.375f
 
 
- - if you can only see text but no solid shapes or lines:
-   - make sure io.FontTexUvForWhite is set to the texture coordinates of a pure white pixel in your texture. 
-     (this is done for you if you are using the default font)
-     (ImGui is using this texture coordinate to draw solid objects so text and solid draw calls can be merged into one.)
-
  - if you want to use a different font than the default:
  - if you want to use a different font than the default:
    - create bitmap font data using BMFont, make sure that BMFont is exporting the .fnt file in Binary mode.
    - create bitmap font data using BMFont, make sure that BMFont is exporting the .fnt file in Binary mode.
        io.Font = new ImBitmapFont();
        io.Font = new ImBitmapFont();
        io.Font->LoadFromFile("path_to_your_fnt_file.fnt");
        io.Font->LoadFromFile("path_to_your_fnt_file.fnt");
-   - load your texture yourself. texture *MUST* have white pixel at UV coordinate io.FontTexUvForWhite. This is used to draw all solid shapes.
+   - load your texture yourself. texture *MUST* have white pixel at UV coordinate io.Font->TexUvForWhite. This is used to draw all solid shapes.
    - the extra_fonts/ folder provides examples of using external fonts.
    - the extra_fonts/ folder provides examples of using external fonts.
+   - if you can only see text but no solid shapes or lines, make sure io.Font->TexUvForWhite is set to the texture coordinates of a pure white pixel in your texture!
 
 
  - if you are confused about the meaning or use of ID in ImGui:
  - if you are confused about the meaning or use of ID in ImGui:
    - some widgets requires state to be carried over multiple frames (most typically ImGui often wants remember what is the "active" widget).
    - some widgets requires state to be carried over multiple frames (most typically ImGui often wants remember what is the "active" widget).
@@ -350,11 +347,8 @@ ImGuiIO::ImGuiIO()
     IniFilename = "imgui.ini";
     IniFilename = "imgui.ini";
     LogFilename = "imgui_log.txt";
     LogFilename = "imgui_log.txt";
     Font = NULL;
     Font = NULL;
-    FontYOffset = 0.0f;
-    FontTexUvForWhite = ImVec2(0.0f,0.0f);
-    FontBaseScale = 1.0f;
+    FontGlobalScale = 1.0f;
     FontAllowUserScaling = false;
     FontAllowUserScaling = false;
-    FontFallbackGlyph = (ImWchar)'?';
     PixelCenterOffset = 0.0f;
     PixelCenterOffset = 0.0f;
     MousePos = ImVec2(-1,-1);
     MousePos = ImVec2(-1,-1);
     MousePosPrev = ImVec2(-1,-1);
     MousePosPrev = ImVec2(-1,-1);
@@ -731,7 +725,8 @@ struct ImGuiState
     bool                    Initialized;
     bool                    Initialized;
     ImGuiIO                 IO;
     ImGuiIO                 IO;
     ImGuiStyle              Style;
     ImGuiStyle              Style;
-    float                   FontSize;                           // == IO.FontBaseScale * IO.Font->GetFontSize(). Vertical distance between two lines of text, aka == CalcTextSize(" ").y
+    float                   FontSize;                           // == IO.FontGlobalScale * IO.Font->Scale * IO.Font->GetFontSize(). Vertical distance between two lines of text, aka == CalcTextSize(" ").y
+    ImVec2                  FontTexUvForWhite;                  // == IO.Font->FontTexUvForWhite (cached copy)
 
 
     float                   Time;
     float                   Time;
     int                     FrameCount;
     int                     FrameCount;
@@ -1348,7 +1343,6 @@ void ImGui::NewFrame()
     IM_ASSERT(g.IO.DeltaTime > 0.0f);
     IM_ASSERT(g.IO.DeltaTime > 0.0f);
     IM_ASSERT(g.IO.DisplaySize.x > 0.0f && g.IO.DisplaySize.y > 0.0f);
     IM_ASSERT(g.IO.DisplaySize.x > 0.0f && g.IO.DisplaySize.y > 0.0f);
     IM_ASSERT(g.IO.RenderDrawListsFn != NULL);  // Must be implemented
     IM_ASSERT(g.IO.RenderDrawListsFn != NULL);  // Must be implemented
-    IM_ASSERT(g.IO.FontBaseScale > 0.0f);
 
 
     if (!g.Initialized)
     if (!g.Initialized)
     {
     {
@@ -1368,16 +1362,20 @@ void ImGui::NewFrame()
             new(g.IO.Font) ImFont();
             new(g.IO.Font) ImFont();
             g.IO.Font->LoadFromMemory(fnt_data, fnt_size);
             g.IO.Font->LoadFromMemory(fnt_data, fnt_size);
             IM_ASSERT(g.IO.Font->IsLoaded());       // Font failed to load
             IM_ASSERT(g.IO.Font->IsLoaded());       // Font failed to load
-            g.IO.FontYOffset = +1;
+            g.IO.Font->DisplayOffset = ImVec2(0.0f, +1.0f);
         }
         }
         g.Initialized = true;
         g.Initialized = true;
     }
     }
+
     IM_ASSERT(g.IO.Font && g.IO.Font->IsLoaded());  // Font not loaded
     IM_ASSERT(g.IO.Font && g.IO.Font->IsLoaded());  // Font not loaded
+    IM_ASSERT(g.IO.Font->Scale > 0.0f);
+    g.FontSize = g.IO.FontGlobalScale * g.IO.Font->GetFontSize() * g.IO.Font->Scale;
+    g.FontTexUvForWhite = g.IO.Font->TexUvForWhite;
+    g.IO.Font->FallbackGlyph = g.IO.Font->FindGlyph(g.IO.Font->FallbackChar);
 
 
     g.Time += g.IO.DeltaTime;
     g.Time += g.IO.DeltaTime;
     g.FrameCount += 1;
     g.FrameCount += 1;
     g.Tooltip[0] = '\0';
     g.Tooltip[0] = '\0';
-    g.FontSize = g.IO.FontBaseScale * g.IO.Font->GetFontSize();
 
 
     // Update inputs state
     // Update inputs state
     if (g.IO.MousePos.x < 0 && g.IO.MousePos.y < 0)
     if (g.IO.MousePos.x < 0 && g.IO.MousePos.y < 0)
@@ -5454,7 +5452,7 @@ void ImDrawList::AddVtx(const ImVec2& pos, ImU32 col)
 {
 {
     vtx_write->pos = pos;
     vtx_write->pos = pos;
     vtx_write->col = col;
     vtx_write->col = col;
-    vtx_write->uv = GImGui.IO.FontTexUvForWhite;
+    vtx_write->uv = GImGui.FontTexUvForWhite;
     vtx_write++;
     vtx_write++;
 }
 }
 
 
@@ -5686,6 +5684,11 @@ void ImDrawList::AddText(ImFont* font, float font_size, const ImVec2& pos, ImU32
 
 
 ImFont::ImFont()
 ImFont::ImFont()
 {
 {
+    Scale = 1.0f;
+    DisplayOffset = ImVec2(0.0f,0.0f);
+    TexUvForWhite = ImVec2(0.0f,0.0f);
+    FallbackChar = (ImWchar)'?';
+
     Data = NULL;
     Data = NULL;
     DataSize = 0;
     DataSize = 0;
     DataOwned = false;
     DataOwned = false;
@@ -5695,7 +5698,6 @@ ImFont::ImFont()
     GlyphsCount = 0;
     GlyphsCount = 0;
     Kerning = NULL;
     Kerning = NULL;
     KerningCount = 0;
     KerningCount = 0;
-    TabCount = 4;
 }
 }
 
 
 void    ImFont::Clear()
 void    ImFont::Clear()
@@ -5790,10 +5792,11 @@ bool    ImFont::LoadFromMemory(const void* data, size_t data_size)
             Glyphs = (FntGlyph*)p;
             Glyphs = (FntGlyph*)p;
             GlyphsCount = block_size / sizeof(FntGlyph);
             GlyphsCount = block_size / sizeof(FntGlyph);
             break;
             break;
-        default:
+        case 5:
             IM_ASSERT(Kerning == NULL && KerningCount == 0);
             IM_ASSERT(Kerning == NULL && KerningCount == 0);
             Kerning = (FntKerning*)p;
             Kerning = (FntKerning*)p;
             KerningCount = block_size / sizeof(FntKerning);
             KerningCount = block_size / sizeof(FntKerning);
+        default:
             break;
             break;
         }
         }
         p += block_size;
         p += block_size;
@@ -5987,7 +5990,7 @@ static int ImTextCountUtf8BytesFromWchar(const ImWchar* in_text, const ImWchar*
     return bytes_count;
     return bytes_count;
 }
 }
 
 
-const char* ImFont::CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width, const FntGlyph* fallback_glyph) const
+const char* ImFont::CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width) const
 {
 {
     // Simple word-wrapping for English, not full-featured. Please submit failing cases!
     // Simple word-wrapping for English, not full-featured. Please submit failing cases!
     // FIXME: Much possible improvements (don't cut things like "word !", "word!!!" but cut within "word,,,,", more sensible support for punctuations, support for Unicode punctuations, etc.)
     // FIXME: Much possible improvements (don't cut things like "word !", "word!!!" but cut within "word,,,,", more sensible support for punctuations, support for Unicode punctuations, etc.)
@@ -6042,7 +6045,7 @@ const char* ImFont::CalcWordWrapPositionA(float scale, const char* text, const c
         }
         }
         else
         else
         {
         {
-            if (const FntGlyph* glyph = FindGlyph((unsigned short)c, fallback_glyph))
+            if (const FntGlyph* glyph = FindGlyph((unsigned short)c, FallbackGlyph))
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
         }
         }
 
 
@@ -6096,7 +6099,6 @@ ImVec2 ImFont::CalcTextSizeA(float size, float max_width, float wrap_width, cons
 
 
     const float scale = size / (float)Info->FontSize;
     const float scale = size / (float)Info->FontSize;
     const float line_height = (float)Info->FontSize * scale;
     const float line_height = (float)Info->FontSize * scale;
-    const FntGlyph* fallback_glyph = FindGlyph(GImGui.IO.FontFallbackGlyph);
 
 
     ImVec2 text_size = ImVec2(0,0);
     ImVec2 text_size = ImVec2(0,0);
     float line_width = 0.0f;
     float line_width = 0.0f;
@@ -6112,7 +6114,7 @@ ImVec2 ImFont::CalcTextSizeA(float size, float max_width, float wrap_width, cons
             // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature.
             // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature.
             if (!word_wrap_eol)
             if (!word_wrap_eol)
             {
             {
-                word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - line_width, fallback_glyph);
+                word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - line_width);
                 if (word_wrap_eol == s) // Wrap_width is too small to fit anything. Force displaying 1 character to minimize the height discontinuity.
                 if (word_wrap_eol == s) // Wrap_width is too small to fit anything. Force displaying 1 character to minimize the height discontinuity.
                     word_wrap_eol++;    // +1 may not be a character start point in UTF-8 but it's ok because we use s >= word_wrap_eol below
                     word_wrap_eol++;    // +1 may not be a character start point in UTF-8 but it's ok because we use s >= word_wrap_eol below
             }
             }
@@ -6156,7 +6158,7 @@ ImVec2 ImFont::CalcTextSizeA(float size, float max_width, float wrap_width, cons
             if (const FntGlyph* glyph = FindGlyph((unsigned short)' '))
             if (const FntGlyph* glyph = FindGlyph((unsigned short)' '))
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * 4 * scale;
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * 4 * scale;
         }
         }
-        else if (const FntGlyph* glyph = FindGlyph((unsigned short)c, fallback_glyph))
+        else if (const FntGlyph* glyph = FindGlyph((unsigned short)c, FallbackGlyph))
         {
         {
             char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
             char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
         }
         }
@@ -6187,7 +6189,6 @@ ImVec2 ImFont::CalcTextSizeW(float size, float max_width, const ImWchar* text_be
 
 
     const float scale = size / (float)Info->FontSize;
     const float scale = size / (float)Info->FontSize;
     const float line_height = (float)Info->FontSize * scale;
     const float line_height = (float)Info->FontSize * scale;
-    const FntGlyph* fallback_glyph = FindGlyph(GImGui.IO.FontFallbackGlyph);
 
 
     ImVec2 text_size = ImVec2(0,0);
     ImVec2 text_size = ImVec2(0,0);
     float line_width = 0.0f;
     float line_width = 0.0f;
@@ -6215,7 +6216,7 @@ ImVec2 ImFont::CalcTextSizeW(float size, float max_width, const ImWchar* text_be
         }
         }
         else
         else
         {
         {
-            if (const FntGlyph* glyph = FindGlyph((unsigned short)c, fallback_glyph))
+            if (const FntGlyph* glyph = FindGlyph((unsigned short)c, FallbackGlyph))
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
                 char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
         }
         }
 
 
@@ -6248,11 +6249,10 @@ void ImFont::RenderText(float size, ImVec2 pos, ImU32 col, const ImVec4& clip_re
     const float tex_scale_x = 1.0f / (float)Common->ScaleW;
     const float tex_scale_x = 1.0f / (float)Common->ScaleW;
     const float tex_scale_y = 1.0f / (float)(Common->ScaleH);
     const float tex_scale_y = 1.0f / (float)(Common->ScaleH);
     const float outline = (float)Info->Outline;
     const float outline = (float)Info->Outline;
-    const FntGlyph* fallback_glyph = FindGlyph(GImGui.IO.FontFallbackGlyph);
 
 
     // Align to be pixel perfect
     // Align to be pixel perfect
-    pos.x = (float)(int)pos.x;
-    pos.y = (float)(int)pos.y + GImGui.IO.FontYOffset;
+    pos.x = (float)(int)pos.x + DisplayOffset.x;
+    pos.y = (float)(int)pos.y + DisplayOffset.y;
 
 
     const bool word_wrap_enabled = (wrap_width > 0.0f);
     const bool word_wrap_enabled = (wrap_width > 0.0f);
     const char* word_wrap_eol = NULL;
     const char* word_wrap_eol = NULL;
@@ -6269,7 +6269,7 @@ void ImFont::RenderText(float size, ImVec2 pos, ImU32 col, const ImVec4& clip_re
             // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature.
             // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature.
             if (!word_wrap_eol)
             if (!word_wrap_eol)
             {
             {
-                word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - (x - pos.x), fallback_glyph);
+                word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - (x - pos.x));
                 if (word_wrap_eol == s) // Wrap_width is too small to fit anything. Force displaying 1 character to minimize the height discontinuity.
                 if (word_wrap_eol == s) // Wrap_width is too small to fit anything. Force displaying 1 character to minimize the height discontinuity.
                     word_wrap_eol++;    // +1 may not be a character start point in UTF-8 but it's ok because we use s >= word_wrap_eol below
                     word_wrap_eol++;    // +1 may not be a character start point in UTF-8 but it's ok because we use s >= word_wrap_eol below
             }
             }
@@ -6309,7 +6309,7 @@ void ImFont::RenderText(float size, ImVec2 pos, ImU32 col, const ImVec4& clip_re
             if (const FntGlyph* glyph = FindGlyph((unsigned short)' '))
             if (const FntGlyph* glyph = FindGlyph((unsigned short)' '))
                 char_width += (glyph->XAdvance + Info->SpacingHoriz) * 4 * scale;
                 char_width += (glyph->XAdvance + Info->SpacingHoriz) * 4 * scale;
         }
         }
-        else if (const FntGlyph* glyph = FindGlyph((unsigned short)c, fallback_glyph))
+        else if (const FntGlyph* glyph = FindGlyph((unsigned short)c, FallbackGlyph))
         {
         {
             char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
             char_width = (glyph->XAdvance + Info->SpacingHoriz) * scale;
             if (c != ' ')
             if (c != ' ')
@@ -6525,6 +6525,20 @@ void ImGui::ShowStyleEditor(ImGuiStyle* ref)
         ImGui::TreePop();
         ImGui::TreePop();
     }
     }
 
 
+    /*
+    // Font scaling options
+    // Note that those are not actually part of the style.
+    if (ImGui::TreeNode("Font"))
+    {
+        static float window_scale = 1.0f;
+        ImGui::SliderFloat("window scale", &window_scale, 0.3f, 2.0f, "%.1f");                   // scale only this window
+        ImGui::SliderFloat("font scale", &ImGui::GetIO().Font->Scale, 0.3f, 2.0f, "%.1f");       // scale only this font
+        ImGui::SliderFloat("global scale", &ImGui::GetIO().FontGlobalScale, 0.3f, 2.0f, "%.1f"); // scale everything
+        ImGui::SetWindowFontScale(window_scale);
+        ImGui::TreePop();
+    }
+    */
+
     ImGui::PopItemWidth();
     ImGui::PopItemWidth();
 }
 }
 
 
@@ -6569,6 +6583,7 @@ void ImGui::ShowTestWindow(bool* open)
         ImGui::Checkbox("no move", &no_move); ImGui::SameLine(150);
         ImGui::Checkbox("no move", &no_move); ImGui::SameLine(150);
         ImGui::Checkbox("no scrollbar", &no_scrollbar);
         ImGui::Checkbox("no scrollbar", &no_scrollbar);
         ImGui::SliderFloat("fill alpha", &fill_alpha, 0.0f, 1.0f);
         ImGui::SliderFloat("fill alpha", &fill_alpha, 0.0f, 1.0f);
+
         if (ImGui::TreeNode("Style Editor"))
         if (ImGui::TreeNode("Style Editor"))
         {
         {
             ImGui::ShowStyleEditor();
             ImGui::ShowStyleEditor();

+ 55 - 50
imgui.h

@@ -30,8 +30,8 @@ struct ImGuiWindow;
 #endif
 #endif
 
 
 typedef unsigned int ImU32;
 typedef unsigned int ImU32;
-typedef unsigned short ImWchar;
-typedef ImU32 ImGuiID;
+typedef unsigned short ImWchar;     // hold a character for display
+typedef ImU32 ImGuiID;              // hold widget unique ID
 typedef int ImGuiCol;               // enum ImGuiCol_
 typedef int ImGuiCol;               // enum ImGuiCol_
 typedef int ImGuiStyleVar;          // enum ImGuiStyleVar_
 typedef int ImGuiStyleVar;          // enum ImGuiStyleVar_
 typedef int ImGuiKey;               // enum ImGuiKey_
 typedef int ImGuiKey;               // enum ImGuiKey_
@@ -160,7 +160,7 @@ namespace ImGui
     IMGUI_API ImDrawList*   GetWindowDrawList();                                                // get rendering command-list if you want to append your own draw primitives.
     IMGUI_API ImDrawList*   GetWindowDrawList();                                                // get rendering command-list if you want to append your own draw primitives.
     IMGUI_API ImFont*       GetWindowFont();
     IMGUI_API ImFont*       GetWindowFont();
     IMGUI_API float         GetWindowFontSize();
     IMGUI_API float         GetWindowFontSize();
-    IMGUI_API void          SetWindowFontScale(float scale);                                    // per-window font scale. Adjust IO.FontBaseScale if you want to scale all windows together.
+    IMGUI_API void          SetWindowFontScale(float scale);                                    // per-window font scale. Adjust IO.FontGlobalScale if you want to scale all windows.
     IMGUI_API void          SetScrollPosHere();                                                 // adjust scrolling position to center into the current cursor position.
     IMGUI_API void          SetScrollPosHere();                                                 // adjust scrolling position to center into the current cursor position.
     IMGUI_API void          SetKeyboardFocusHere(int offset = 0);                               // focus keyboard on the next widget. Use 'offset' to access sub components of a multiple component widget.
     IMGUI_API void          SetKeyboardFocusHere(int offset = 0);                               // focus keyboard on the next widget. Use 'offset' to access sub components of a multiple component widget.
     IMGUI_API void          SetTreeStateStorage(ImGuiStorage* tree);                            // replace tree state storage with our own (if you want to manipulate it yourself, typically clear subsection of it).
     IMGUI_API void          SetTreeStateStorage(ImGuiStorage* tree);                            // replace tree state storage with our own (if you want to manipulate it yourself, typically clear subsection of it).
@@ -454,12 +454,9 @@ struct ImGuiIO
     float       MouseDoubleClickTime;       // = 0.30f                  // Time for a double-click, in seconds.
     float       MouseDoubleClickTime;       // = 0.30f                  // Time for a double-click, in seconds.
     float       MouseDoubleClickMaxDist;    // = 6.0f                   // Distance threshold to stay in to validate a double-click, in pixels.
     float       MouseDoubleClickMaxDist;    // = 6.0f                   // Distance threshold to stay in to validate a double-click, in pixels.
     int         KeyMap[ImGuiKey_COUNT];     // <unset>                  // Map of indices into the KeysDown[512] entries array
     int         KeyMap[ImGuiKey_COUNT];     // <unset>                  // Map of indices into the KeysDown[512] entries array
-    ImFont*     Font;                       // <auto>                   // Font
-    float       FontYOffset;                // = 0.0f                   // Offset font rendering by xx pixels in Y axis.
-    ImVec2      FontTexUvForWhite;          // = (0.0f,0.0f)            // Font texture must have a white pixel at this UV coordinate. Adjust if you are using custom texture.
-    float       FontBaseScale;              // = 1.0f                   // Base font scale, multiplied by the per-window font scale which you can adjust with SetFontScale()
-    bool        FontAllowUserScaling;       // = false                  // Set to allow scaling text with CTRL+Wheel.
-    ImWchar     FontFallbackGlyph;          // = '?'                    // Replacement glyph is one isn't found.
+    ImFont*     Font;                       // <auto>                   // Font (also see 'Settings' fields inside ImFont structure for details)
+    float       FontGlobalScale;            // = 1.0f                   // Global scale all fonts
+    bool        FontAllowUserScaling;       // = false                  // Allow user scaling text of individual window with CTRL+Wheel.
     float       PixelCenterOffset;          // = 0.0f                   // Try to set to 0.5f or 0.375f if rendering is blurry
     float       PixelCenterOffset;          // = 0.0f                   // Try to set to 0.5f or 0.375f if rendering is blurry
 
 
     void*       UserData;                   // = NULL                   // Store your own data for retrieval by callbacks.
     void*       UserData;                   // = NULL                   // Store your own data for retrieval by callbacks.
@@ -693,10 +690,54 @@ struct ImDrawList
 //  - tool: http://www.angelcode.com/products/bmfont
 //  - tool: http://www.angelcode.com/products/bmfont
 //  - file-format: http://www.angelcode.com/products/bmfont/doc/file_format.html
 //  - file-format: http://www.angelcode.com/products/bmfont/doc/file_format.html
 // Assume valid file data (won't handle invalid/malicious data)
 // Assume valid file data (won't handle invalid/malicious data)
-// Handle a subset of parameters.
-//  - kerning pair are not supported (because ImGui code does per-character CalcTextSize calls, need to turn it into something more stateful to allow kerning)
+// Handle a subset of the options, namely:
+//  - kerning pair are not supported (because some ImGui code does per-character CalcTextSize calls, need to turn it into something more state-ful to allow for kerning)
 struct ImFont
 struct ImFont
 {
 {
+    struct FntInfo;
+    struct FntCommon;
+    struct FntGlyph;
+    struct FntKerning;
+
+    // Settings
+    float                       Scale;              // = 1.0f          // Base font scale, multiplied by the per-window font scale which you can adjust with SetFontScale()
+    ImVec2                      DisplayOffset;      // = (0.0f,0.0f    // Offset font rendering by xx pixels
+    ImVec2                      TexUvForWhite;      // = (0.0f,0.0f)   // Font texture must have a white pixel at this UV coordinate. Adjust if you are using custom texture.
+    ImWchar                     FallbackChar;       // = '?'           // Replacement glyph is one isn't found.
+
+    // Data
+    unsigned char*              Data;               // Raw data, content of .fnt file
+    size_t                      DataSize;           //
+    bool                        DataOwned;          // 
+    const FntInfo*              Info;               // (point into raw data)
+    const FntCommon*            Common;             // (point into raw data)
+    const FntGlyph*             Glyphs;             // (point into raw data)
+    size_t                      GlyphsCount;        //
+    const FntKerning*           Kerning;            // (point into raw data) - NB: kerning is unsupported
+    size_t                      KerningCount;       //
+    ImVector<const char*>       Filenames;          // (point into raw data)
+    ImVector<int>               IndexLookup;        // (built)
+    const FntGlyph*             FallbackGlyph;      // == FindGlyph(FontFallbackChar)
+
+    IMGUI_API ImFont();
+    IMGUI_API ~ImFont()         { Clear(); }
+
+    IMGUI_API bool			    LoadFromMemory(const void* data, size_t data_size);
+    IMGUI_API bool              LoadFromFile(const char* filename);
+    IMGUI_API void              Clear();
+    IMGUI_API void              BuildLookupTable();
+    IMGUI_API const FntGlyph*   FindGlyph(unsigned short c, const FntGlyph* fallback = NULL) const;
+    IMGUI_API float             GetFontSize() const { return (float)Info->FontSize; } // before scale!
+    IMGUI_API bool              IsLoaded() const { return Info != NULL && Common != NULL && Glyphs != NULL; }
+
+    // 'max_width' stops rendering after a certain width (could be turned into a 2d size). FLT_MAX to disable.
+    // 'wrap_width' enable automatic word-wrapping across multiple lines to fit into given width. 0.0f to disable.
+    IMGUI_API ImVec2            CalcTextSizeA(float size, float max_width, float wrap_width, const char* text_begin, const char* text_end = NULL, const char** remaining = NULL) const; // utf8
+    IMGUI_API ImVec2            CalcTextSizeW(float size, float max_width, const ImWchar* text_begin, const ImWchar* text_end, const ImWchar** remaining = NULL) const;                 // wchar
+    IMGUI_API void              RenderText(float size, ImVec2 pos, ImU32 col, const ImVec4& clip_rect, const char* text_begin, const char* text_end, ImDrawVert*& out_vertices, float wrap_width = 0.0f) const;
+
+    IMGUI_API const char*       CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width) const;
+
 #pragma pack(push, 1)
 #pragma pack(push, 1)
     struct FntInfo
     struct FntInfo
     {
     {
@@ -706,15 +747,13 @@ struct ImFont
         unsigned short  StretchH;
         unsigned short  StretchH;
         unsigned char   AA;
         unsigned char   AA;
         unsigned char   PaddingUp, PaddingRight, PaddingDown, PaddingLeft;
         unsigned char   PaddingUp, PaddingRight, PaddingDown, PaddingLeft;
-        unsigned char   SpacingHoriz, SpacingVert;
-        unsigned char   Outline;
+        unsigned char   SpacingHoriz, SpacingVert, Outline;
         //char          FontName[];
         //char          FontName[];
     };
     };
 
 
     struct FntCommon
     struct FntCommon
     {
     {
-        unsigned short  LineHeight;
-        unsigned short  Base;
+        unsigned short  LineHeight, Base;
         unsigned short  ScaleW, ScaleH;
         unsigned short  ScaleW, ScaleH;
         unsigned short  Pages;
         unsigned short  Pages;
         unsigned char   BitField;
         unsigned char   BitField;
@@ -724,8 +763,7 @@ struct ImFont
     struct FntGlyph
     struct FntGlyph
     {
     {
         unsigned int    Id;
         unsigned int    Id;
-        unsigned short  X, Y;
-        unsigned short  Width, Height;
+        unsigned short  X, Y, Width, Height;
         signed short    XOffset, YOffset;
         signed short    XOffset, YOffset;
         signed short    XAdvance;
         signed short    XAdvance;
         unsigned char   Page;
         unsigned char   Page;
@@ -739,37 +777,4 @@ struct ImFont
         signed short    Amount;
         signed short    Amount;
     };
     };
 #pragma pack(pop)
 #pragma pack(pop)
-
-    unsigned char*              Data;               // Raw data, content of .fnt file
-    size_t                      DataSize;           //
-    bool                        DataOwned;          // 
-    const FntInfo*              Info;               // (point into raw data)
-    const FntCommon*            Common;             // (point into raw data)
-    const FntGlyph*             Glyphs;             // (point into raw data)
-    size_t                      GlyphsCount;        //
-    const FntKerning*           Kerning;            // (point into raw data)
-    size_t                      KerningCount;       //
-    int                         TabCount;           // FIXME: mishandled (add fixed amount instead of aligning to column)
-    ImVector<const char*>       Filenames;          // (point into raw data)
-    ImVector<int>               IndexLookup;        // (built)
-
-    IMGUI_API ImFont();
-    IMGUI_API ~ImFont()         { Clear(); }
-
-    IMGUI_API bool			    LoadFromMemory(const void* data, size_t data_size);
-    IMGUI_API bool              LoadFromFile(const char* filename);
-    IMGUI_API void              Clear();
-    IMGUI_API void              BuildLookupTable();
-    IMGUI_API const FntGlyph*   FindGlyph(unsigned short c, const FntGlyph* fallback = NULL) const;
-    IMGUI_API float             GetFontSize() const { return (float)Info->FontSize; }
-    IMGUI_API bool              IsLoaded() const { return Info != NULL && Common != NULL && Glyphs != NULL; }
-
-    // 'max_width' stops rendering after a certain width (could be turned into a 2d size). FLT_MAX to disable.
-    // 'wrap_width' enable automatic word-wrapping across multiple lines to fit into given width. 0.0f to disable.
-    IMGUI_API ImVec2            CalcTextSizeA(float size, float max_width, float wrap_width, const char* text_begin, const char* text_end = NULL, const char** remaining = NULL) const; // utf8
-    IMGUI_API ImVec2            CalcTextSizeW(float size, float max_width, const ImWchar* text_begin, const ImWchar* text_end, const ImWchar** remaining = NULL) const;                 // wchar
-    IMGUI_API void              RenderText(float size, ImVec2 pos, ImU32 col, const ImVec4& clip_rect, const char* text_begin, const char* text_end, ImDrawVert*& out_vertices, float wrap_width = 0.0f) const;
-
-private:
-    IMGUI_API const char*       CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width, const FntGlyph* fallback_glyph) const;
 };
 };