Status bar: dynamic filler (#13702)
Some checks failed
macos / macOS 13 x86-64 🔨15.2 🎯10.15 (push) Has been cancelled
macos / macOS 14 ARM64 🔨15.4 🎯11.0 (push) Has been cancelled

This commit is contained in:
hius07
2025-05-01 16:50:23 +03:00
committed by GitHub
parent 8b1605bb49
commit 75f49b135f

View File

@@ -49,6 +49,7 @@ local MODE = {
custom_text = 17,
book_author = 18,
page_turning_inverted = 19, -- includes both page-turn-button and swipe-and-tap inversion
dynamic_filler = 20,
}
local symbol_prefix = {
@@ -133,7 +134,8 @@ if BD.mirroredUILayout() then
end
-- functions that generates footer text for each mode
local footerTextGeneratorMap = {
local footerTextGeneratorMap
footerTextGeneratorMap = {
empty = function() return "" end,
frontlight = function(footer)
local symbol_type = footer.settings.item_prefix
@@ -412,6 +414,42 @@ local footerTextGeneratorMap = {
local merge = footer.custom_text:gsub(" ", ""):len() == 0
return footer.custom_text:rep(footer.custom_text_repetitions), merge
end,
dynamic_filler = function(footer)
local max_width = footer[1]:getSize().w - 2 * footer.horizontal_margin
-- when the filler is between other items, it replaces the separator
local text, is_filler_inside = footer:genAllFooterText(footerTextGeneratorMap.dynamic_filler)
local tmp = TextWidget:new{
text = text,
face = footer.footer_text_face,
bold = footer.settings.text_font_bold,
}
local text_width = tmp:getSize().w
tmp:free()
if footer.separator_width == nil then
tmp = TextWidget:new{
text = footer:genSeparator(),
face = footer.footer_text_face,
bold = footer.settings.text_font_bold,
}
footer.separator_width = tmp:getSize().w
tmp:free()
end
local separator_width = is_filler_inside and footer.separator_width or 0
local filler_space = "\u{200A}" -- HAIR SPACE
if footer.filler_space_width == nil then
tmp = TextWidget:new{
text = filler_space,
face = footer.footer_text_face,
bold = footer.settings.text_font_bold,
}
footer.filler_space_width = tmp:getSize().w
tmp:free()
end
local filler_nb = math.floor((max_width - text_width + separator_width) / footer.filler_space_width)
if filler_nb > 0 then
return filler_space:rep(filler_nb), true
end
end,
}
local ReaderFooter = WidgetContainer:extend{
@@ -980,6 +1018,7 @@ function ReaderFooter:textOptionTitles(option)
custom_text = T(_("Custom text (long-press to edit): \'%1\'%2"), self.custom_text,
self.custom_text_repetitions > 1 and
string.format(" × %d", self.custom_text_repetitions) or ""),
dynamic_filler = _("Dynamic filler"),
}
return option_titles[option]
end
@@ -1372,6 +1411,7 @@ function ReaderFooter:addToMainMenu(menu_items)
table.insert(footer_items, getMinibarOption("book_title"))
table.insert(footer_items, getMinibarOption("book_chapter"))
table.insert(footer_items, getMinibarOption("custom_text"))
table.insert(footer_items, getMinibarOption("dynamic_filler"))
-- configure footer_items
table.insert(sub_items, {
@@ -1500,6 +1540,8 @@ With this feature enabled, the current page is factored in, resulting in the cou
bold = self.settings.text_font_bold,
}
self.text_container[1] = self.footer_text
self.separator_width = nil
self.filler_space_width = nil
self:refreshFooter(true, true)
if touchmenu_instance then touchmenu_instance:updateItems() end
end,
@@ -1522,6 +1564,8 @@ With this feature enabled, the current page is factored in, resulting in the cou
bold = self.settings.text_font_bold,
}
self.text_container[1] = self.footer_text
self.separator_width = nil
self.filler_space_width = nil
self:refreshFooter(true, true)
end,
},
@@ -1823,6 +1867,7 @@ function ReaderFooter:genItemSeparatorMenuItems(value)
end,
callback = function()
self.settings.items_separator = value
self.separator_width = nil
self:refreshFooter(true)
end,
}
@@ -1922,16 +1967,23 @@ function ReaderFooter:genSeparator()
or (self.settings.item_prefix == "compact_items" and " " or " ")
end
function ReaderFooter:genAllFooterText()
function ReaderFooter:genAllFooterText(gen_to_skip)
local info = {}
-- We need to BD.wrap() all items and separators, so we're
-- sure they are laid out in our order (reversed in RTL),
-- without ordering by the RTL Bidi algorithm.
local prev_had_merge
local count = 0 -- total number of visible items
local skipped_idx, prev_had_merge
for _, gen in ipairs(self.footerTextGenerators) do
if gen == gen_to_skip then
count = count + 1
skipped_idx = count
goto continue
end
-- Skip empty generators, so they don't generate bogus separators
local text, merge = gen(self)
if text and text ~= "" then
count = count + 1
if self.settings.item_prefix == "compact_items" then
-- remove whitespace from footer items if symbol_type is compact_items
-- use a hair-space to avoid issues with RTL display
@@ -1950,8 +2002,9 @@ function ReaderFooter:genAllFooterText()
table.insert(info, BD.wrap(text))
end
end
::continue::
end
return table.concat(info, BD.wrap(self:genSeparator()))
return table.concat(info, BD.wrap(self:genSeparator())), skipped_idx ~= 1 and skipped_idx ~= count
end
function ReaderFooter:setTocMarkers(reset)