Update Rich text style params

This commit is contained in:
Insality
2023-08-05 19:01:06 +03:00
parent 5a0cf42e3d
commit 628723386e
8 changed files with 123 additions and 83 deletions

View File

@@ -13,9 +13,6 @@ local utf8 = utf8 or utf8_lua
local M = {}
M.ADJUST_STEPS = 20
M.ADJUST_SCALE_DELTA = 0.02
-- Trim spaces on string start
local function ltrim(text)
return text:match('^%s*(.*)')
@@ -144,12 +141,13 @@ local function measure_node(word, settings, previous_word)
end
--- Create rich text gui nodes from text
-- @param text The text to create rich text nodes from
-- @param settings Optional settings table (refer to documentation for details)
-- @return words
-- @return metrics
function M.create(text, settings)
-- Create rich text gui nodes from text
--- @param text string The text to create rich text nodes from
--- @param settings table Optional settings table (refer to documentation for details)
--- @param style druid.rich_text.style
--- @return words
--- @return metrics
function M.create(text, settings, style)
assert(text, "You must provide a text")
-- default settings for a word
@@ -178,12 +176,11 @@ function M.create(text, settings)
image_color = gui.get_color(settings.node_prefab),
default_animation = nil,
-- Tags
anchor = nil,
br = nil,
nobr = nil,
}
local parsed_words = parser.parse(text, word_params)
local parsed_words = parser.parse(text, word_params, style)
local lines = M._split_on_lines(parsed_words, settings)
local lines_metrics = M._position_lines(lines, settings)
M._update_nodes(lines, settings)
@@ -450,7 +447,8 @@ end
---@param words druid.rich_text.word[]
---@param settings druid.rich_text.settings
---@param lines_metrics druid.rich_text.lines_metrics
function M.adjust_to_area(words, settings, lines_metrics)
---@param style druid.rich_text.style
function M.adjust_to_area(words, settings, lines_metrics, style)
local last_line_metrics = lines_metrics
if not settings.is_multiline then
@@ -459,7 +457,7 @@ function M.adjust_to_area(words, settings, lines_metrics)
end
else
-- Multiline adjusting is very tricky stuff...
-- It's do a lot of calculations, beware!
-- It's doing a lot of calculations, beware!
if lines_metrics.text_width > settings.width or lines_metrics.text_height > settings.height then
local scale_koef = math.sqrt(settings.height / lines_metrics.text_height)
if lines_metrics.text_width * scale_koef > settings.width then
@@ -469,9 +467,9 @@ function M.adjust_to_area(words, settings, lines_metrics)
local lines = M.apply_scale_without_update(words, settings, adjust_scale)
local is_fit = M.is_fit_info_area(lines, settings)
local step = is_fit and M.ADJUST_SCALE_DELTA or -M.ADJUST_SCALE_DELTA
local step = is_fit and style.ADJUST_SCALE_DELTA or -style.ADJUST_SCALE_DELTA
for i = 1, M.ADJUST_STEPS do
for i = 1, style.ADJUST_STEPS do
-- Grow down to check if we fit
if step < 0 and is_fit then
last_line_metrics = M.set_text_scale(words, settings, adjust_scale)
@@ -487,7 +485,7 @@ function M.adjust_to_area(words, settings, lines_metrics)
lines = M.apply_scale_without_update(words, settings, adjust_scale)
is_fit = M.is_fit_info_area(lines, settings)
if i == M.ADJUST_STEPS then
if i == style.ADJUST_STEPS then
last_line_metrics = M.set_text_scale(words, settings, adjust_scale)
end
end

View File

@@ -3,44 +3,47 @@
-- Modified by: Insality
local M = {}
local cache = {}
function M.parse_hex(hex)
if cache[hex] then
return cache[hex]
end
local r,g,b,a = hex:match("#?(%x%x)(%x%x)(%x%x)(%x?%x?)")
if a == "" then a = "ff" end
if r and g and b and a then
return vmath.vector4(
local color = vmath.vector4(
tonumber(r, 16) / 255,
tonumber(g, 16) / 255,
tonumber(b, 16) / 255,
tonumber(a, 16) / 255)
tonumber(a, 16) / 255
)
cache[hex] = color
return color
end
return nil
end
function M.parse_decimal(dec)
if cache[dec] then
return cache[dec]
end
local r,g,b,a = dec:match("(%d*%.?%d*),(%d*%.?%d*),(%d*%.?%d*),(%d*%.?%d*)")
if r and g and b and a then
return vmath.vector4(tonumber(r), tonumber(g), tonumber(b), tonumber(a))
local color = vmath.vector4(tonumber(r), tonumber(g), tonumber(b), tonumber(a))
cache[dec] = color
return color
end
return nil
end
function M.add(name, color)
if type(color) == "string" then
color = M.parse_hex(color) or M.parse_decimal(color)
end
assert(type(color) == "userdata" and color.x and color.y and color.z and color.w, "Unable to add color")
M.COLORS[name] = color
end
M.COLORS = {}
function M.parse(c)
return M.COLORS[c] or M.parse_hex(c) or M.parse_decimal(c)
return M.parse_hex(c) or M.parse_decimal(c)
end

View File

@@ -8,9 +8,9 @@ local utf8 = utf8 or utf8_lua
local M = {}
local function parse_tag(tag, params)
local function parse_tag(tag, params, style)
local settings = { tags = { [tag] = params }, tag = tag }
if not tags.apply(tag, params, settings) then
if not tags.apply(tag, params, settings, style) then
settings[tag] = params
end
@@ -110,8 +110,9 @@ end
--- Parse the text into individual words
-- @param text The text to parse
-- @param default_settings Default settings for each word
-- @param color_aliases Color aliases table
-- @return List of all words
function M.parse(text, default_settings)
function M.parse(text, default_settings, style)
assert(text)
assert(default_settings)
@@ -151,12 +152,12 @@ function M.parse(text, default_settings)
if is_empty then
-- empty tag, ie tag without content
-- example <br/> and <img=texture:image/>
local empty_tag_settings = parse_tag(name, params)
local empty_tag_settings = parse_tag(name, params, style)
merge_tags(empty_tag_settings, word_settings)
add_word("", empty_tag_settings, all_words)
elseif not is_endtag then
-- open tag - parse and add it
local tag_settings = parse_tag(name, params)
local tag_settings = parse_tag(name, params, style)
open_tags[#open_tags + 1] = tag_settings
else
-- end tag - remove it from the list of open tags

View File

@@ -5,17 +5,16 @@
local color = require("druid.custom.rich_text.module.rt_color")
local M = {}
local tags = {}
function M.apply(tag, params, settings)
function M.apply(tag, params, settings, style)
local fn = tags[tag]
if not fn then
return false
end
fn(params, settings)
fn(params, settings, style)
return true
end
@@ -44,17 +43,20 @@ end
-- Format: <color=[#]{HEX_VALUE}>{Text}</color>
-- Format: <color={COLOR_NAME}>{Text}</color>
-- Example: <color=FF0000>Rich Text</color>
M.register("color", function(params, settings)
M.register("color", function(params, settings, style)
params = style.COLORS[params] or params
settings.color = color.parse(params)
end)
M.register("shadow", function(params, settings)
M.register("shadow", function(params, settings, style)
params = style.COLORS[params] or params
settings.shadow = color.parse(params)
end)
M.register("outline", function(params, settings)
M.register("outline", function(params, settings, style)
params = style.COLORS[params] or params
settings.outline = color.parse(params)
end)
@@ -69,11 +71,6 @@ M.register("size", function(params, settings)
end)
M.register("a", function(params, settings)
settings.anchor = true
end)
-- Example: </br>
M.register("br", function(params, settings)
settings.br = true

View File

@@ -59,7 +59,6 @@
-- font: string,
-- image: druid.rich_text.image,
-- default_animation: string,
-- anchor: number,
-- br: boolean,
-- nobr: boolean,
-- }
@@ -125,6 +124,21 @@ function RichText.init(self, template, nodes)
end
--- Component style params.
-- You can override this component styles params in Druid styles table
-- or create your own style
-- @table style
-- @tfield[opt={}] table COLORS Rich Text color aliases
-- @tfield[opt=20] number ADJUST_STEPS Amount steps of attemps text adjust by height
-- @tfield[opt=0.02] number ADJUST_SCALE_DELTA Scale step on each height adjust step
function RichText.on_style_change(self, style)
self.style = {}
self.style.COLORS = style.COLORS or {}
self.style.ADJUST_STEPS = style.ADJUST_STEPS or 20
self.style.ADJUST_SCALE_DELTA = style.ADJUST_SCALE_DELTA or 0.02
end
--- Set text for Rich Text
-- @tparam RichText self @{RichText}
-- @tparam string text The text to set
@@ -174,10 +188,10 @@ end
-- <img=texture:image,size/>
-- <img=texture:image,width,height/>
function RichText.set_text(self, text)
self:clean()
self:clear()
local words, settings, line_metrics = rich_text.create(text, self._settings)
line_metrics = rich_text.adjust_to_area(words, settings, line_metrics)
local words, settings, line_metrics = rich_text.create(text, self._settings, self.style)
line_metrics = rich_text.adjust_to_area(words, settings, line_metrics, self.style)
self._words = words
self._line_metrics = line_metrics
@@ -187,13 +201,22 @@ end
function RichText:on_remove()
self:clean()
self:clear()
end
--- Get all words, which has a passed tag
--- Clear all created words.
function RichText:clear()
if self._words then
rich_text.remove(self._words)
self._words = nil
end
end
--- Get all words, which has a passed tag.
-- @tparam string tag
-- @treturn table Words
-- @treturn druid.rich_text.word[] words
function RichText:tagged(tag)
if not self._words then
return
@@ -204,12 +227,19 @@ end
--- Get all current words.
-- @treturn table Words
-- @treturn table druid.rich_text.word[]
function RichText:get_words()
return self._words
end
--- Get current line metrics
--- @treturn druid.rich_text.lines_metrics
function RichText:get_line_metric()
return self._line_metrics
end
function RichText:_create_settings()
local root_size = gui.get_size(self.root)
return {
@@ -219,7 +249,7 @@ function RichText:_create_settings()
parent = self.root,
width = root_size.x,
height = root_size.y,
combine_words = false,
combine_words = false, -- disabled now
text_prefab = self.text_prefab,
node_prefab = self.icon_prefab,
@@ -231,7 +261,7 @@ function RichText:_create_settings()
is_multiline = gui.get_line_break(self.text_prefab),
-- Image settings
image_pixel_grid_snap = false,
image_pixel_grid_snap = false, -- disabled now
node_scale = gui.get_scale(self.icon_prefab),
image_scale = gui.get_scale(self.icon_prefab),
default_animation = gui.get_flipbook(self.icon_prefab),
@@ -239,13 +269,4 @@ function RichText:_create_settings()
end
--- Clear all created words.
function RichText:clean()
if self._words then
rich_text.remove(self._words)
self._words = nil
end
end
return RichText