Added emergency catch, for font sizing

This commit is contained in:
Jon Michael Aanes 2018-06-11 16:21:26 +02:00
parent f351bb0623
commit a97b9a8b18

View File

@ -77,12 +77,15 @@ local function generate_bait_link()
end end
local function fit_font_to_line_height (font_name, height) local function fit_font_to_line_height (font_name, height)
assert(type(font_name) == 'string')
assert(type(height) == 'number')
--
local size_min, size_max = 1, 50 local size_min, size_max = 1, 50
while true do while true do
local size_guess = math.floor((size_max + size_min)/2) local size_guess = math.floor((size_max + size_min)/2)
assert(size_min <= size_guess and size_guess <= size_max) assert(size_min <= size_guess and size_guess <= size_max)
local font = assert(imlib.font.load(font_name..'/'..size_guess)) local font = assert(imlib.font.load(font_name..'/'..size_guess))
if size_guess == size_min then return font end if size_guess == size_min then return font, size_guess end
local text_w, text_h = font:get_size 'k' local text_w, text_h = font:get_size 'k'
-- --
if text_h <= height then size_min = size_guess if text_h <= height then size_min = size_guess
@ -92,13 +95,21 @@ local function fit_font_to_line_height (font_name, height)
return nil return nil
end end
local function load_font_of_size (font_name, size)
return assert(imlib.font.load(font_name..'/'..size))
end
local function determine_required_font_size (font_name, text, width) local function determine_required_font_size (font_name, text, width)
assert(type(font_name) == 'string')
assert(type(text) == 'string')
assert(type(width) == 'number')
--
local size_min, size_max = 1, 50 local size_min, size_max = 1, 50
while true do while true do
local size_guess = math.floor((size_max + size_min)/2) local size_guess = math.floor((size_max + size_min)/2)
assert(size_min <= size_guess and size_guess <= size_max) assert(size_min <= size_guess and size_guess <= size_max)
local font = assert(imlib.font.load(font_name..'/'..size_guess)) local font = load_font_of_size(font_name, size_guess)
if size_guess == size_min then return font end if size_guess == size_min then return font, size_guess end
local text_w, text_h = font:get_size(text) local text_w, text_h = font:get_size(text)
-- --
if text_w <= width then size_min = size_guess if text_w <= width then size_min = size_guess
@ -147,7 +158,7 @@ end
local function determine_font_and_lines_for_box (font_name, text, width, height) local function determine_font_and_lines_for_box (font_name, text, width, height)
local num_lines, last_actual, actual_lines = 1, nil, nil local num_lines, last_actual, actual_lines = 1, nil, nil
for iteration = 1, 10 do for iteration = 1, 100 do
local estimate_font = determine_required_font_size(font_name, text, width * num_lines) local estimate_font = determine_required_font_size(font_name, text, width * num_lines)
local line_height = select(2, estimate_font:get_size(text)) local line_height = select(2, estimate_font:get_size(text))
@ -167,9 +178,19 @@ local function determine_font_and_lines_for_box (font_name, text, width, height)
end end
assert(actual_lines) assert(actual_lines)
local actual_font = fit_font_to_line_height(font_name, height / #actual_lines) -- Find final font size
local _, min_font_size = fit_font_to_line_height(font_name, height / #actual_lines)
for _, line in ipairs(actual_lines) do
min_font_size = math.min(min_font_size, select(2, determine_required_font_size(font_name, line, width)))
end
local actual_font = load_font_of_size(font_name, min_font_size)
-- Assertions and error correction
if (#actual_lines * select(2, actual_font:get_size(text)) < height) then
io.write(' !! Performed bad fitting of text: '..text..'\n')
actual_font, actual_lines = determine_required_font_size(font_name, text, width), {text}
end
assert(#actual_lines * select(2, actual_font:get_size(text)) < height)
return actual_font, actual_lines return actual_font, actual_lines
end end
@ -400,6 +421,7 @@ local function generate_brain_explosion_image (topics)
assert(type(topics) == 'table' and 1 <= #topics and #topics <= BRAIN_MAX_EXPLOSION_TOPICS) assert(type(topics) == 'table' and 1 <= #topics and #topics <= BRAIN_MAX_EXPLOSION_TOPICS)
-- --
local base_img = imlib.image.new(BRAIN_ROW_WIDTH * 2, BRAIN_ROW_HEIGHT * #topics) local base_img = imlib.image.new(BRAIN_ROW_WIDTH * 2, BRAIN_ROW_HEIGHT * #topics)
base_img:fill_rectangle(0, 0, BRAIN_ROW_WIDTH * 2, BRAIN_ROW_HEIGHT * #topics, COLOR_WHITE)
local font_name = choose_random_font() local font_name = choose_random_font()
-- --
for i, topic_info in ipairs(topics) do for i, topic_info in ipairs(topics) do