Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 17 additions & 9 deletions tabular.lua
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
local _tl_compat; if (tonumber((_VERSION or ''):match('[%d.]*$')) or 0) < 5.3 then local p, m = pcall(require, 'compat53.module'); if p then _tl_compat = m end end; local ipairs = _tl_compat and _tl_compat.ipairs or ipairs; local math = _tl_compat and _tl_compat.math or math; local os = _tl_compat and _tl_compat.os or os; local pairs = _tl_compat and _tl_compat.pairs or pairs; local string = _tl_compat and _tl_compat.string or string; local table = _tl_compat and _tl_compat.table or table; local utf8 = _tl_compat and _tl_compat.utf8 or utf8; local tabular = {}
local _tl_compat; if (tonumber((_VERSION or ''):match('[%d.]*$')) or 0) < 5.3 then local p, m = pcall(require, 'compat53.module'); if p then _tl_compat = m end end; local ipairs = _tl_compat and _tl_compat.ipairs or ipairs; local math = _tl_compat and _tl_compat.math or math; local os = _tl_compat and _tl_compat.os or os; local pairs = _tl_compat and _tl_compat.pairs or pairs; local string = _tl_compat and _tl_compat.string or string; local table = _tl_compat and _tl_compat.table or table; local utf8 = _tl_compat and _tl_compat.utf8 or utf8



local tabular = {}


local AnsiColors = {}



Expand Down Expand Up @@ -63,7 +67,7 @@ if (os.getenv("LANG") or ""):upper():match("UTF%-?8") then

end

local Output = {}




Expand All @@ -80,7 +84,7 @@ local function escape_chars(c)
return "\\" .. string.byte(c)
end

local Pair = {}


local function show_as_list(t, color, seen, ids, skip_array)
local tt = {}
Expand Down Expand Up @@ -136,7 +140,7 @@ local function show_primitive(t)
return out
end

local Row = {}




Expand Down Expand Up @@ -194,7 +198,7 @@ show_as_columns = function(t, bgcolor, seen, ids, column_order, skip_header)
elseif bgcolor then
table.insert(line, bgcolor)
end
table.insert(line, text .. (" "):rep(w - strlen(text)))
table.insert(line, text .. (" "):rep((w - strlen(text))))
if color then
table.insert(line, bgcolor)
end
Expand Down Expand Up @@ -236,7 +240,7 @@ show_as_columns = function(t, bgcolor, seen, ids, column_order, skip_header)
local line = { draw.V }
for _, cname in ipairs(column_names) do
local row = columns[cname][i]
output_cell(line, cname, row and row[h] or "", bgcolor and colors[(i % #colors) + 1])
output_cell(line, cname, row and row[math.floor(h)] or "", bgcolor and colors[(i % #colors) + 1])
end
output_line(out, table.concat(line))
end
Expand Down Expand Up @@ -266,7 +270,7 @@ show = function(t, color, seen, ids, column_order)

if type(t) == "table" then
local tt = t
if #tt > 0 and type(tt[1]) == "table" then
if #(tt) > 0 and type(tt[1]) == "table" then
return show_as_columns(tt, color, seen, ids, column_order)
else
return show_as_list(tt, color, seen, ids)
Expand Down Expand Up @@ -302,4 +306,8 @@ if arg and arg[0]:match("tabular%..*$") then
os.exit(0)
end

return setmetatable(tabular, { __call = function(_, ...) return tabular.show(...) end })
return setmetatable(tabular, {
__call = function(_, ...)
return tabular.show(...)
end,
})
44 changes: 26 additions & 18 deletions tabular.tl
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
local tabular = {}
local record Tabular
show: function(t: any, column_order?: {string}, color?: boolean): string
end

local tabular: Tabular = {}

local record AnsiColors
noReset: function(string):string
Expand Down Expand Up @@ -26,7 +30,7 @@ local colors: {string} = {
ansicolors.noReset("%{white}"),
}

local function strlen(s: string): number
local function strlen(s: string): integer
s = s:gsub("\27[^m]*m", "")
return #s
end
Expand All @@ -48,17 +52,17 @@ if (os.getenv("LANG") or ""):upper():match("UTF%-?8") then
X = "┼",
}

strlen = function(s: string): number
strlen = function(s: string): integer
s = s:gsub("\27[^m]*m", "")
return utf8.len(s) or #s
return utf8.len(s) as integer or #s
end

strsub = function(s: string, i: number, j: number): string
local uj = utf8.offset(s, j + 1)
local uj: number = utf8.offset(s, j + 1)
if uj then
uj = uj - 1
end
return s:sub(utf8.offset(s, i), uj)
return s:sub(utf8.offset(s, i) as integer, uj as integer)
end

end
Expand All @@ -68,8 +72,8 @@ local record Output
width: number
end

local show: function(any, string, {any:boolean}, {any:number}, {string}):Output
local show_as_columns: function({{any:any}}, string, {any:boolean}, {any:number}, {string}, boolean): Output
local show: function(any, string, {any:boolean}, {any:number}, ?{string}):Output
local show_as_columns: function({{any:any}}, string, {any:boolean}, {any:number}, {string}, ?boolean): Output

local function output_line(out: Output, line: string)
table.insert(out, line)
Expand All @@ -82,7 +86,7 @@ end

local type Pair = {string, any}

local function show_as_list(t: {any:any}, color: string, seen: {any:boolean}, ids: {any:number}, skip_array: boolean): Output
local function show_as_list(t: {any:any}, color: string, seen: {any:boolean}, ids: {any:number}, skip_array?: boolean): Output
local tt: {Pair} = {}
local width = 0
local keys = {}
Expand Down Expand Up @@ -186,15 +190,15 @@ show_as_columns = function(t: {{any:any}}, bgcolor: string, seen: {any:boolean},
table.sort(column_names)
end

local function output_cell(line: {string}, cname: string, text: string, color: string)
local function output_cell(line: {string}, cname: string, text: string, color?: string)
local w = columns[cname].width
text = text or ""
if color then
table.insert(line, color)
elseif bgcolor then
table.insert(line, bgcolor)
end
table.insert(line, text .. (" "):rep(w - strlen(text)))
table.insert(line, text .. (" "):rep((w - strlen(text)) as integer))
if color then
table.insert(line, bgcolor)
end
Expand All @@ -207,8 +211,8 @@ show_as_columns = function(t: {{any:any}}, bgcolor: string, seen: {any:boolean},
local border_bot = {}
for i, cname in ipairs(column_names) do
local w = columns[cname].width
table.insert(border_top, draw.H:rep(w))
table.insert(border_bot, draw.H:rep(w))
table.insert(border_top, draw.H:rep(w as integer))
table.insert(border_bot, draw.H:rep(w as integer))
if i < #column_names then
table.insert(border_top, draw.N)
table.insert(border_bot, draw.S)
Expand Down Expand Up @@ -236,7 +240,7 @@ show_as_columns = function(t: {{any:any}}, bgcolor: string, seen: {any:boolean},
local line = { draw.V }
for _, cname in ipairs(column_names) do
local row = columns[cname][i]
output_cell(line, cname, row and row[h] or "", bgcolor and colors[(i % #colors) + 1])
output_cell(line, cname, row and row[math.floor(h)] or "", bgcolor and colors[(i % #colors) + 1])
end
output_line(out, table.concat(line))
end
Expand Down Expand Up @@ -266,7 +270,7 @@ show = function(t: any, color: string, seen: {any:boolean}, ids: {any:number}, c

if type(t) == "table" then
local tt = t as {any:any}
if #tt > 0 and type(tt[1]) == "table" then
if #(tt as {any}) > 0 and type(tt[1]) == "table" then
return show_as_columns(tt as {{any:any}}, color, seen, ids, column_order)
else
return show_as_list(tt, color, seen, ids)
Expand All @@ -276,7 +280,7 @@ show = function(t: any, color: string, seen: {any:boolean}, ids: {any:number}, c
end
end

local function detect_cycles(t: any, n: number, seen: {any:number}): {any:number}, number
local function detect_cycles(t: any, n?: number, seen?: {any:number}): {any:number}, number
n = n or 0
seen = seen or {}
if type(t) == "table" then
Expand All @@ -292,7 +296,7 @@ local function detect_cycles(t: any, n: number, seen: {any:number}): {any:number
return seen, n
end

function tabular.show(t: any, column_order: {string}, color: boolean): string
function tabular.show(t: any, column_order?: {string}, color?: boolean): string
local ids = detect_cycles(t)
return table.concat(show(t, color and colors and ansicolors.noReset("%{reset}"), {}, ids, column_order), "\n")
end
Expand All @@ -302,4 +306,8 @@ if arg and arg[0]:match("tabular%..*$") then
os.exit(0)
end

return setmetatable( tabular, { __call = function(_, ...): string return tabular.show(...) end } )
return setmetatable( tabular, {
__call = function(_: Tabular, ...:any): string
return tabular.show(... as {string})
end
} )