Fonts: ImFontGlyphRangesBuilder + GetGlyphRangesDefault, ImFont:CalcWordWrapPosition, stb_decompress + Decode85 + AddFontFromMemoryCompressed(Base85)TTF, atlas helpers (RemoveFont, RemoveCustomRect, AddRemapCodepoint (remap never triggered before), IsGlyphRangeUnused, texture status/format names...); t_fonts
This commit is contained in:
+442
-5
@@ -138,7 +138,7 @@ if not utf8 then
|
||||
end
|
||||
|
||||
|
||||
local ImGui, ImVec2, ImVec4, ImRect, HelpMarker, ImVec2_Copy, IMGUI_DEMO_MARKER, ImGuiTableFlags, ImStd, ImVector, ImGuiKey, ImDrawFlags, ImGuiInputFlags, ImRect_Copy, ImGuiDataType, ImStb, IM_TRUNC, ImVec2_CopyV, ImGuiStyleVarInfo, IM_ASSERT_USER_ERROR, ImGuiHoveredFlags, ImFormatString, IM_ASSERT_USER_ERROR_RET, ImHashStr, ImS32, ImGuiColorEditFlags, ImIsPowerOfTwo, ImAbs, ImVec4_Copy, ExampleAppConsoleMT, IM_ROUND, ImGuiTableColumnFlags, ImGuiTreeNodeFlags, PopStyleCompact, PushStyleCompact, IM_ASSERT_PARANOID, ImU16, ExampleNames, ImGuiWindowFlags, ImGuiItemFlags, stbte, ImColor, ImCos, ImGuiButtonFlags, ImGuiDebugLogFlags, ImGuiLocKey, ImU32, ExampleTreeFuncs, ImGuiListClipper, ImS16, _PathArcToFastExXY, ImGuiMultiSelectFlags, ImSin, ImGuiTabBarFlags, ImUpperPowerOfTwo, IM_F32_TO_INT8_SAT, ImFontAtlasPackGetRect, ImGuiMouseCursor, DockSettingsRenameNodeReferences, ExampleDualListBoxMT, IM_DRAWLIST_TEX_LINES_WIDTH_MAX, ImCeil, ImFabs, ImGuiCol, ImGuiSelectionBasicStorage, ImLengthSqr, ImS8, ImU8, ExampleAppPropertyEditorMT, ImGuiScrollFlags, ImGui_ImplLOVE_GetBackendData, ImLog, ExampleSelectionWithDeletionMT, CustomConstraints, ExampleAppLogMT, ImFontAtlasBuildInit, ImGuiComboFlags, ImGuiPopupFlags, ImGuiSliderFlags, ImTextClassifierSetCharClass, MyDocument, ShowExampleMenuFile, CalcCornerArcStepAndCount, ImFontAtlasBakedAddFontGlyph, ImFontAtlasPackAddRect, ImFontBaked_BuildLoadGlyph, ImGuiInputTextFlags, ImGuiStyle_Copy, ExampleAsset_s_current_sort_specs, ExampleMemberInfo, IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC, ImFontAtlasBuildRenderBitmapFromString, ImFontAtlasFontDestroyOutput, ImFontAtlasFontSourceAddToFont, ImFontAtlasFontSourceInit, ImFontAtlasTextureAdd, ImFontAtlasTextureBlockQueueUpload, ImFontBaked_BuildGrowIndex, ImGuiTableColumn, stb_textedit_key, stbtt_GetGlyphBitmapBoxSubpixel, IM_FREE, ImDrawListSplitter, ImGuiDragDropFlags, ImGuiFocusedFlags, stb_text_locate_coord, stb_text_makeundo_insert, stb_text_makeundo_replace, stb_textedit_find_charpos, stbtt_GetGlyphShape, IM_ALLOC, ImGuiTableColumnSortSpecs, ImGuiTableInstanceData, ImGuiTableSettings, stb_text_makeundo_delete, stb_text_redo, stb_text_undo, stb_textedit_click, stb_textedit_drag, stbtt_FindGlyphIndex, stbtt_GetFontOffsetForIndex, stbtt_GetFontVMetrics, stbtt_GetGlyphBitmapBox, stbtt_GetGlyphHMetrics, stbtt_InitFont, stbtt_MakeGlyphBitmapSubpixelPrefilter, stbtt_ScaleForPixelHeight, stbtt__GetGlyphInfoT2, stbtt__GetGlyphShapeT2, stbtt_fontinfo, ImGuiOldColumnData, ImGuiOldColumnFlags, ImGuiOldColumns, ImGuiTable, ImGuiTableColumnSettings, ImGuiTableSortSpecs, ImGuiTableTempData, ImGui_ImplLOVE_CreateTexture, ImGui_ImplLOVE_DestroyTexture, ImGui_ImplLOVE_Init, ImGui_ImplLOVE_NewFrame, ImGui_ImplLOVE_RenderDrawData, ImGui_ImplLOVE_Shutdown, ImGui_ImplLOVE_UpdateTexture, stbrp_init_target, IMGUI_TABLE_MAX_COLUMNS, IMSTB_TEXTEDIT_UNDOSTATECOUNT, IM_COL32_DISABLE, ImGui_ImplLove, STB_TEXTEDIT_K_BACKSPACE, STB_TEXTEDIT_K_DELETE, STB_TEXTEDIT_K_DOWN, STB_TEXTEDIT_K_LEFT, STB_TEXTEDIT_K_LINEEND, STB_TEXTEDIT_K_LINESTART, STB_TEXTEDIT_K_PGDOWN, STB_TEXTEDIT_K_PGUP, STB_TEXTEDIT_K_REDO, STB_TEXTEDIT_K_RIGHT, STB_TEXTEDIT_K_SHIFT
|
||||
local ImGui, ImVec2, ImVec4, ImRect, HelpMarker, ImVec2_Copy, IMGUI_DEMO_MARKER, ImGuiTableFlags, ImStd, ImVector, ImGuiKey, ImDrawFlags, ImGuiInputFlags, ImRect_Copy, ImGuiDataType, ImStb, IM_TRUNC, ImVec2_CopyV, ImGuiStyleVarInfo, IM_ASSERT_USER_ERROR, ImGuiHoveredFlags, ImFormatString, IM_ASSERT_USER_ERROR_RET, ImHashStr, ImS32, ImGuiColorEditFlags, ImIsPowerOfTwo, ImAbs, ImVec4_Copy, ExampleAppConsoleMT, IM_ROUND, ImGuiTableColumnFlags, ImGuiTreeNodeFlags, PopStyleCompact, PushStyleCompact, IM_ASSERT_PARANOID, ImU16, ExampleNames, ImGuiWindowFlags, ImGuiItemFlags, stbte, ImColor, ImCos, ImGuiButtonFlags, ImGuiDebugLogFlags, ImGuiLocKey, ImU32, ExampleTreeFuncs, ImGuiListClipper, ImS16, _PathArcToFastExXY, ImGuiMultiSelectFlags, ImSin, ImGuiTabBarFlags, ImUpperPowerOfTwo, IM_F32_TO_INT8_SAT, ImFontAtlasPackGetRect, ImGuiMouseCursor, DockSettingsRenameNodeReferences, ExampleDualListBoxMT, IM_DRAWLIST_TEX_LINES_WIDTH_MAX, ImCeil, ImFabs, ImGuiCol, ImGuiSelectionBasicStorage, ImLengthSqr, ImS8, ImU8, ExampleAppPropertyEditorMT, ImGuiScrollFlags, ImGui_ImplLOVE_GetBackendData, ImLog, ExampleSelectionWithDeletionMT, CustomConstraints, ExampleAppLogMT, ImFontAtlasBuildInit, ImFontAtlasFontDestroyOutput, ImGuiComboFlags, ImGuiPopupFlags, ImGuiSliderFlags, ImTextClassifierSetCharClass, MyDocument, ShowExampleMenuFile, CalcCornerArcStepAndCount, ImFontAtlasBakedAddFontGlyph, ImFontAtlasPackAddRect, ImFontBaked_BuildLoadGlyph, ImFontConfig, ImGuiInputTextFlags, ImGuiStyle_Copy, ExampleAsset_s_current_sort_specs, ExampleMemberInfo, IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC, ImFontAtlasBuildNotifySetFont, ImFontAtlasBuildRenderBitmapFromString, ImFontAtlasFontDestroySourceData, ImFontAtlasFontSourceAddToFont, ImFontAtlasFontSourceInit, ImGuiTableColumn, stb_textedit_key, stbtt_GetGlyphBitmapBoxSubpixel, IM_FREE, ImDrawListSplitter, ImGuiDragDropFlags, ImGuiFocusedFlags, stb_text_locate_coord, stb_text_makeundo_insert, stb_text_makeundo_replace, stb_textedit_find_charpos, stbtt_GetGlyphShape, ImGuiTableColumnSortSpecs, ImGuiTableInstanceData, ImGuiTableSettings, stb_text_makeundo_delete, stb_text_redo, stb_text_undo, stb_textedit_click, stb_textedit_drag, stbtt_FindGlyphIndex, stbtt_GetFontOffsetForIndex, stbtt_GetFontVMetrics, stbtt_GetGlyphBitmapBox, stbtt_GetGlyphHMetrics, stbtt_InitFont, stbtt_MakeGlyphBitmapSubpixelPrefilter, stbtt_ScaleForPixelHeight, stbtt__GetGlyphInfoT2, stbtt__GetGlyphShapeT2, stbtt_fontinfo, ImGuiOldColumnData, ImGuiOldColumnFlags, ImGuiOldColumns, ImGuiTable, ImGuiTableColumnSettings, ImGuiTableSortSpecs, ImGuiTableTempData, ImGui_ImplLOVE_CreateTexture, ImGui_ImplLOVE_DestroyTexture, ImGui_ImplLOVE_Init, ImGui_ImplLOVE_NewFrame, ImGui_ImplLOVE_RenderDrawData, ImGui_ImplLOVE_Shutdown, ImGui_ImplLOVE_UpdateTexture, stbrp_init_target, IMGUI_TABLE_MAX_COLUMNS, IMSTB_TEXTEDIT_UNDOSTATECOUNT, IM_COL32_DISABLE, ImGui_ImplLove, STB_TEXTEDIT_K_BACKSPACE, STB_TEXTEDIT_K_DELETE, STB_TEXTEDIT_K_DOWN, STB_TEXTEDIT_K_LEFT, STB_TEXTEDIT_K_LINEEND, STB_TEXTEDIT_K_LINESTART, STB_TEXTEDIT_K_PGDOWN, STB_TEXTEDIT_K_PGUP, STB_TEXTEDIT_K_REDO, STB_TEXTEDIT_K_RIGHT, STB_TEXTEDIT_K_SHIFT, STB_TEXTEDIT_K_TEXTEND
|
||||
local type, mathMin, mathMax, mathFloor, mathCeil, bitOr, bitLShift = type, math.min, math.max, math.floor, math.ceil, bit32.bor, bit32.lshift
|
||||
local function IM_COL32(R, G, B, A) return (bitOr(bitLShift(A, 24 --[[IM_COL32_A_SHIFT]]), bitLShift(B, 16 --[[IM_COL32_B_SHIFT]]), bitLShift(G, 8 --[[IM_COL32_G_SHIFT]]), bitLShift(R, 0 --[[IM_COL32_R_SHIFT]]))) end
|
||||
|
||||
@@ -34342,6 +34342,28 @@ function ImFontAtlasTextureBlockCopy(src_tex, src_x, src_y, dst_tex, dst_x, dst_
|
||||
end
|
||||
end
|
||||
|
||||
--- @param dst_tex ImTextureData
|
||||
--- @param col ImU32
|
||||
function ImFontAtlasTextureBlockFill(dst_tex, dst_x, dst_y, w, h, col)
|
||||
if dst_tex.Format == 1 --[[ImTextureFormat.Alpha8]] then
|
||||
local col_a = bit32.band(bit32.rshift(col, 24 --[[IM_COL32_A_SHIFT]]), 0xFF)
|
||||
for y = 0, h - 1 do
|
||||
local p, base = dst_tex:GetPixelsAt(dst_x, dst_y + y)
|
||||
for i = base, base + w - 1 do p[i] = col_a end
|
||||
end
|
||||
else
|
||||
-- [Luau] Pixels is a byte table: write the 4 bytes of the little-endian ImU32
|
||||
local c0, c1, c2, c3 = bit32.band(col, 0xFF), bit32.band(bit32.rshift(col, 8), 0xFF), bit32.band(bit32.rshift(col, 16), 0xFF), bit32.band(bit32.rshift(col, 24), 0xFF)
|
||||
for y = 0, h - 1 do
|
||||
local p, i = dst_tex:GetPixelsAt(dst_x, dst_y + y)
|
||||
for _ = w, 1, -1 do
|
||||
p[i] = c0; p[i + 1] = c1; p[i + 2] = c2; p[i + 3] = c3
|
||||
i = i + 4
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- Queue texture block update for renderer backend
|
||||
--- @param tex ImTextureData
|
||||
--- @param x int
|
||||
@@ -34996,6 +35018,18 @@ function ImFontAtlasBuildSetupFontBakedBlanks(atlas, baked)
|
||||
end
|
||||
end
|
||||
|
||||
--- @param glyph ImFontGlyph
|
||||
function ImFontAtlasBakedDiscardFontGlyph(atlas, font, baked, glyph)
|
||||
if glyph.PackId ~= (-1) --[[ImFontAtlasRectId_Invalid]] then
|
||||
ImFontAtlasPackDiscardRect(atlas, glyph.PackId)
|
||||
glyph.PackId = (-1) --[[ImFontAtlasRectId_Invalid]]
|
||||
end
|
||||
local c = glyph.Codepoint
|
||||
assert(font.FallbackChar ~= c and font.EllipsisChar ~= c) -- Unsupported for simplicity
|
||||
baked.IndexLookup.Data[c + 1] = IM_FONTGLYPH_INDEX_UNUSED
|
||||
baked.IndexAdvanceX.Data[c + 1] = baked.FallbackAdvanceX
|
||||
end
|
||||
|
||||
--- @param atlas ImFontAtlas
|
||||
--- @param font ImFont
|
||||
--- @param font_size float
|
||||
@@ -35154,6 +35188,11 @@ function ImFontAtlasFontDestroyOutput(atlas, font)
|
||||
end
|
||||
end
|
||||
|
||||
function ImFontAtlasFontRebuildOutput(atlas, font)
|
||||
ImFontAtlasFontDestroyOutput(atlas, font)
|
||||
ImFontAtlasFontInitOutput(atlas, font)
|
||||
end
|
||||
|
||||
--- @param atlas ImFontAtlas
|
||||
--- @param src ImFontConfig
|
||||
--- @return boolean
|
||||
@@ -36040,6 +36079,32 @@ function ImFontAtlasBuildMain(atlas)
|
||||
atlas.TexIsBuilt = true
|
||||
end
|
||||
|
||||
-- [Luau] Ported but its call above stays disabled: the Roblox/LÖVE backends support RendererHasTextures.
|
||||
function ImFontAtlasBuildLegacyPreloadAllGlyphRanges(atlas)
|
||||
atlas.Builder.PreloadedAllGlyphsRanges = true
|
||||
for _, font in atlas.Fonts:iter() do
|
||||
local baked = font:GetFontBaked(font.LegacySize)
|
||||
if font.FallbackChar ~= 0 then
|
||||
baked:FindGlyph(font.FallbackChar)
|
||||
end
|
||||
if font.EllipsisChar ~= 0 then
|
||||
baked:FindGlyph(font.EllipsisChar)
|
||||
end
|
||||
for _, src in font.Sources:iter() do
|
||||
local ranges = src.GlyphRanges and src.GlyphRanges or atlas:GetGlyphRangesDefault()
|
||||
local i = 1
|
||||
while ranges[i] ~= 0 do
|
||||
local c = ranges[i]
|
||||
while c <= ranges[i + 1] and c <= 65535 --[[IM_UNICODE_CODEPOINT_MAX]] do
|
||||
baked:FindGlyph(c)
|
||||
c = c + 1
|
||||
end
|
||||
i = i + 2
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] ImTextureData
|
||||
-------------------------------------------------------------------------------
|
||||
@@ -36047,6 +36112,25 @@ end
|
||||
-- - ImTextureData:DestroyPixels()
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
--- @param status ImTextureStatus
|
||||
function ImTextureDataGetStatusName(status)
|
||||
if status == 0 --[[ImTextureStatus.OK]] then return "OK"
|
||||
elseif status == 1 --[[ImTextureStatus.Destroyed]] then return "Destroyed"
|
||||
elseif status == 2 --[[ImTextureStatus.WantCreate]] then return "WantCreate"
|
||||
elseif status == 3 --[[ImTextureStatus.WantUpdates]] then return "WantUpdates"
|
||||
elseif status == 4 --[[ImTextureStatus.WantDestroy]] then return "WantDestroy"
|
||||
end
|
||||
return "N/A"
|
||||
end
|
||||
|
||||
--- @param format ImTextureFormat
|
||||
function ImTextureDataGetFormatName(format)
|
||||
if format == 1 --[[ImTextureFormat.Alpha8]] then return "Alpha8"
|
||||
elseif format == 0 --[[ImTextureFormat.RGBA32]] then return "RGBA32"
|
||||
end
|
||||
return "N/A"
|
||||
end
|
||||
|
||||
function MT.ImTextureData:DestroyPixels()
|
||||
self.Pixels = nil
|
||||
self.UseColors = false
|
||||
@@ -36083,6 +36167,74 @@ function MT.ImTextureData:Create(format, w, h)
|
||||
self.UpdateRect.h = 0
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] ImFontAtlas: glyph ranges helpers
|
||||
-------------------------------------------------------------------------------
|
||||
-- - GetGlyphRangesDefault()
|
||||
-- [Luau] The obsolete GetGlyphRangesXXX() (IMGUI_DISABLE_OBSOLETE_FUNCTIONS) are not ported.
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
-- Retrieve list of range (2 int per range, values are inclusive)
|
||||
local GlyphRangesDefault =
|
||||
{
|
||||
0x0020, 0x00FF, -- Basic Latin + Latin Supplement
|
||||
0,
|
||||
}
|
||||
function MT.ImFontAtlas:GetGlyphRangesDefault()
|
||||
return GlyphRangesDefault
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] ImFontGlyphRangesBuilder
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
--- @param text ImString
|
||||
--- @param text_end? int # exclusive, 1-based
|
||||
function MT.ImFontGlyphRangesBuilder:AddText(text, text_end)
|
||||
if text_end == nil then
|
||||
text_end = #text + 1
|
||||
end
|
||||
local s = 1
|
||||
while s < text_end do
|
||||
local c_len, c = ImStd.ImTextCharFromUtf8(text, s, text_end)
|
||||
s = s + c_len
|
||||
if c_len == 0 then
|
||||
break
|
||||
end
|
||||
self:AddChar(c)
|
||||
end
|
||||
end
|
||||
|
||||
--- @param ranges ImWchar[] # 1-based, zero-terminated
|
||||
function MT.ImFontGlyphRangesBuilder:AddRanges(ranges)
|
||||
local i = 1
|
||||
while ranges[i] ~= 0 do
|
||||
local c = ranges[i]
|
||||
while c <= ranges[i + 1] and c <= 65535 --[[IM_UNICODE_CODEPOINT_MAX]] do
|
||||
self:AddChar(c)
|
||||
c = c + 1
|
||||
end
|
||||
i = i + 2
|
||||
end
|
||||
end
|
||||
|
||||
--- @param out_ranges ImVector<ImWchar>
|
||||
function MT.ImFontGlyphRangesBuilder:BuildRanges(out_ranges)
|
||||
local max_codepoint = 65535 --[[IM_UNICODE_CODEPOINT_MAX]]
|
||||
local n = 0
|
||||
while n <= max_codepoint do
|
||||
if self:GetBit(n) then
|
||||
out_ranges:push_back(n)
|
||||
while n < max_codepoint and self:GetBit(n + 1) do
|
||||
n = n + 1
|
||||
end
|
||||
out_ranges:push_back(n)
|
||||
end
|
||||
n = n + 1
|
||||
end
|
||||
out_ranges:push_back(0)
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] ImFontBaked, ImFont
|
||||
-------------------------------------------------------------------------------
|
||||
@@ -36152,6 +36304,21 @@ function MT.ImFont:ClearOutputData()
|
||||
self.LastBaked = nil
|
||||
end
|
||||
|
||||
-- API is designed this way to avoid exposing the 8K page size
|
||||
-- e.g. use with IsGlyphRangeUnused(0, 255)
|
||||
function MT.ImFont:IsGlyphRangeUnused(c_begin, c_last)
|
||||
local page_begin = math.floor(c_begin / 8192)
|
||||
local page_last = math.floor(c_last / 8192)
|
||||
for page_n = page_begin, page_last do
|
||||
if bit32.rshift(page_n, 3) < (65535 --[[IM_UNICODE_CODEPOINT_MAX]] + 1) / 8192 / 8 then -- sizeof(Used8kPagesMap)
|
||||
if bit32.band(self.Used8kPagesMap[bit32.rshift(page_n, 3) + 1] or 0, bit32.lshift(1, bit32.band(page_n, 7))) ~= 0 then
|
||||
return false
|
||||
end
|
||||
end
|
||||
end
|
||||
return true
|
||||
end
|
||||
|
||||
--- @param font_id ImGuiID
|
||||
--- @param baked_size float
|
||||
--- @param rasterizer_density float
|
||||
@@ -36319,6 +36486,14 @@ function MT.ImFont:GetFontBaked(size, density)
|
||||
return baked
|
||||
end
|
||||
|
||||
-- Makes 'from_codepoint' character points to 'to_codepoint' glyph.
|
||||
-- [Luau] AddRemapCodepointToGlyphIndex() not ported: needs the 1.93 loader split (FontSrcGetGlyphIndexFromCodepoint).
|
||||
function MT.ImFont:AddRemapCodepoint(from_codepoint, to_codepoint)
|
||||
local data = to_codepoint
|
||||
assert(bit32.band(data, bit32.lshift(1, 31)) == 0)
|
||||
self.RemapPairs[from_codepoint] = data
|
||||
end
|
||||
|
||||
--- @param atlas ImFontAtlas
|
||||
--- @param font ImFont
|
||||
--- @param c ImWchar
|
||||
@@ -36326,7 +36501,7 @@ end
|
||||
--- @nodiscard
|
||||
local function ImFontAtlas_FontHookRemapCodepoint(atlas, font, c)
|
||||
-- IM_UNUSED(atlas)
|
||||
if #font.RemapPairs > 0 then
|
||||
if next(font.RemapPairs) ~= nil then -- [Luau] font->RemapPairs.Data.Size != 0 (RemapPairs is a hash table)
|
||||
local ret = font.RemapPairs[c]
|
||||
return (ret ~= nil) and ret or c
|
||||
end
|
||||
@@ -36721,6 +36896,16 @@ function ImFontCalcWordWrapPositionEx_Uncached(baked, size, text, pos, text_end,
|
||||
return s
|
||||
end
|
||||
|
||||
--- @param size float
|
||||
--- @param text ImString
|
||||
--- @param pos int # [Luau] 1-based start position (C++ 'text' pointer)
|
||||
--- @param text_end int # exclusive
|
||||
--- @param wrap_width float
|
||||
--- @return int
|
||||
function MT.ImFont:CalcWordWrapPosition(size, text, pos, text_end, wrap_width)
|
||||
return ImFontCalcWordWrapPositionEx(self, size, text, pos, text_end, wrap_width, 0 --[[ImDrawTextFlags.None]])
|
||||
end
|
||||
|
||||
--- @param font ImFont
|
||||
--- @param size float
|
||||
--- @param max_width float
|
||||
@@ -37048,6 +37233,25 @@ function MT.ImFontAtlas:AddFont(font_cfg_in)
|
||||
return font
|
||||
end
|
||||
|
||||
-- Default font TTF is compressed with stb_compress then base85 encoded (see misc/fonts/binary_to_compressed_c.cpp for encoder)
|
||||
local stb_decompress_length
|
||||
local stb_decompress
|
||||
local function Decode85Byte(c) return (c >= 92) and (c - 36) or (c - 35) end -- c >= '\\'
|
||||
--- @param src string
|
||||
--- @param dst buffer
|
||||
local function Decode85(src, dst)
|
||||
local d = 0
|
||||
local src_len = #src
|
||||
local s = 1
|
||||
while s + 4 <= src_len do -- [Luau] while (*src): stop at the last complete 5-char group
|
||||
local b0, b1, b2, b3, b4 = string.byte(src, s, s + 4)
|
||||
local tmp = (Decode85Byte(b0) + 85 * (Decode85Byte(b1) + 85 * (Decode85Byte(b2) + 85 * (Decode85Byte(b3) + 85 * Decode85Byte(b4))))) % 4294967296
|
||||
buffer.writeu8(dst, d + 0, tmp % 256); buffer.writeu8(dst, d + 1, math.floor(tmp / 256) % 256); buffer.writeu8(dst, d + 2, math.floor(tmp / 65536) % 256); buffer.writeu8(dst, d + 3, math.floor(tmp / 16777216) % 256) -- We can't assume little-endianness.
|
||||
s = s + 5
|
||||
d = d + 4
|
||||
end
|
||||
end
|
||||
|
||||
-- This duplicates some of the logic in UpdateFontsNewFrame() which is a bit chicken-and-eggy/tricky to extract due to variety of codepaths and possible initialization ordering.
|
||||
--- @param ctx ImGuiContext
|
||||
--- @return float
|
||||
@@ -37081,9 +37285,68 @@ function MT.ImFontAtlas:AddFontFromMemoryTTF(font_data, font_data_size, size_pix
|
||||
return self:AddFont(font_cfg)
|
||||
end
|
||||
|
||||
-- TODO: GetDefaultCompressedFontDataProggyClean, GetDefaultCompressedFontDataProggyForever
|
||||
function MT.ImFontAtlas:AddFontFromMemoryCompressedTTF()
|
||||
-- TODO:
|
||||
--- @param compressed_ttf_data buffer|string|ImU8[] # [Luau] stb_compress() output: buffer, string or 1-based byte table
|
||||
--- @param compressed_ttf_size int
|
||||
function MT.ImFontAtlas:AddFontFromMemoryCompressedTTF(compressed_ttf_data, compressed_ttf_size, size_pixels, font_cfg_template, glyph_ranges)
|
||||
-- [Luau] normalize input to a buffer
|
||||
if type(compressed_ttf_data) == "string" then
|
||||
compressed_ttf_data = buffer.fromstring(compressed_ttf_data)
|
||||
elseif type(compressed_ttf_data) == "table" then
|
||||
local b = buffer.create(compressed_ttf_size)
|
||||
for n = 1, compressed_ttf_size do buffer.writeu8(b, n - 1, compressed_ttf_data[n]) end
|
||||
compressed_ttf_data = b
|
||||
end
|
||||
local buf_decompressed_size = stb_decompress_length(compressed_ttf_data)
|
||||
local buf_decompressed_data = buffer.create(buf_decompressed_size)
|
||||
stb_decompress(buf_decompressed_data, compressed_ttf_data, compressed_ttf_size)
|
||||
|
||||
-- [Luau] FontData is a 1-based byte table (see stbtt / ImFileLoadToMemory)
|
||||
local ttf_data = table.create and table.create(buf_decompressed_size) or {}
|
||||
for n = 1, buf_decompressed_size do ttf_data[n] = buffer.readu8(buf_decompressed_data, n - 1) end
|
||||
|
||||
local font_cfg = font_cfg_template and font_cfg_template or ImFontConfig()
|
||||
assert(font_cfg.FontData == nil)
|
||||
font_cfg.FontDataOwnedByAtlas = true
|
||||
return self:AddFontFromMemoryTTF(ttf_data, buf_decompressed_size, size_pixels or 0.0, font_cfg, glyph_ranges)
|
||||
end
|
||||
|
||||
--- @param compressed_ttf_data_base85 string
|
||||
function MT.ImFontAtlas:AddFontFromMemoryCompressedBase85TTF(compressed_ttf_data_base85, size_pixels, font_cfg, glyph_ranges)
|
||||
local compressed_ttf_size = math.floor((#compressed_ttf_data_base85 + 4) / 5) * 4
|
||||
local compressed_ttf = buffer.create(compressed_ttf_size)
|
||||
Decode85(compressed_ttf_data_base85, compressed_ttf)
|
||||
local font = self:AddFontFromMemoryCompressedTTF(compressed_ttf, compressed_ttf_size, size_pixels, font_cfg, glyph_ranges)
|
||||
return font
|
||||
end
|
||||
|
||||
--- @param font ImFont
|
||||
function MT.ImFontAtlas:RemoveFont(font)
|
||||
assert(not self.Locked, "Cannot modify a locked ImFontAtlas!")
|
||||
|
||||
ImFontAtlasFontDestroyOutput(self, font)
|
||||
for _, src in font.Sources:iter() do
|
||||
ImFontAtlasFontDestroySourceData(self, src)
|
||||
end
|
||||
local src_n = 1
|
||||
while src_n <= self.Sources.Size do
|
||||
if self.Sources.Data[src_n].DstFont == font then
|
||||
self.Sources:erase(src_n)
|
||||
else
|
||||
src_n = src_n + 1
|
||||
end
|
||||
end
|
||||
|
||||
local removed = self.Fonts:find_erase(font)
|
||||
assert(removed)
|
||||
|
||||
ImFontAtlasBuildUpdatePointers(self)
|
||||
|
||||
font.OwnerAtlas = nil
|
||||
|
||||
-- Notify external systems
|
||||
local new_current_font = nil
|
||||
if self.Fonts.Size > 0 then new_current_font = self.Fonts.Data[1] end
|
||||
ImFontAtlasBuildNotifySetFont(self, font, new_current_font)
|
||||
end
|
||||
|
||||
function MT.ImFontAtlas:AddFontFromFileTTF(filename, size_pixels, font_cfg_template, glyph_ranges)
|
||||
@@ -37239,6 +37502,13 @@ function MT.ImFontAtlas:AddCustomRect(width, height, out_r)
|
||||
return r_id
|
||||
end
|
||||
|
||||
function MT.ImFontAtlas:RemoveCustomRect(id)
|
||||
if ImFontAtlasPackGetRectSafe(self, id) == nil then
|
||||
return
|
||||
end
|
||||
ImFontAtlasPackDiscardRect(self, id)
|
||||
end
|
||||
|
||||
local function IM_NORMALIZE2F_OVER_ZERO(VX, VY)
|
||||
local d2 = VX * VX + VY * VY
|
||||
if d2 > 0.0 then
|
||||
@@ -41251,6 +41521,136 @@ function MT.ImDrawList:PathFillConcave(col)
|
||||
self._Path.Size = 0
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] Decompression code
|
||||
-------------------------------------------------------------------------------
|
||||
-- Compressed with stb_compress() then converted to a C array and encoded as base85.
|
||||
-- Use the program in misc/fonts/binary_to_compressed_c.cpp to create the array from a TTF file.
|
||||
-- The purpose of encoding as base85 instead of "0x00,0x01,..." style is only save on _source code_ size.
|
||||
-- Decompression from stb.h (public domain) by Sean Barrett https://github.com/nothings/stb/blob/master/stb.h
|
||||
-- [Luau] Input and output are buffers, pointers are 0-based byte offsets into them.
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
do
|
||||
local readu8 = buffer.readu8
|
||||
local writeu8 = buffer.writeu8
|
||||
|
||||
--- @param input buffer
|
||||
function stb_decompress_length(input)
|
||||
return readu8(input, 8) * 16777216 + readu8(input, 9) * 65536 + readu8(input, 10) * 256 + readu8(input, 11)
|
||||
end
|
||||
|
||||
local stb__barrier_out_e, stb__barrier_out_b
|
||||
local stb__barrier_in_b
|
||||
local stb__dout
|
||||
local stb__out, stb__in -- [Luau] buffers the offsets above point into
|
||||
local function stb__match(data, length)
|
||||
-- INVERSE of memmove... write each byte before copying the next...
|
||||
assert(stb__dout + length <= stb__barrier_out_e)
|
||||
if stb__dout + length > stb__barrier_out_e then stb__dout = stb__dout + length; return end
|
||||
if data < stb__barrier_out_b then stb__dout = stb__barrier_out_e + 1; return end
|
||||
if stb__dout - data >= length then -- [Luau] no overlap: block copy
|
||||
buffer.copy(stb__out, stb__dout, stb__out, data, length)
|
||||
stb__dout = stb__dout + length
|
||||
return
|
||||
end
|
||||
local out = stb__out
|
||||
local dout = stb__dout
|
||||
for n = 0, length - 1 do writeu8(out, dout + n, readu8(out, data + n)) end
|
||||
stb__dout = dout + length
|
||||
end
|
||||
|
||||
local function stb__lit(data, length)
|
||||
assert(stb__dout + length <= stb__barrier_out_e)
|
||||
if stb__dout + length > stb__barrier_out_e then stb__dout = stb__dout + length; return end
|
||||
if data < stb__barrier_in_b then stb__dout = stb__barrier_out_e + 1; return end
|
||||
buffer.copy(stb__out, stb__dout, stb__in, data, length)
|
||||
stb__dout = stb__dout + length
|
||||
end
|
||||
|
||||
local function stb__in2(i, x) return readu8(stb__in, i + x) * 256 + readu8(stb__in, i + x + 1) end
|
||||
local function stb__in3(i, x) return readu8(stb__in, i + x) * 65536 + stb__in2(i, x + 1) end
|
||||
local function stb__in4(i, x) return readu8(stb__in, i + x) * 16777216 + stb__in3(i, x + 1) end
|
||||
|
||||
local function stb_decompress_token(i)
|
||||
local i0 = readu8(stb__in, i)
|
||||
if i0 >= 0x20 then -- use fewer if's for cases that expand small
|
||||
if i0 >= 0x80 then stb__match(stb__dout - readu8(stb__in, i + 1) - 1, i0 - 0x80 + 1); i = i + 2
|
||||
elseif i0 >= 0x40 then stb__match(stb__dout - (stb__in2(i, 0) - 0x4000 + 1), readu8(stb__in, i + 2) + 1); i = i + 3
|
||||
else --[[ *i >= 0x20 ]] stb__lit(i + 1, i0 - 0x20 + 1); i = i + 1 + (i0 - 0x20 + 1)
|
||||
end
|
||||
else -- more ifs for cases that expand large, since overhead is amortized
|
||||
if i0 >= 0x18 then stb__match(stb__dout - (stb__in3(i, 0) - 0x180000 + 1), readu8(stb__in, i + 3) + 1); i = i + 4
|
||||
elseif i0 >= 0x10 then stb__match(stb__dout - (stb__in3(i, 0) - 0x100000 + 1), stb__in2(i, 3) + 1); i = i + 5
|
||||
elseif i0 >= 0x08 then stb__lit(i + 2, stb__in2(i, 0) - 0x0800 + 1); i = i + 2 + (stb__in2(i, 0) - 0x0800 + 1)
|
||||
elseif i0 == 0x07 then stb__lit(i + 3, stb__in2(i, 1) + 1); i = i + 3 + (stb__in2(i, 1) + 1)
|
||||
elseif i0 == 0x06 then stb__match(stb__dout - (stb__in3(i, 1) + 1), readu8(stb__in, i + 4) + 1); i = i + 5
|
||||
elseif i0 == 0x04 then stb__match(stb__dout - (stb__in3(i, 1) + 1), stb__in2(i, 4) + 1); i = i + 6
|
||||
end
|
||||
end
|
||||
return i
|
||||
end
|
||||
|
||||
--- @param buf buffer
|
||||
--- @param buflen int
|
||||
local function stb_adler32(adler32, buf, buflen)
|
||||
local ADLER_MOD = 65521
|
||||
local s1 = adler32 % 65536
|
||||
local s2 = math.floor(adler32 / 65536)
|
||||
local blocklen = buflen % 5552
|
||||
|
||||
local p = 0
|
||||
while buflen > 0 do
|
||||
for _ = 1, blocklen do
|
||||
s1 = s1 + readu8(buf, p); s2 = s2 + s1
|
||||
p = p + 1
|
||||
end
|
||||
|
||||
s1 = s1 % ADLER_MOD; s2 = s2 % ADLER_MOD
|
||||
buflen = buflen - blocklen
|
||||
blocklen = 5552
|
||||
end
|
||||
return s2 * 65536 + s1
|
||||
end
|
||||
|
||||
--- @param output buffer
|
||||
--- @param i buffer
|
||||
function stb_decompress(output, i, length)
|
||||
stb__in = i
|
||||
if stb__in4(0, 0) ~= 0x57bC0000 then return 0 end
|
||||
if stb__in4(0, 4) ~= 0 then return 0 end -- error! stream is > 4GB
|
||||
local olen = stb_decompress_length(i)
|
||||
stb__barrier_in_b = 0
|
||||
stb__barrier_out_e = olen
|
||||
stb__barrier_out_b = 0
|
||||
stb__out = output
|
||||
local p = 16
|
||||
|
||||
stb__dout = 0
|
||||
while true do
|
||||
local old_p = p
|
||||
p = stb_decompress_token(p)
|
||||
if p == old_p then
|
||||
if readu8(i, p) == 0x05 and readu8(i, p + 1) == 0xfa then
|
||||
assert(stb__dout == olen)
|
||||
if stb__dout ~= olen then return 0 end
|
||||
if stb_adler32(1, output, olen) ~= stb__in4(p, 2) then
|
||||
return 0
|
||||
end
|
||||
return olen
|
||||
else
|
||||
assert(false) -- NOTREACHED
|
||||
return 0
|
||||
end
|
||||
end
|
||||
assert(stb__dout <= olen)
|
||||
if stb__dout > olen then
|
||||
return 0
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return true -- [Roblox] ModuleScripts must return exactly one value
|
||||
end
|
||||
|
||||
@@ -42395,6 +42795,34 @@ function ImFontGlyph()
|
||||
}
|
||||
end
|
||||
|
||||
-- Helper to build glyph ranges from text/string data. Feed your application strings/characters to it then call BuildRanges().
|
||||
-- This is essentially a tightly packed of vector of 64k booleans = 8KB storage.
|
||||
--- @class ImFontGlyphRangesBuilder
|
||||
--- @field UsedChars ImVector<ImU32> # Store 1-bit per Unicode code point (0=unused, 1=used)
|
||||
MT.ImFontGlyphRangesBuilder = {}
|
||||
MT.ImFontGlyphRangesBuilder.__index = MT.ImFontGlyphRangesBuilder
|
||||
|
||||
--- @return ImFontGlyphRangesBuilder
|
||||
--- @nodiscard
|
||||
function ImFontGlyphRangesBuilder()
|
||||
local this = setmetatable({ UsedChars = ImVector() }, MT.ImFontGlyphRangesBuilder)
|
||||
this:Clear()
|
||||
return this
|
||||
end
|
||||
|
||||
function MT.ImFontGlyphRangesBuilder:Clear()
|
||||
local size_in_bytes = (65535 --[[IM_UNICODE_CODEPOINT_MAX]] + 1) / 8
|
||||
self.UsedChars:resize(size_in_bytes / 4)
|
||||
local data = self.UsedChars.Data
|
||||
for i = 1, self.UsedChars.Size do data[i] = 0 end
|
||||
end
|
||||
-- Get bit n in the array
|
||||
function MT.ImFontGlyphRangesBuilder:GetBit(n) local off = bit32.rshift(n, 5); local mask = bit32.lshift(1, bit32.band(n, 31)); return bit32.band(self.UsedChars.Data[off + 1], mask) ~= 0 end
|
||||
-- Set bit n in the array
|
||||
function MT.ImFontGlyphRangesBuilder:SetBit(n) local off = bit32.rshift(n, 5); local mask = bit32.lshift(1, bit32.band(n, 31)); self.UsedChars.Data[off + 1] = bit32.bor(self.UsedChars.Data[off + 1], mask) end
|
||||
-- Add character
|
||||
function MT.ImFontGlyphRangesBuilder:AddChar(c) self:SetBit(c) end
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
-- [SECTION] ImGuiIO
|
||||
-------------------------------------------------------------------------------
|
||||
@@ -70879,6 +71307,7 @@ return {
|
||||
ImFontAtlasBakedAddFontGlyph = ImFontAtlasBakedAddFontGlyph,
|
||||
ImFontAtlasBakedAddFontGlyphAdvancedX = ImFontAtlasBakedAddFontGlyphAdvancedX,
|
||||
ImFontAtlasBakedDiscard = ImFontAtlasBakedDiscard,
|
||||
ImFontAtlasBakedDiscardFontGlyph = ImFontAtlasBakedDiscardFontGlyph,
|
||||
ImFontAtlasBakedGetClosestMatch = ImFontAtlasBakedGetClosestMatch,
|
||||
ImFontAtlasBakedGetId = ImFontAtlasBakedGetId,
|
||||
ImFontAtlasBakedGetOrAdd = ImFontAtlasBakedGetOrAdd,
|
||||
@@ -70886,6 +71315,7 @@ return {
|
||||
ImFontAtlasBuildClear = ImFontAtlasBuildClear,
|
||||
ImFontAtlasBuildDestroy = ImFontAtlasBuildDestroy,
|
||||
ImFontAtlasBuildInit = ImFontAtlasBuildInit,
|
||||
ImFontAtlasBuildLegacyPreloadAllGlyphRanges = ImFontAtlasBuildLegacyPreloadAllGlyphRanges,
|
||||
ImFontAtlasBuildMain = ImFontAtlasBuildMain,
|
||||
ImFontAtlasBuildNotifySetFont = ImFontAtlasBuildNotifySetFont,
|
||||
ImFontAtlasBuildRenderBitmapFromString = ImFontAtlasBuildRenderBitmapFromString,
|
||||
@@ -70905,6 +71335,7 @@ return {
|
||||
ImFontAtlasFontDestroySourceData = ImFontAtlasFontDestroySourceData,
|
||||
ImFontAtlasFontDiscardBakes = ImFontAtlasFontDiscardBakes,
|
||||
ImFontAtlasFontInitOutput = ImFontAtlasFontInitOutput,
|
||||
ImFontAtlasFontRebuildOutput = ImFontAtlasFontRebuildOutput,
|
||||
ImFontAtlasFontSourceAddToFont = ImFontAtlasFontSourceAddToFont,
|
||||
ImFontAtlasFontSourceInit = ImFontAtlasFontSourceInit,
|
||||
ImFontAtlasGetMouseCursorTexData = ImFontAtlasGetMouseCursorTexData,
|
||||
@@ -70924,6 +71355,7 @@ return {
|
||||
ImFontAtlasTextureAdd = ImFontAtlasTextureAdd,
|
||||
ImFontAtlasTextureBlockConvert = ImFontAtlasTextureBlockConvert,
|
||||
ImFontAtlasTextureBlockCopy = ImFontAtlasTextureBlockCopy,
|
||||
ImFontAtlasTextureBlockFill = ImFontAtlasTextureBlockFill,
|
||||
ImFontAtlasTextureBlockPostProcess = ImFontAtlasTextureBlockPostProcess,
|
||||
ImFontAtlasTextureBlockPostProcessMultiply = ImFontAtlasTextureBlockPostProcessMultiply,
|
||||
ImFontAtlasTextureBlockQueueUpload = ImFontAtlasTextureBlockQueueUpload,
|
||||
@@ -70942,6 +71374,7 @@ return {
|
||||
ImFontConfig = ImFontConfig,
|
||||
ImFontFlags = ImFontFlags,
|
||||
ImFontGlyph = ImFontGlyph,
|
||||
ImFontGlyphRangesBuilder = ImFontGlyphRangesBuilder,
|
||||
ImFontLoader = ImFontLoader,
|
||||
ImFontStackData = ImFontStackData,
|
||||
ImFormatString = ImFormatString,
|
||||
@@ -71155,6 +71588,8 @@ return {
|
||||
ImTextInitClassifiers = ImTextInitClassifiers,
|
||||
ImTextureData = ImTextureData,
|
||||
ImTextureDataGetFormatBytesPerPixel = ImTextureDataGetFormatBytesPerPixel,
|
||||
ImTextureDataGetFormatName = ImTextureDataGetFormatName,
|
||||
ImTextureDataGetStatusName = ImTextureDataGetStatusName,
|
||||
ImTextureDataUpdateNewFrame = ImTextureDataUpdateNewFrame,
|
||||
ImTextureFormat = ImTextureFormat,
|
||||
ImTextureID_Invalid = ImTextureID_Invalid,
|
||||
@@ -71239,6 +71674,8 @@ return {
|
||||
UINT_MAX = UINT_MAX,
|
||||
VTX_STRIDE = VTX_STRIDE,
|
||||
_PathArcToFastExXY = _PathArcToFastExXY,
|
||||
stb_decompress = stb_decompress,
|
||||
stb_decompress_length = stb_decompress_length,
|
||||
stb_text_locate_coord = stb_text_locate_coord,
|
||||
stb_text_makeundo_delete = stb_text_makeundo_delete,
|
||||
stb_text_makeundo_insert = stb_text_makeundo_insert,
|
||||
|
||||
Reference in New Issue
Block a user