mirror of
https://github.com/MikaylaFischler/cc-mek-scada.git
synced 2024-08-30 18:22:34 +00:00
#344 element redraws and shorter assert messages
This commit is contained in:
parent
70831b49d2
commit
ed4180a072
@ -360,6 +360,8 @@ function element.new(args, child_offset_x, child_offset_y)
|
||||
---@param result any
|
||||
function protected.response_callback(result) end
|
||||
|
||||
-- accessors and control --
|
||||
|
||||
-- get value
|
||||
---@nodiscard
|
||||
function protected.get_value() return protected.value end
|
||||
@ -387,6 +389,9 @@ function element.new(args, child_offset_x, child_offset_y)
|
||||
-- luacheck: pop
|
||||
---@diagnostic enable: unused-local, unused-vararg
|
||||
|
||||
-- re-draw this element
|
||||
function protected.redraw() end
|
||||
|
||||
-- start animations
|
||||
function protected.start_anim() end
|
||||
|
||||
|
@ -1,7 +1,5 @@
|
||||
-- Color Map Graphics Element
|
||||
|
||||
local util = require("scada-common.util")
|
||||
|
||||
local element = require("graphics.element")
|
||||
|
||||
---@class colormap_args
|
||||
@ -16,7 +14,7 @@ local element = require("graphics.element")
|
||||
---@return graphics_element element, element_id id
|
||||
local function colormap(args)
|
||||
local bkg = "008877FFCCEE114455DD9933BBAA2266"
|
||||
local spaces = util.spaces(32)
|
||||
local spaces = string.rep(" ", 32)
|
||||
|
||||
args.width = 32
|
||||
args.height = 1
|
||||
@ -25,8 +23,13 @@ local function colormap(args)
|
||||
local e = element.new(args)
|
||||
|
||||
-- draw color map
|
||||
function e.redraw()
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_blit(spaces, bkg, bkg)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -24,10 +24,10 @@ local MOUSE_CLICK = core.events.MOUSE_CLICK
|
||||
---@param args app_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function app_button(args)
|
||||
assert(type(args.text) == "string", "graphics.elements.controls.app: text is a required field")
|
||||
assert(type(args.title) == "string", "graphics.elements.controls.app: title is a required field")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.app: callback is a required field")
|
||||
assert(type(args.app_fg_bg) == "table", "graphics.elements.controls.app: app_fg_bg is a required field")
|
||||
assert(type(args.text) == "string", "controls.app: text is a required field")
|
||||
assert(type(args.title) == "string", "controls.app: title is a required field")
|
||||
assert(type(args.callback) == "function", "controls.app: callback is a required field")
|
||||
assert(type(args.app_fg_bg) == "table", "controls.app: app_fg_bg is a required field")
|
||||
|
||||
args.height = 4
|
||||
args.width = 5
|
||||
@ -35,10 +35,6 @@ local function app_button(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- write app title, centered
|
||||
e.w_set_cur(math.floor((e.frame.w - string.len(args.title)) / 2) + 1, 4)
|
||||
e.w_write(args.title)
|
||||
|
||||
-- draw the app button
|
||||
local function draw()
|
||||
local fgd = args.app_fg_bg.fgd
|
||||
@ -120,8 +116,18 @@ local function app_button(args)
|
||||
if val then e.handle_mouse(core.events.mouse_generic(core.events.MOUSE_CLICK.UP, 1, 1)) end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
-- write app title, centered
|
||||
e.w_set_cur(math.floor((e.frame.w - string.len(args.title)) / 2) + 1, 4)
|
||||
e.w_write(args.title)
|
||||
|
||||
-- draw button
|
||||
draw()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -18,8 +18,8 @@ local element = require("graphics.element")
|
||||
---@param args checkbox_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function checkbox(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.controls.checkbox: label is a required field")
|
||||
assert(type(args.box_fg_bg) == "table", "graphics.elements.controls.checkbox: box_fg_bg is a required field")
|
||||
assert(type(args.label) == "string", "controls.checkbox: label is a required field")
|
||||
assert(type(args.box_fg_bg) == "table", "controls.checkbox: box_fg_bg is a required field")
|
||||
|
||||
args.can_focus = true
|
||||
args.height = 1
|
||||
@ -105,9 +105,14 @@ local function checkbox(args)
|
||||
e.on_enabled = draw_label
|
||||
e.on_disabled = draw_label
|
||||
|
||||
-- initial draw
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
draw()
|
||||
draw_label()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -21,21 +21,16 @@ local element = require("graphics.element")
|
||||
---@param args hazard_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function hazard_button(args)
|
||||
assert(type(args.text) == "string", "graphics.elements.controls.hazard_button: text is a required field")
|
||||
assert(type(args.accent) == "number", "graphics.elements.controls.hazard_button: accent is a required field")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.hazard_button: callback is a required field")
|
||||
assert(type(args.text) == "string", "controls.hazard_button: text is a required field")
|
||||
assert(type(args.accent) == "number", "controls.hazard_button: accent is a required field")
|
||||
assert(type(args.callback) == "function", "controls.hazard_button: callback is a required field")
|
||||
|
||||
-- static dimensions
|
||||
args.height = 3
|
||||
args.width = string.len(args.text) + 4
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- write the button text
|
||||
e.w_set_cur(3, 2)
|
||||
e.w_write(args.text)
|
||||
|
||||
-- draw border
|
||||
---@param accent color accent color
|
||||
local function draw_border(accent)
|
||||
@ -158,7 +153,6 @@ local function hazard_button(args)
|
||||
-- 1.5 second timeout
|
||||
tcd.dispatch(1.5, on_timeout)
|
||||
|
||||
-- call the touch callback
|
||||
args.callback()
|
||||
end
|
||||
end
|
||||
@ -195,8 +189,16 @@ local function hazard_button(args)
|
||||
e.w_write(args.text)
|
||||
end
|
||||
|
||||
-- initial draw of border
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
-- write the button text and draw border
|
||||
e.w_set_cur(3, 2)
|
||||
e.w_write(args.text)
|
||||
draw_border(args.accent)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -29,13 +29,11 @@ local element = require("graphics.element")
|
||||
---@param args multi_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function multi_button(args)
|
||||
assert(type(args.options) == "table", "graphics.elements.controls.multi_button: options is a required field")
|
||||
assert(#args.options > 0, "graphics.elements.controls.multi_button: at least one option is required")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.multi_button: callback is a required field")
|
||||
assert(type(args.default) == "nil" or (type(args.default) == "number" and args.default > 0),
|
||||
"graphics.elements.controls.multi_button: default must be nil or a number > 0")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0),
|
||||
"graphics.elements.controls.multi_button: min_width must be nil or a number > 0")
|
||||
assert(type(args.options) == "table", "controls.multi_button: options is a required field")
|
||||
assert(#args.options > 0, "controls.multi_button: at least one option is required")
|
||||
assert(type(args.callback) == "function", "controls.multi_button: callback is a required field")
|
||||
assert(type(args.default) == "nil" or (type(args.default) == "number" and args.default > 0), "controls.multi_button: default must be nil or a number > 0")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0), "controls.multi_button: min_width must be nil or a number > 0")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
@ -71,7 +69,7 @@ local function multi_button(args)
|
||||
end
|
||||
|
||||
-- show the button state
|
||||
local function draw()
|
||||
function e.redraw()
|
||||
for i = 1, #args.options do
|
||||
local opt = args.options[i] ---@type button_option
|
||||
|
||||
@ -115,7 +113,7 @@ local function multi_button(args)
|
||||
-- tap always has identical coordinates, so this always passes for taps
|
||||
if button_ini == button_cur and button_cur ~= nil then
|
||||
e.value = button_cur
|
||||
draw()
|
||||
e.redraw()
|
||||
args.callback(e.value)
|
||||
end
|
||||
end
|
||||
@ -125,11 +123,11 @@ local function multi_button(args)
|
||||
---@param val integer new value
|
||||
function e.set_value(val)
|
||||
e.value = val
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
draw()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -26,10 +26,9 @@ local KEY_CLICK = core.events.KEY_CLICK
|
||||
---@param args push_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function push_button(args)
|
||||
assert(type(args.text) == "string", "graphics.elements.controls.push_button: text is a required field")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.push_button: callback is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0),
|
||||
"graphics.elements.controls.push_button: min_width must be nil or a number > 0")
|
||||
assert(type(args.text) == "string", "controls.push_button: text is a required field")
|
||||
assert(type(args.callback) == "function", "controls.push_button: callback is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0), "controls.push_button: min_width must be nil or a number > 0")
|
||||
|
||||
local text_width = string.len(args.text)
|
||||
|
||||
@ -46,7 +45,7 @@ local function push_button(args)
|
||||
local v_pad = math.floor(e.frame.h / 2) + 1
|
||||
|
||||
-- draw the button
|
||||
local function draw()
|
||||
function e.redraw()
|
||||
e.window.clear()
|
||||
|
||||
-- write the button text
|
||||
@ -60,7 +59,7 @@ local function push_button(args)
|
||||
e.value = true
|
||||
e.w_set_fgd(args.active_fg_bg.fgd)
|
||||
e.w_set_bkg(args.active_fg_bg.bkg)
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
@ -70,7 +69,7 @@ local function push_button(args)
|
||||
e.value = false
|
||||
e.w_set_fgd(e.fg_bg.fgd)
|
||||
e.w_set_bkg(e.fg_bg.bkg)
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
@ -117,7 +116,7 @@ local function push_button(args)
|
||||
e.value = false
|
||||
e.w_set_fgd(e.fg_bg.fgd)
|
||||
e.w_set_bkg(e.fg_bg.bkg)
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
@ -127,7 +126,7 @@ local function push_button(args)
|
||||
e.value = false
|
||||
e.w_set_fgd(args.dis_fg_bg.fgd)
|
||||
e.w_set_bkg(args.dis_fg_bg.bkg)
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
@ -136,7 +135,7 @@ local function push_button(args)
|
||||
e.on_unfocused = show_unpressed
|
||||
|
||||
-- initial draw
|
||||
draw()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -27,11 +27,12 @@ local element = require("graphics.element")
|
||||
---@param args radio_2d_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function radio_2d_button(args)
|
||||
assert(type(args.options) == "table" and #args.options > 0, "graphics.elements.controls.radio_2d: options should be a table with length >= 1")
|
||||
assert(type(args.radio_colors) == "table", "graphics.elements.controls.radio_2d: radio_colors is a required field")
|
||||
assert(type(args.select_color) == "number" or type(args.color_map) == "table", "graphics.elements.controls.radio_2d: select_color or color_map is required")
|
||||
assert(type(args.default) == "nil" or (type(args.default) == "number" and args.default > 0),
|
||||
"graphics.elements.controls.radio_2d: default must be nil or a number > 0")
|
||||
assert(type(args.options) == "table" and #args.options > 0, "controls.radio_2d: options should be a table with length >= 1")
|
||||
assert(util.is_int(args.rows) and util.is_int(args.columns), "controls.radio_2d: rows/columns must be integers")
|
||||
assert((args.rows * args.columns) >= #args.options, "controls.radio_2d: rows x columns size insufficient for provided number of options")
|
||||
assert(type(args.radio_colors) == "table", "controls.radio_2d: radio_colors is a required field")
|
||||
assert(type(args.select_color) == "number" or type(args.color_map) == "table", "controls.radio_2d: select_color or color_map is required")
|
||||
assert(type(args.default) == "nil" or (type(args.default) == "number" and args.default > 0), "controls.radio_2d: default must be nil or a number > 0")
|
||||
|
||||
local array = {}
|
||||
local col_widths = {}
|
||||
@ -74,8 +75,8 @@ local function radio_2d_button(args)
|
||||
-- selected option (convert nil to 1 if missing)
|
||||
e.value = args.default or 1
|
||||
|
||||
-- show the args.options/states
|
||||
local function draw()
|
||||
-- draw the element
|
||||
function e.redraw()
|
||||
local col_x = 1
|
||||
|
||||
local radio_color_b = util.trinary(type(args.disable_color) == "number" and not e.enabled, args.disable_color, args.radio_colors.color_b)
|
||||
@ -135,7 +136,7 @@ local function radio_2d_button(args)
|
||||
if elem ~= nil and event.initial.x >= elem.x_1 and event.initial.x <= elem.x_2 and event.current.x >= elem.x_1 and event.current.x <= elem.x_2 then
|
||||
e.value = elem.id
|
||||
focused_opt = elem.id
|
||||
draw()
|
||||
e.redraw()
|
||||
if type(args.callback) == "function" then args.callback(e.value) end
|
||||
break
|
||||
end
|
||||
@ -149,30 +150,30 @@ local function radio_2d_button(args)
|
||||
if event.type == core.events.KEY_CLICK.DOWN or event.type == core.events.KEY_CLICK.HELD then
|
||||
if event.type == core.events.KEY_CLICK.DOWN and (event.key == keys.space or event.key == keys.enter or event.key == keys.numPadEnter) then
|
||||
e.value = focused_opt
|
||||
draw()
|
||||
e.redraw()
|
||||
if type(args.callback) == "function" then args.callback(e.value) end
|
||||
elseif event.key == keys.down then
|
||||
if focused_opt < #args.options then
|
||||
focused_opt = focused_opt + 1
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
elseif event.key == keys.up then
|
||||
if focused_opt > 1 then
|
||||
focused_opt = focused_opt - 1
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
elseif event.key == keys.right then
|
||||
if array[focus_y + 1] and array[focus_y + 1][focus_x] then
|
||||
focused_opt = array[focus_y + 1][focus_x].id
|
||||
else focused_opt = array[1][focus_x].id end
|
||||
draw()
|
||||
e.redraw()
|
||||
elseif event.key == keys.left then
|
||||
if array[focus_y - 1] and array[focus_y - 1][focus_x] then
|
||||
focused_opt = array[focus_y - 1][focus_x].id
|
||||
draw()
|
||||
e.redraw()
|
||||
elseif array[#array][focus_x] then
|
||||
focused_opt = array[#array][focus_x].id
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
end
|
||||
@ -183,20 +184,20 @@ local function radio_2d_button(args)
|
||||
function e.set_value(val)
|
||||
if val > 0 and val <= #args.options then
|
||||
e.value = val
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
-- handle focus
|
||||
e.on_focused = draw
|
||||
e.on_unfocused = draw
|
||||
e.on_focused = e.redraw
|
||||
e.on_unfocused = e.redraw
|
||||
|
||||
-- handle enable
|
||||
e.on_enabled = draw
|
||||
e.on_disabled = draw
|
||||
e.on_enabled = e.redraw
|
||||
e.on_disabled = e.redraw
|
||||
|
||||
-- initial draw
|
||||
draw()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -25,14 +25,14 @@ local KEY_CLICK = core.events.KEY_CLICK
|
||||
---@param args radio_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function radio_button(args)
|
||||
assert(type(args.options) == "table", "graphics.elements.controls.radio_button: options is a required field")
|
||||
assert(#args.options > 0, "graphics.elements.controls.radio_button: at least one option is required")
|
||||
assert(type(args.radio_colors) == "table", "graphics.elements.controls.radio_button: radio_colors is a required field")
|
||||
assert(type(args.select_color) == "number", "graphics.elements.controls.radio_button: select_color is a required field")
|
||||
assert(type(args.options) == "table", "controls.radio_button: options is a required field")
|
||||
assert(#args.options > 0, "controls.radio_button: at least one option is required")
|
||||
assert(type(args.radio_colors) == "table", "controls.radio_button: radio_colors is a required field")
|
||||
assert(type(args.select_color) == "number", "controls.radio_button: select_color is a required field")
|
||||
assert(type(args.default) == "nil" or (type(args.default) == "number" and args.default > 0),
|
||||
"graphics.elements.controls.radio_button: default must be nil or a number > 0")
|
||||
"controls.radio_button: default must be nil or a number > 0")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0),
|
||||
"graphics.elements.controls.radio_button: min_width must be nil or a number > 0")
|
||||
"controls.radio_button: min_width must be nil or a number > 0")
|
||||
|
||||
-- determine widths
|
||||
local max_width = 1
|
||||
@ -59,7 +59,7 @@ local function radio_button(args)
|
||||
e.value = args.default or 1
|
||||
|
||||
-- show the button state
|
||||
local function draw()
|
||||
function e.redraw()
|
||||
for i = 1, #args.options do
|
||||
local opt = args.options[i] ---@type string
|
||||
|
||||
@ -97,7 +97,7 @@ local function radio_button(args)
|
||||
if args.options[event.current.y] ~= nil then
|
||||
e.value = event.current.y
|
||||
focused_opt = e.value
|
||||
draw()
|
||||
e.redraw()
|
||||
if type(args.callback) == "function" then args.callback(e.value) end
|
||||
end
|
||||
end
|
||||
@ -109,17 +109,17 @@ local function radio_button(args)
|
||||
if event.type == KEY_CLICK.DOWN or event.type == KEY_CLICK.HELD then
|
||||
if event.type == KEY_CLICK.DOWN and (event.key == keys.space or event.key == keys.enter or event.key == keys.numPadEnter) then
|
||||
e.value = focused_opt
|
||||
draw()
|
||||
e.redraw()
|
||||
if type(args.callback) == "function" then args.callback(e.value) end
|
||||
elseif event.key == keys.down then
|
||||
if focused_opt < #args.options then
|
||||
focused_opt = focused_opt + 1
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
elseif event.key == keys.up then
|
||||
if focused_opt > 1 then
|
||||
focused_opt = focused_opt - 1
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
end
|
||||
@ -130,20 +130,20 @@ local function radio_button(args)
|
||||
function e.set_value(val)
|
||||
if val > 0 and val <= #args.options then
|
||||
e.value = val
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
-- handle focus
|
||||
e.on_focused = draw
|
||||
e.on_unfocused = draw
|
||||
e.on_focused = e.redraw
|
||||
e.on_unfocused = e.redraw
|
||||
|
||||
-- handle enable
|
||||
e.on_enabled = draw
|
||||
e.on_disabled = draw
|
||||
e.on_enabled = e.redraw
|
||||
e.on_disabled = e.redraw
|
||||
|
||||
-- initial draw
|
||||
draw()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -1,6 +1,7 @@
|
||||
-- Sidebar Graphics Element
|
||||
|
||||
local tcd = require("scada-common.tcd")
|
||||
local util = require("scada-common.util")
|
||||
|
||||
local core = require("graphics.core")
|
||||
local element = require("graphics.element")
|
||||
@ -26,11 +27,10 @@ local MOUSE_CLICK = core.events.MOUSE_CLICK
|
||||
---@param args sidebar_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function sidebar(args)
|
||||
assert(type(args.tabs) == "table", "graphics.elements.controls.sidebar: tabs is a required field")
|
||||
assert(#args.tabs > 0, "graphics.elements.controls.sidebar: at least one tab is required")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.sidebar: callback is a required field")
|
||||
assert(type(args.tabs) == "table", "controls.sidebar: tabs is a required field")
|
||||
assert(#args.tabs > 0, "controls.sidebar: at least one tab is required")
|
||||
assert(type(args.callback) == "function", "controls.sidebar: callback is a required field")
|
||||
|
||||
-- always 3 wide
|
||||
args.width = 3
|
||||
|
||||
-- create new graphics element base object
|
||||
@ -41,10 +41,14 @@ local function sidebar(args)
|
||||
-- default to 1st tab
|
||||
e.value = 1
|
||||
|
||||
local was_pressed = false
|
||||
|
||||
-- show the button state
|
||||
---@param pressed boolean if the currently selected tab should appear as actively pressed
|
||||
---@param pressed? boolean if the currently selected tab should appear as actively pressed
|
||||
---@param pressed_idx? integer optional index to show as held (that is not yet selected)
|
||||
local function draw(pressed, pressed_idx)
|
||||
pressed = util.trinary(pressed == nil, was_pressed, pressed)
|
||||
was_pressed = pressed
|
||||
pressed_idx = pressed_idx or e.value
|
||||
|
||||
for i = 1, #args.tabs do
|
||||
@ -65,12 +69,8 @@ local function sidebar(args)
|
||||
e.w_write(" ")
|
||||
e.w_set_cur(1, y + 1)
|
||||
if e.value == i then
|
||||
-- show as selected
|
||||
e.w_write(" " .. tab.char .. "\x10")
|
||||
else
|
||||
-- show as unselected
|
||||
e.w_write(" " .. tab.char .. " ")
|
||||
end
|
||||
else e.w_write(" " .. tab.char .. " ") end
|
||||
e.w_set_cur(1, y + 2)
|
||||
e.w_write(" ")
|
||||
end
|
||||
@ -113,8 +113,10 @@ local function sidebar(args)
|
||||
draw(false)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
draw(false)
|
||||
-- element redraw
|
||||
e.redraw = draw
|
||||
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -29,8 +29,8 @@ local function spinbox(args)
|
||||
local wn_prec = args.whole_num_precision
|
||||
local fr_prec = args.fractional_precision
|
||||
|
||||
assert(util.is_int(wn_prec), "graphics.element.controls.spinbox_numeric: whole number precision must be an integer")
|
||||
assert(util.is_int(fr_prec), "graphics.element.controls.spinbox_numeric: fractional precision must be an integer")
|
||||
assert(util.is_int(wn_prec), "controls.spinbox_numeric: whole number precision must be an integer")
|
||||
assert(util.is_int(fr_prec), "controls.spinbox_numeric: fractional precision must be an integer")
|
||||
|
||||
local fmt, fmt_init ---@type string, string
|
||||
|
||||
@ -44,7 +44,7 @@ local function spinbox(args)
|
||||
|
||||
local dec_point_x = args.whole_num_precision + 1
|
||||
|
||||
assert(type(args.arrow_fg_bg) == "table", "graphics.element.spinbox_numeric: arrow_fg_bg is a required field")
|
||||
assert(type(args.arrow_fg_bg) == "table", "controls.spinbox_numeric: arrow_fg_bg is a required field")
|
||||
|
||||
-- determine widths
|
||||
args.width = wn_prec + fr_prec + util.trinary(fr_prec > 0, 1, 0)
|
||||
@ -72,8 +72,6 @@ local function spinbox(args)
|
||||
end
|
||||
end
|
||||
|
||||
draw_arrows(args.arrow_fg_bg.fgd)
|
||||
|
||||
-- populate digits from current value
|
||||
local function set_digits()
|
||||
local initial_str = util.sprintf(fmt_init, e.value)
|
||||
@ -125,9 +123,6 @@ local function spinbox(args)
|
||||
e.w_write(util.sprintf(fmt, e.value))
|
||||
end
|
||||
|
||||
-- init with the default value
|
||||
show_num()
|
||||
|
||||
-- handle mouse interaction
|
||||
---@param event mouse_interaction mouse event
|
||||
function e.handle_mouse(event)
|
||||
@ -138,10 +133,8 @@ local function spinbox(args)
|
||||
local idx = util.trinary(event.current.x > dec_point_x, event.current.x - 1, event.current.x)
|
||||
if digits[idx] ~= nil then
|
||||
if event.current.y == 1 then
|
||||
-- increment
|
||||
digits[idx] = digits[idx] + 1
|
||||
elseif event.current.y == 3 then
|
||||
-- decrement
|
||||
digits[idx] = digits[idx] - 1
|
||||
end
|
||||
|
||||
@ -176,18 +169,19 @@ local function spinbox(args)
|
||||
end
|
||||
|
||||
-- enable this input
|
||||
function e.on_enabled()
|
||||
draw_arrows(args.arrow_fg_bg.fgd)
|
||||
end
|
||||
function e.on_enabled() draw_arrows(args.arrow_fg_bg.fgd) end
|
||||
|
||||
-- disable this input
|
||||
function e.on_disabled()
|
||||
draw_arrows(args.arrow_disable or colors.lightGray)
|
||||
function e.on_disabled() draw_arrows(args.arrow_disable or colors.lightGray) end
|
||||
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
show_num()
|
||||
draw_arrows(util.trinary(e.enabled, args.arrow_fg_bg.fgd, args.arrow_disable or colors.lightGray))
|
||||
end
|
||||
|
||||
-- default to zero, init digits table
|
||||
e.value = 0
|
||||
set_digits()
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -21,15 +21,13 @@ local element = require("graphics.element")
|
||||
---@param args switch_button_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function switch_button(args)
|
||||
assert(type(args.text) == "string", "graphics.elements.controls.switch_button: text is a required field")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.switch_button: callback is a required field")
|
||||
assert(type(args.active_fg_bg) == "table", "graphics.elements.controls.switch_button: active_fg_bg is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0),
|
||||
"graphics.elements.controls.switch_button: min_width must be nil or a number > 0")
|
||||
assert(type(args.text) == "string", "controls.switch_button: text is a required field")
|
||||
assert(type(args.callback) == "function", "controls.switch_button: callback is a required field")
|
||||
assert(type(args.active_fg_bg) == "table", "controls.switch_button: active_fg_bg is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0), "controls.switch_button: min_width must be nil or a number > 0")
|
||||
|
||||
local text_width = string.len(args.text)
|
||||
|
||||
-- single line height, calculate width
|
||||
args.height = 1
|
||||
args.min_width = args.min_width or 0
|
||||
args.width = math.max(text_width, args.min_width)
|
||||
@ -37,44 +35,32 @@ local function switch_button(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- button state (convert nil to false if missing)
|
||||
e.value = args.default or false
|
||||
|
||||
local h_pad = math.floor((e.frame.w - text_width) / 2) + 1
|
||||
local v_pad = math.floor(e.frame.h / 2) + 1
|
||||
|
||||
-- show the button state
|
||||
local function draw_state()
|
||||
function e.redraw()
|
||||
if e.value then
|
||||
-- show as pressed
|
||||
e.w_set_fgd(args.active_fg_bg.fgd)
|
||||
e.w_set_bkg(args.active_fg_bg.bkg)
|
||||
else
|
||||
-- show as unpressed
|
||||
e.w_set_fgd(e.fg_bg.fgd)
|
||||
e.w_set_bkg(e.fg_bg.bkg)
|
||||
end
|
||||
|
||||
-- clear to redraw background
|
||||
e.window.clear()
|
||||
|
||||
-- write the button text
|
||||
e.w_set_cur(h_pad, v_pad)
|
||||
e.w_write(args.text)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
draw_state()
|
||||
|
||||
-- handle mouse interaction
|
||||
---@param event mouse_interaction mouse event
|
||||
function e.handle_mouse(event)
|
||||
if e.enabled and core.events.was_clicked(event.type) then
|
||||
-- toggle state
|
||||
e.value = not e.value
|
||||
draw_state()
|
||||
|
||||
-- call the touch callback with state
|
||||
e.redraw()
|
||||
args.callback(e.value)
|
||||
end
|
||||
end
|
||||
@ -82,11 +68,13 @@ local function switch_button(args)
|
||||
-- set the value
|
||||
---@param val boolean new value
|
||||
function e.set_value(val)
|
||||
-- set state
|
||||
e.value = val
|
||||
draw_state()
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
||||
|
@ -27,13 +27,11 @@ local element = require("graphics.element")
|
||||
---@param args tabbar_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function tabbar(args)
|
||||
assert(type(args.tabs) == "table", "graphics.elements.controls.tabbar: tabs is a required field")
|
||||
assert(#args.tabs > 0, "graphics.elements.controls.tabbar: at least one tab is required")
|
||||
assert(type(args.callback) == "function", "graphics.elements.controls.tabbar: callback is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0),
|
||||
"graphics.elements.controls.tabbar: min_width must be nil or a number > 0")
|
||||
assert(type(args.tabs) == "table", "controls.tabbar: tabs is a required field")
|
||||
assert(#args.tabs > 0, "controls.tabbar: at least one tab is required")
|
||||
assert(type(args.callback) == "function", "controls.tabbar: callback is a required field")
|
||||
assert(type(args.min_width) == "nil" or (type(args.min_width) == "number" and args.min_width > 0), "controls.tabbar: min_width must be nil or a number > 0")
|
||||
|
||||
-- always 1 tall
|
||||
args.height = 1
|
||||
|
||||
-- determine widths
|
||||
@ -67,7 +65,7 @@ local function tabbar(args)
|
||||
end
|
||||
|
||||
-- show the tab state
|
||||
local function draw()
|
||||
function e.redraw()
|
||||
for i = 1, #args.tabs do
|
||||
local tab = args.tabs[i] ---@type tabbar_tab
|
||||
|
||||
@ -109,7 +107,7 @@ local function tabbar(args)
|
||||
-- tap always has identical coordinates, so this always passes for taps
|
||||
if tab_ini == tab_cur and tab_cur ~= nil then
|
||||
e.value = tab_cur
|
||||
draw()
|
||||
e.redraw()
|
||||
args.callback(e.value)
|
||||
end
|
||||
end
|
||||
@ -119,11 +117,11 @@ local function tabbar(args)
|
||||
---@param val integer new value
|
||||
function e.set_value(val)
|
||||
e.value = val
|
||||
draw()
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
draw()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -42,30 +42,6 @@ local function number_field(args)
|
||||
-- make an interactive field manager
|
||||
local ifield = core.new_ifield(e, args.max_digits, args.fg_bg, args.dis_fg_bg)
|
||||
|
||||
|
||||
-- draw input
|
||||
local function show()
|
||||
if e.enabled then
|
||||
e.w_set_bkg(args.fg_bg.bkg)
|
||||
e.w_set_fgd(args.fg_bg.fgd)
|
||||
else
|
||||
e.w_set_bkg(args.dis_fg_bg.bkg)
|
||||
e.w_set_fgd(args.dis_fg_bg.fgd)
|
||||
end
|
||||
|
||||
-- clear and print
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(string.rep(" ", e.frame.w))
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(e.value)
|
||||
|
||||
-- show cursor if focused
|
||||
if e.is_focused() and e.enabled then
|
||||
e.w_set_fgd(colors.lightGray)
|
||||
e.w_write("_")
|
||||
end
|
||||
end
|
||||
|
||||
-- handle mouse interaction
|
||||
---@param event mouse_interaction mouse event
|
||||
function e.handle_mouse(event)
|
||||
@ -117,9 +93,7 @@ local function number_field(args)
|
||||
-- set the value (must be a number)
|
||||
---@param val number number to show
|
||||
function e.set_value(val)
|
||||
if tonumber(val) then
|
||||
ifield.set_value("" .. tonumber(val))
|
||||
end
|
||||
if tonumber(val) then ifield.set_value("" .. tonumber(val)) end
|
||||
end
|
||||
|
||||
-- set minimum input value
|
||||
@ -140,9 +114,6 @@ local function number_field(args)
|
||||
end
|
||||
end
|
||||
|
||||
-- handle focused
|
||||
e.on_focused = show
|
||||
|
||||
-- handle unfocused
|
||||
function e.on_unfocused()
|
||||
local val = tonumber(e.value)
|
||||
@ -162,12 +133,14 @@ local function number_field(args)
|
||||
ifield.show()
|
||||
end
|
||||
|
||||
-- handle enable
|
||||
-- handle focus (not unfocus), enable, and redraw with show()
|
||||
e.on_focused = ifield.show
|
||||
e.on_enabled = ifield.show
|
||||
e.on_disabled = ifield.show
|
||||
e.redraw = ifield.show
|
||||
|
||||
-- initial draw
|
||||
ifield.show()
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -88,16 +88,15 @@ local function text_field(args)
|
||||
ifield.set_value(text)
|
||||
end
|
||||
|
||||
-- handle focus
|
||||
-- handle focus, enable, and redraw with show()
|
||||
e.on_focused = ifield.show
|
||||
e.on_unfocused = ifield.show
|
||||
|
||||
-- handle enable
|
||||
e.on_enabled = ifield.show
|
||||
e.on_disabled = ifield.show
|
||||
e.redraw = ifield.show
|
||||
|
||||
-- initial draw
|
||||
ifield.show()
|
||||
e.redraw()
|
||||
|
||||
local elem, id = e.complete()
|
||||
return elem, id, ifield.censor
|
||||
|
@ -25,13 +25,13 @@ local flasher = require("graphics.flasher")
|
||||
---@param args alarm_indicator_light
|
||||
---@return graphics_element element, element_id id
|
||||
local function alarm_indicator_light(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.alight: label is a required field")
|
||||
assert(type(args.c1) == "number", "graphics.elements.indicators.alight: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "graphics.elements.indicators.alight: c2 is a required field")
|
||||
assert(type(args.c3) == "number", "graphics.elements.indicators.alight: c3 is a required field")
|
||||
assert(type(args.label) == "string", "indicators.alight: label is a required field")
|
||||
assert(type(args.c1) == "number", "indicators.alight: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "indicators.alight: c2 is a required field")
|
||||
assert(type(args.c3) == "number", "indicators.alight: c3 is a required field")
|
||||
|
||||
if args.flash then
|
||||
assert(util.is_int(args.period), "graphics.elements.indicators.alight: period is a required field if flash is enabled")
|
||||
assert(util.is_int(args.period), "indicators.alight: period is a required field if flash is enabled")
|
||||
end
|
||||
|
||||
-- single line
|
||||
@ -51,6 +51,8 @@ local function alarm_indicator_light(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = 1
|
||||
|
||||
-- called by flasher when enabled
|
||||
local function flash_callback()
|
||||
e.w_set_cur(1, 1)
|
||||
@ -105,9 +107,14 @@ local function alarm_indicator_light(args)
|
||||
---@param val integer indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
e.on_update(1)
|
||||
-- draw label and indicator light
|
||||
function e.redraw()
|
||||
e.on_update(e.value)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -18,8 +18,8 @@ local element = require("graphics.element")
|
||||
---@param args core_map_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function core_map(args)
|
||||
assert(util.is_int(args.reactor_l), "graphics.elements.indicators.coremap: reactor_l is a required field")
|
||||
assert(util.is_int(args.reactor_w), "graphics.elements.indicators.coremap: reactor_w is a required field")
|
||||
assert(util.is_int(args.reactor_l), "indicators.coremap: reactor_l is a required field")
|
||||
assert(util.is_int(args.reactor_w), "indicators.coremap: reactor_w is a required field")
|
||||
|
||||
-- require max dimensions
|
||||
args.width = 18
|
||||
@ -31,6 +31,8 @@ local function core_map(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = 0
|
||||
|
||||
local alternator = true
|
||||
|
||||
local core_l = args.reactor_l - 2
|
||||
@ -157,11 +159,14 @@ local function core_map(args)
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial (one-time except for resize()) frame draw
|
||||
-- redraw both frame and core
|
||||
function e.redraw()
|
||||
draw_frame()
|
||||
draw_core(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.on_update(0)
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -24,25 +24,17 @@ local element = require("graphics.element")
|
||||
---@param args data_indicator_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function data(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.data: label is a required field")
|
||||
assert(type(args.format) == "string", "graphics.elements.indicators.data: format is a required field")
|
||||
assert(args.value ~= nil, "graphics.elements.indicators.data: value is a required field")
|
||||
assert(util.is_int(args.width), "graphics.elements.indicators.data: width is a required field")
|
||||
assert(type(args.label) == "string", "indicators.data: label is a required field")
|
||||
assert(type(args.format) == "string", "indicators.data: format is a required field")
|
||||
assert(args.value ~= nil, "indicators.data: value is a required field")
|
||||
assert(util.is_int(args.width), "indicators.data: width is a required field")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- label color
|
||||
if args.lu_colors ~= nil then
|
||||
e.w_set_fgd(args.lu_colors.color_a)
|
||||
end
|
||||
|
||||
-- write label
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
e.value = args.value
|
||||
|
||||
local value_color = e.fg_bg.fgd
|
||||
local label_len = string.len(args.label)
|
||||
@ -93,8 +85,17 @@ local function data(args)
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial value draw
|
||||
e.on_update(args.value)
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
if args.lu_colors ~= nil then e.w_set_fgd(args.lu_colors.color_a) end
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -28,10 +28,12 @@ local function hbar(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = 0.0
|
||||
|
||||
-- bar width is width - 5 characters for " 100%" if showing percent
|
||||
local bar_width = util.trinary(args.show_percent, e.frame.w - 5, e.frame.w)
|
||||
|
||||
assert(bar_width > 0, "graphics.elements.indicators.hbar: too small for bar")
|
||||
assert(bar_width > 0, "indicators.hbar: too small for bar")
|
||||
|
||||
-- determine bar colors
|
||||
local bar_bkg = e.fg_bg.blit_bkg
|
||||
@ -105,20 +107,21 @@ local function hbar(args)
|
||||
function e.recolor(bar_fg_bg)
|
||||
bar_bkg = bar_fg_bg.blit_bkg
|
||||
bar_fgd = bar_fg_bg.blit_fgd
|
||||
|
||||
-- re-draw
|
||||
last_num_bars = 0
|
||||
if type(e.value) == "number" then
|
||||
e.on_update(e.value)
|
||||
end
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- set the percentage value
|
||||
---@param val number 0.0 to 1.0
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- initialize to 0
|
||||
e.on_update(0)
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
last_num_bars = -1
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -23,18 +23,17 @@ local element = require("graphics.element")
|
||||
---@param args icon_indicator_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function icon(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.icon: label is a required field")
|
||||
assert(type(args.states) == "table", "graphics.elements.indicators.icon: states is a required field")
|
||||
assert(type(args.label) == "string", "indicators.icon: label is a required field")
|
||||
assert(type(args.states) == "table", "indicators.icon: states is a required field")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 1, string.len(args.label)) + 4
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = args.value or 1
|
||||
|
||||
-- state blit strings
|
||||
local state_blit_cmds = {}
|
||||
for i = 1, #args.states do
|
||||
@ -47,10 +46,6 @@ local function icon(args)
|
||||
})
|
||||
end
|
||||
|
||||
-- write label and initial indicator light
|
||||
e.w_set_cur(5, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
-- on state change
|
||||
---@param new_state integer indicator state
|
||||
function e.on_update(new_state)
|
||||
@ -64,8 +59,16 @@ local function icon(args)
|
||||
---@param val integer indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- initial icon draw
|
||||
e.on_update(args.value or 1)
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
e.w_set_cur(5, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -23,25 +23,23 @@ local flasher = require("graphics.flasher")
|
||||
---@param args indicator_led_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function indicator_led(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.led: label is a required field")
|
||||
assert(type(args.colors) == "table", "graphics.elements.indicators.led: colors is a required field")
|
||||
assert(type(args.label) == "string", "indicators.led: label is a required field")
|
||||
assert(type(args.colors) == "table", "indicators.led: colors is a required field")
|
||||
|
||||
if args.flash then
|
||||
assert(util.is_int(args.period), "graphics.elements.indicators.led: period is a required field if flash is enabled")
|
||||
assert(util.is_int(args.period), "indicators.led: period is a required field if flash is enabled")
|
||||
end
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 0, string.len(args.label)) + 2
|
||||
|
||||
-- flasher state
|
||||
local flash_on = true
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = false
|
||||
|
||||
-- called by flasher when enabled
|
||||
local function flash_callback()
|
||||
e.w_set_cur(1, 1)
|
||||
@ -88,12 +86,17 @@ local function indicator_led(args)
|
||||
---@param val boolean indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
e.on_update(false)
|
||||
-- draw label and indicator light
|
||||
function e.redraw()
|
||||
e.on_update(e.value)
|
||||
if string.len(args.label) > 0 then
|
||||
e.w_set_cur(3, 1)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -25,25 +25,20 @@ local flasher = require("graphics.flasher")
|
||||
---@param args indicator_led_pair_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function indicator_led_pair(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.ledpair: label is a required field")
|
||||
assert(type(args.off) == "number", "graphics.elements.indicators.ledpair: off is a required field")
|
||||
assert(type(args.c1) == "number", "graphics.elements.indicators.ledpair: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "graphics.elements.indicators.ledpair: c2 is a required field")
|
||||
assert(type(args.label) == "string", "indicators.ledpair: label is a required field")
|
||||
assert(type(args.off) == "number", "indicators.ledpair: off is a required field")
|
||||
assert(type(args.c1) == "number", "indicators.ledpair: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "indicators.ledpair: c2 is a required field")
|
||||
|
||||
if args.flash then
|
||||
assert(util.is_int(args.period), "graphics.elements.indicators.ledpair: period is a required field if flash is enabled")
|
||||
assert(util.is_int(args.period), "indicators.ledpair: period is a required field if flash is enabled")
|
||||
end
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 0, string.len(args.label)) + 2
|
||||
|
||||
-- flasher state
|
||||
local flash_on = true
|
||||
|
||||
-- blit translations
|
||||
local co = colors.toBlit(args.off)
|
||||
local c1 = colors.toBlit(args.c1)
|
||||
local c2 = colors.toBlit(args.c2)
|
||||
@ -51,7 +46,6 @@ local function indicator_led_pair(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- init value for initial check in on_update
|
||||
e.value = 1
|
||||
|
||||
-- called by flasher when enabled
|
||||
@ -86,7 +80,6 @@ local function indicator_led_pair(args)
|
||||
elseif new_state <= 1 then
|
||||
flash_on = false
|
||||
flasher.stop(flash_callback)
|
||||
|
||||
e.w_blit("\x8c", co, e.fg_bg.blit_bkg)
|
||||
end
|
||||
elseif new_state == 2 then
|
||||
@ -102,12 +95,17 @@ local function indicator_led_pair(args)
|
||||
---@param val integer indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
e.on_update(1)
|
||||
-- draw label and indicator light
|
||||
function e.redraw()
|
||||
e.on_update(e.value)
|
||||
if string.len(args.label) > 0 then
|
||||
e.w_set_cur(3, 1)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -18,19 +18,15 @@ local element = require("graphics.element")
|
||||
---@param args indicator_led_rgb_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function indicator_led_rgb(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.ledrgb: label is a required field")
|
||||
assert(type(args.colors) == "table", "graphics.elements.indicators.ledrgb: colors is a required field")
|
||||
assert(type(args.label) == "string", "indicators.ledrgb: label is a required field")
|
||||
assert(type(args.colors) == "table", "indicators.ledrgb: colors is a required field")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 0, string.len(args.label)) + 2
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- init value for initial check in on_update
|
||||
e.value = 1
|
||||
|
||||
-- on state change
|
||||
@ -47,12 +43,17 @@ local function indicator_led_rgb(args)
|
||||
---@param val integer indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
e.on_update(1)
|
||||
-- draw label and indicator light
|
||||
function e.redraw()
|
||||
e.on_update(e.value)
|
||||
if string.len(args.label) > 0 then
|
||||
e.w_set_cur(3, 1)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -23,25 +23,23 @@ local flasher = require("graphics.flasher")
|
||||
---@param args indicator_light_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function indicator_light(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.light: label is a required field")
|
||||
assert(type(args.colors) == "table", "graphics.elements.indicators.light: colors is a required field")
|
||||
assert(type(args.label) == "string", "indicators.light: label is a required field")
|
||||
assert(type(args.colors) == "table", "indicators.light: colors is a required field")
|
||||
|
||||
if args.flash then
|
||||
assert(util.is_int(args.period), "graphics.elements.indicators.light: period is a required field if flash is enabled")
|
||||
assert(util.is_int(args.period), "indicators.light: period is a required field if flash is enabled")
|
||||
end
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 1, string.len(args.label)) + 2
|
||||
|
||||
-- flasher state
|
||||
local flash_on = true
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = false
|
||||
|
||||
-- called by flasher when enabled
|
||||
local function flash_callback()
|
||||
e.w_set_cur(1, 1)
|
||||
@ -88,10 +86,15 @@ local function indicator_light(args)
|
||||
---@param val boolean indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
-- draw label and indicator light
|
||||
function e.redraw()
|
||||
e.on_update(false)
|
||||
e.w_set_cur(3, 1)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -9,7 +9,7 @@ local element = require("graphics.element")
|
||||
---@field format string power format override (lua string format)
|
||||
---@field rate boolean? whether to append /t to the end (power per tick)
|
||||
---@field lu_colors? cpair label foreground color (a), unit foreground color (b)
|
||||
---@field value any default value
|
||||
---@field value number default value
|
||||
---@field parent graphics_element
|
||||
---@field id? string element id
|
||||
---@field x? integer 1 if omitted
|
||||
@ -23,26 +23,17 @@ local element = require("graphics.element")
|
||||
---@param args power_indicator_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function power(args)
|
||||
assert(args.value ~= nil, "graphics.elements.indicators.power: value is a required field")
|
||||
assert(util.is_int(args.width), "graphics.elements.indicators.power: width is a required field")
|
||||
assert(type(args.value) == "number", "indicators.power: value is a required number field")
|
||||
assert(util.is_int(args.width), "indicators.power: width is a required field")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- label color
|
||||
if args.lu_colors ~= nil then
|
||||
e.w_set_fgd(args.lu_colors.color_a)
|
||||
end
|
||||
e.value = args.value
|
||||
|
||||
-- write label
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
local data_start = string.len(args.label) + 2
|
||||
if string.len(args.label) == 0 then data_start = 1 end
|
||||
local data_start = 0
|
||||
|
||||
-- on state change
|
||||
---@param value any new value
|
||||
@ -77,8 +68,20 @@ local function power(args)
|
||||
---@param val any new value
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- initial value draw
|
||||
e.on_update(args.value)
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
if args.lu_colors ~= nil then e.w_set_fgd(args.lu_colors.color_a) end
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
data_start = string.len(args.label) + 2
|
||||
if string.len(args.label) == 0 then data_start = 1 end
|
||||
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -10,7 +10,7 @@ local element = require("graphics.element")
|
||||
---@field format string data format (lua string format)
|
||||
---@field commas? boolean whether to use commas if a number is given (default to false)
|
||||
---@field lu_colors? cpair label foreground color (a), unit foreground color (b)
|
||||
---@field value any default value
|
||||
---@field value number default value
|
||||
---@field parent graphics_element
|
||||
---@field id? string element id
|
||||
---@field x? integer 1 if omitted
|
||||
@ -24,24 +24,17 @@ local element = require("graphics.element")
|
||||
---@param args rad_indicator_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function rad(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.rad: label is a required field")
|
||||
assert(type(args.format) == "string", "graphics.elements.indicators.rad: format is a required field")
|
||||
assert(util.is_int(args.width), "graphics.elements.indicators.rad: width is a required field")
|
||||
assert(type(args.value) ~= "number", "indicators.rad: value is a required number field")
|
||||
assert(type(args.label) == "string", "indicators.rad: label is a required field")
|
||||
assert(type(args.format) == "string", "indicators.rad: format is a required field")
|
||||
assert(util.is_int(args.width), "indicators.rad: width is a required field")
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- label color
|
||||
if args.lu_colors ~= nil then
|
||||
e.w_set_fgd(args.lu_colors.color_a)
|
||||
end
|
||||
|
||||
-- write label
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
e.value = types.new_zero_radiation_reading()
|
||||
|
||||
local label_len = string.len(args.label)
|
||||
local data_start = 1
|
||||
@ -82,8 +75,17 @@ local function rad(args)
|
||||
---@param val any new value
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- initial value draw
|
||||
e.on_update(types.new_zero_radiation_reading())
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
if args.lu_colors ~= nil then e.w_set_fgd(args.lu_colors.color_a) end
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_write(args.label)
|
||||
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -25,16 +25,14 @@ local element = require("graphics.element")
|
||||
---@param args state_indicator_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function state_indicator(args)
|
||||
assert(type(args.states) == "table", "graphics.elements.indicators.state: states is a required field")
|
||||
assert(type(args.states) == "table", "indicators.state: states is a required field")
|
||||
|
||||
-- determine height
|
||||
if util.is_int(args.height) then
|
||||
assert(args.height % 2 == 1, "graphics.elements.indicators.state: height should be an odd number")
|
||||
assert(args.height % 2 == 1, "indicators.state: height should be an odd number")
|
||||
else
|
||||
args.height = 1
|
||||
end
|
||||
|
||||
-- initial guess at width
|
||||
args.width = args.min_width or 1
|
||||
|
||||
-- state blit strings
|
||||
@ -42,7 +40,6 @@ local function state_indicator(args)
|
||||
for i = 1, #args.states do
|
||||
local state_def = args.states[i] ---@type state_text_color
|
||||
|
||||
-- re-determine width
|
||||
if string.len(state_def.text) > args.width then
|
||||
args.width = string.len(state_def.text)
|
||||
end
|
||||
@ -59,13 +56,20 @@ local function state_indicator(args)
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = args.value or 1
|
||||
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
local blit_cmd = state_blit_cmds[e.value]
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_blit(blit_cmd.text, blit_cmd.fgd, blit_cmd.bkg)
|
||||
end
|
||||
|
||||
-- on state change
|
||||
---@param new_state integer indicator state
|
||||
function e.on_update(new_state)
|
||||
local blit_cmd = state_blit_cmds[new_state]
|
||||
e.value = new_state
|
||||
e.w_set_cur(1, 1)
|
||||
e.w_blit(blit_cmd.text, blit_cmd.fgd, blit_cmd.bkg)
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- set indicator state
|
||||
@ -73,7 +77,7 @@ local function state_indicator(args)
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- initial draw
|
||||
e.on_update(args.value or 1)
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -25,35 +25,29 @@ local flasher = require("graphics.flasher")
|
||||
---@param args tristate_indicator_light_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function tristate_indicator_light(args)
|
||||
assert(type(args.label) == "string", "graphics.elements.indicators.trilight: label is a required field")
|
||||
assert(type(args.c1) == "number", "graphics.elements.indicators.trilight: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "graphics.elements.indicators.trilight: c2 is a required field")
|
||||
assert(type(args.c3) == "number", "graphics.elements.indicators.trilight: c3 is a required field")
|
||||
assert(type(args.label) == "string", "indicators.trilight: label is a required field")
|
||||
assert(type(args.c1) == "number", "indicators.trilight: c1 is a required field")
|
||||
assert(type(args.c2) == "number", "indicators.trilight: c2 is a required field")
|
||||
assert(type(args.c3) == "number", "indicators.trilight: c3 is a required field")
|
||||
|
||||
if args.flash then
|
||||
assert(util.is_int(args.period), "graphics.elements.indicators.trilight: period is a required field if flash is enabled")
|
||||
assert(util.is_int(args.period), "indicators.trilight: period is a required field if flash is enabled")
|
||||
end
|
||||
|
||||
-- single line
|
||||
args.height = 1
|
||||
|
||||
-- determine width
|
||||
args.width = math.max(args.min_label_width or 1, string.len(args.label)) + 2
|
||||
|
||||
-- flasher state
|
||||
local flash_on = true
|
||||
|
||||
-- blit translations
|
||||
local c1 = colors.toBlit(args.c1)
|
||||
local c2 = colors.toBlit(args.c2)
|
||||
local c3 = colors.toBlit(args.c3)
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- init value for initial check in on_update
|
||||
e.value = 1
|
||||
|
||||
local flash_on = true
|
||||
|
||||
local c1 = colors.toBlit(args.c1)
|
||||
local c2 = colors.toBlit(args.c2)
|
||||
local c3 = colors.toBlit(args.c3)
|
||||
|
||||
-- called by flasher when enabled
|
||||
local function flash_callback()
|
||||
e.w_set_cur(1, 1)
|
||||
@ -102,9 +96,14 @@ local function tristate_indicator_light(args)
|
||||
---@param val integer indicator state
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- write label and initial indicator light
|
||||
-- draw light and label
|
||||
function e.redraw()
|
||||
e.on_update(1)
|
||||
e.w_write(args.label)
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -20,13 +20,13 @@ local element = require("graphics.element")
|
||||
---@param args vbar_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function vbar(args)
|
||||
-- properties/state
|
||||
local last_num_bars = -1
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- blit strings
|
||||
e.value = 0.0
|
||||
|
||||
local last_num_bars = -1
|
||||
|
||||
local fgd = string.rep(e.fg_bg.blit_fgd, e.frame.w)
|
||||
local bkg = string.rep(e.fg_bg.blit_bkg, e.frame.w)
|
||||
local spaces = util.spaces(e.frame.w)
|
||||
@ -52,10 +52,7 @@ local function vbar(args)
|
||||
if num_bars ~= last_num_bars then
|
||||
last_num_bars = num_bars
|
||||
|
||||
-- start bottom up
|
||||
local y = e.frame.h
|
||||
|
||||
-- start at base of vertical bar
|
||||
e.w_set_cur(1, y)
|
||||
|
||||
-- fill percentage
|
||||
@ -83,22 +80,26 @@ local function vbar(args)
|
||||
end
|
||||
end
|
||||
|
||||
-- set the percentage value
|
||||
---@param val number 0.0 to 1.0
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
last_num_bars = -1
|
||||
e.on_update(e.value)
|
||||
end
|
||||
|
||||
-- change bar color
|
||||
---@param fg_bg cpair new bar colors
|
||||
function e.recolor(fg_bg)
|
||||
fgd = string.rep(fg_bg.blit_fgd, e.frame.w)
|
||||
bkg = string.rep(fg_bg.blit_bkg, e.frame.w)
|
||||
|
||||
-- re-draw
|
||||
last_num_bars = 0
|
||||
if type(e.value) == "number" then
|
||||
e.on_update(e.value)
|
||||
end
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- set the percentage value
|
||||
---@param val number 0.0 to 1.0
|
||||
function e.set_value(val) e.on_update(val) end
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -274,9 +274,21 @@ local function listbox(args)
|
||||
end
|
||||
end
|
||||
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
draw_arrows(0)
|
||||
draw_bar()
|
||||
|
||||
-- redraw all children
|
||||
for i = 1, #list do
|
||||
local item = list[i] ---@type listbox_item
|
||||
item.e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
||||
|
@ -19,23 +19,30 @@ local element = require("graphics.element")
|
||||
---@param args multipane_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function multipane(args)
|
||||
assert(type(args.panes) == "table", "graphics.elements.multipane: panes is a required field")
|
||||
assert(type(args.panes) == "table", "multipane: panes is a required field")
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = 1
|
||||
|
||||
-- show the selected pane
|
||||
function e.redraw()
|
||||
for i = 1, #args.panes do args.panes[i].hide() end
|
||||
args.panes[e.value].show()
|
||||
end
|
||||
|
||||
-- select which pane is shown
|
||||
---@param value integer pane to show
|
||||
function e.set_value(value)
|
||||
if (e.value ~= value) and (value > 0) and (value <= #args.panes) then
|
||||
e.value = value
|
||||
|
||||
for i = 1, #args.panes do args.panes[i].hide() end
|
||||
args.panes[value].show()
|
||||
e.redraw()
|
||||
end
|
||||
end
|
||||
|
||||
e.set_value(1)
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
@ -24,12 +24,11 @@ local element = require("graphics.element")
|
||||
---@param args pipenet_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function pipenet(args)
|
||||
assert(type(args.pipes) == "table", "graphics.elements.indicators.pipenet: pipes is a required field")
|
||||
assert(type(args.pipes) == "table", "pipenet: pipes is a required field")
|
||||
|
||||
args.width = 0
|
||||
args.height = 0
|
||||
|
||||
-- determine width/height
|
||||
for i = 1, #args.pipes do
|
||||
local pipe = args.pipes[i] ---@type pipe
|
||||
|
||||
@ -57,8 +56,8 @@ local function pipenet(args)
|
||||
if any_thin then break end
|
||||
end
|
||||
|
||||
if not any_thin then
|
||||
-- draw all pipes
|
||||
-- draw all pipes by drawing out lines
|
||||
local function vector_draw()
|
||||
for p = 1, #args.pipes do
|
||||
local pipe = args.pipes[p] ---@type pipe
|
||||
|
||||
@ -161,65 +160,17 @@ local function pipenet(args)
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
-- build map if using thin pipes, easist way to check adjacent blocks (cannot 'cheat' like with standard width)
|
||||
local map = {}
|
||||
|
||||
-- allocate map
|
||||
for x = 1, args.width do
|
||||
table.insert(map, {})
|
||||
for _ = 1, args.height do table.insert(map[x], false) end
|
||||
end
|
||||
|
||||
-- build map
|
||||
for p = 1, #args.pipes do
|
||||
local pipe = args.pipes[p] ---@type pipe
|
||||
|
||||
local x = 1 + pipe.x1
|
||||
local y = 1 + pipe.y1
|
||||
|
||||
local x_step = util.trinary(pipe.x1 >= pipe.x2, -1, 1)
|
||||
local y_step = util.trinary(pipe.y1 >= pipe.y2, -1, 1)
|
||||
|
||||
local entry = { atr = pipe.align_tr, thin = pipe.thin, fg = colors.toBlit(pipe.color), bg = e.fg_bg.blit_bkg }
|
||||
|
||||
if pipe.align_tr then
|
||||
-- cross width then height
|
||||
for _ = 1, pipe.w do
|
||||
map[x][y] = entry
|
||||
x = x + x_step
|
||||
end
|
||||
|
||||
x = x - x_step -- back up one
|
||||
|
||||
for _ = 1, pipe.h do
|
||||
map[x][y] = entry
|
||||
y = y + y_step
|
||||
end
|
||||
else
|
||||
-- cross height then width
|
||||
for _ = 1, pipe.h do
|
||||
map[x][y] = entry
|
||||
y = y + y_step
|
||||
end
|
||||
|
||||
y = y - y_step -- back up one
|
||||
|
||||
for _ = 1, pipe.w do
|
||||
map[x][y] = entry
|
||||
x = x + x_step
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- render
|
||||
for x = 1, args.width do
|
||||
for y = 1, args.height do
|
||||
local entry = map[x][y] ---@type _pipe_map_entry|false
|
||||
-- draw a particular map cell
|
||||
---@param map table 2D cell map
|
||||
---@param x integer x coord
|
||||
---@param y integer y coord
|
||||
local function draw_map_cell(map, x, y)
|
||||
local entry = map[x][y] ---@type _pipe_map_entry already confirmed not false
|
||||
local char
|
||||
local invert = false
|
||||
|
||||
if entry ~= false then
|
||||
local function check(cx, cy)
|
||||
return (map[cx] ~= nil) and (map[cx][cy] ~= nil) and (map[cx][cy] ~= false) and (map[cx][cy].fg == entry.fg)
|
||||
end
|
||||
@ -306,10 +257,74 @@ local function pipenet(args)
|
||||
e.w_blit(char, entry.fg, entry.bg)
|
||||
end
|
||||
end
|
||||
|
||||
-- draw all pipes by assembling and marking up a 2D map<br>
|
||||
-- this is an easy way to check adjacent blocks, which is required to properly draw thin pipes
|
||||
local function map_draw()
|
||||
local map = {}
|
||||
|
||||
for x = 1, args.width do
|
||||
table.insert(map, {})
|
||||
for _ = 1, args.height do table.insert(map[x], false) end
|
||||
end
|
||||
|
||||
-- build map
|
||||
for p = 1, #args.pipes do
|
||||
local pipe = args.pipes[p] ---@type pipe
|
||||
|
||||
local x = 1 + pipe.x1
|
||||
local y = 1 + pipe.y1
|
||||
|
||||
local x_step = util.trinary(pipe.x1 >= pipe.x2, -1, 1)
|
||||
local y_step = util.trinary(pipe.y1 >= pipe.y2, -1, 1)
|
||||
|
||||
local entry = { atr = pipe.align_tr, thin = pipe.thin, fg = colors.toBlit(pipe.color), bg = e.fg_bg.blit_bkg }
|
||||
|
||||
if pipe.align_tr then
|
||||
-- cross width then height
|
||||
for _ = 1, pipe.w do
|
||||
map[x][y] = entry
|
||||
x = x + x_step
|
||||
end
|
||||
|
||||
x = x - x_step -- back up one
|
||||
|
||||
for _ = 1, pipe.h do
|
||||
map[x][y] = entry
|
||||
y = y + y_step
|
||||
end
|
||||
else
|
||||
-- cross height then width
|
||||
for _ = 1, pipe.h do
|
||||
map[x][y] = entry
|
||||
y = y + y_step
|
||||
end
|
||||
|
||||
y = y - y_step -- back up one
|
||||
|
||||
for _ = 1, pipe.w do
|
||||
map[x][y] = entry
|
||||
x = x + x_step
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- render
|
||||
for x = 1, args.width do
|
||||
for y = 1, args.height do
|
||||
if map[x][y] ~= false then draw_map_cell(map, x, y) end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- element redraw
|
||||
function e.redraw()
|
||||
if any_thin then map_draw() else vector_draw() end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
||||
|
@ -22,7 +22,7 @@ local element = require("graphics.element")
|
||||
---@param args rectangle_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function rectangle(args)
|
||||
assert(args.border ~= nil or args.thin ~= true, "graphics.elements.rectangle: thin requires border to be provided")
|
||||
assert(args.border ~= nil or args.thin ~= true, "rectangle: thin requires border to be provided")
|
||||
|
||||
-- if thin, then width will always need to be 1
|
||||
if args.thin == true then
|
||||
@ -65,8 +65,8 @@ local function rectangle(args)
|
||||
local inner_width = e.frame.w - width_x2
|
||||
|
||||
-- check dimensions
|
||||
assert(width_x2 <= e.frame.w, "graphics.elements.rectangle: border too thick for width")
|
||||
assert(width_x2 <= e.frame.h, "graphics.elements.rectangle: border too thick for height")
|
||||
assert(width_x2 <= e.frame.w, "rectangle: border too thick for width")
|
||||
assert(width_x2 <= e.frame.h, "rectangle: border too thick for height")
|
||||
|
||||
-- form the basic line strings and top/bottom blit strings
|
||||
local spaces = util.spaces(e.frame.w)
|
||||
@ -126,6 +126,7 @@ local function rectangle(args)
|
||||
end
|
||||
|
||||
-- draw rectangle with borders
|
||||
function e.redraw()
|
||||
for y = 1, e.frame.h do
|
||||
e.w_set_cur(1, y)
|
||||
-- top border
|
||||
@ -186,6 +187,10 @@ local function rectangle(args)
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw of border
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
||||
|
@ -24,19 +24,20 @@ local TEXT_ALIGN = core.TEXT_ALIGN
|
||||
---@param args textbox_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function textbox(args)
|
||||
assert(type(args.text) == "string", "graphics.elements.textbox: text is a required field")
|
||||
assert(type(args.text) == "string", "textbox: text is a required field")
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
e.value = args.text
|
||||
|
||||
local alignment = args.alignment or TEXT_ALIGN.LEFT
|
||||
|
||||
-- draw textbox
|
||||
function e.redraw()
|
||||
e.window.clear()
|
||||
|
||||
local function display_text(text)
|
||||
e.value = text
|
||||
|
||||
local lines = util.strwrap(text, e.frame.w)
|
||||
local lines = util.strwrap(e.value, e.frame.w)
|
||||
|
||||
for i = 1, #lines do
|
||||
if i > e.frame.h then break end
|
||||
@ -56,15 +57,16 @@ local function textbox(args)
|
||||
end
|
||||
end
|
||||
|
||||
display_text(args.text)
|
||||
|
||||
-- set the string value and re-draw the text
|
||||
---@param val string value
|
||||
function e.set_value(val)
|
||||
e.window.clear()
|
||||
display_text(val)
|
||||
e.value = val
|
||||
e.redraw()
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
||||
|
@ -22,13 +22,11 @@ local element = require("graphics.element")
|
||||
---@param args tiling_args
|
||||
---@return graphics_element element, element_id id
|
||||
local function tiling(args)
|
||||
assert(type(args.fill_c) == "table", "graphics.elements.tiling: fill_c is a required field")
|
||||
assert(type(args.fill_c) == "table", "tiling: fill_c is a required field")
|
||||
|
||||
-- create new graphics element base object
|
||||
local e = element.new(args)
|
||||
|
||||
-- draw tiling box
|
||||
|
||||
local fill_a = args.fill_c.blit_a
|
||||
local fill_b = args.fill_c.blit_b
|
||||
|
||||
@ -38,13 +36,9 @@ local function tiling(args)
|
||||
local start_y = 1
|
||||
local inner_width = math.floor(e.frame.w / util.trinary(even, 2, 1))
|
||||
local inner_height = e.frame.h
|
||||
local alternator = true
|
||||
|
||||
-- border
|
||||
if args.border_c ~= nil then
|
||||
e.w_set_bkg(args.border_c)
|
||||
e.window.clear()
|
||||
|
||||
start_x = 1 + util.trinary(even, 2, 1)
|
||||
start_y = 2
|
||||
|
||||
@ -53,12 +47,21 @@ local function tiling(args)
|
||||
end
|
||||
|
||||
-- check dimensions
|
||||
assert(inner_width > 0, "graphics.elements.tiling: inner_width <= 0")
|
||||
assert(inner_height > 0, "graphics.elements.tiling: inner_height <= 0")
|
||||
assert(start_x <= inner_width, "graphics.elements.tiling: start_x > inner_width")
|
||||
assert(start_y <= inner_height, "graphics.elements.tiling: start_y > inner_height")
|
||||
assert(inner_width > 0, "tiling: inner_width <= 0")
|
||||
assert(inner_height > 0, "tiling: inner_height <= 0")
|
||||
assert(start_x <= inner_width, "tiling: start_x > inner_width")
|
||||
assert(start_y <= inner_height, "tiling: start_y > inner_height")
|
||||
|
||||
-- create pattern
|
||||
-- draw tiling box
|
||||
function e.redraw()
|
||||
local alternator = true
|
||||
|
||||
if args.border_c ~= nil then
|
||||
e.w_set_bkg(args.border_c)
|
||||
e.window.clear()
|
||||
end
|
||||
|
||||
-- draw pattern
|
||||
for y = start_y, inner_height + (start_y - 1) do
|
||||
e.w_set_cur(start_x, y)
|
||||
for _ = 1, inner_width do
|
||||
@ -81,6 +84,10 @@ local function tiling(args)
|
||||
|
||||
if inner_width % 2 == 0 then alternator = not alternator end
|
||||
end
|
||||
end
|
||||
|
||||
-- initial draw
|
||||
e.redraw()
|
||||
|
||||
return e.complete()
|
||||
end
|
||||
|
Loading…
Reference in New Issue
Block a user