aboutsummaryrefslogtreecommitdiff
path: root/system/libraries/format/table.zig
diff options
context:
space:
mode:
Diffstat (limited to 'system/libraries/format/table.zig')
-rw-r--r--system/libraries/format/table.zig101
1 files changed, 101 insertions, 0 deletions
diff --git a/system/libraries/format/table.zig b/system/libraries/format/table.zig
new file mode 100644
index 0000000..e26be32
--- /dev/null
+++ b/system/libraries/format/table.zig
@@ -0,0 +1,101 @@
+//! Table formatting
+
+const io = @import("io");
+const colors = @import("colors");
+
+pub const Alignment = enum {
+ left,
+ right,
+};
+
+pub const Column = struct {
+ name: []const u8,
+ color: u32 = colors.white,
+ alignment: Alignment = .left,
+};
+
+const MAX_COLUMNS = 8;
+const MAX_ROWS = 256;
+
+pub const Table = struct {
+ columns: []const Column,
+ col_widths: [MAX_COLUMNS]usize,
+ rows: [MAX_ROWS][MAX_COLUMNS][]const u8,
+ row_colors: [MAX_ROWS][MAX_COLUMNS]u32,
+ row_count: usize,
+
+ pub fn init(cols: []const Column) Table {
+ var t = Table{
+ .columns = cols,
+ .col_widths = [_]usize{0} ** MAX_COLUMNS,
+ .rows = undefined,
+ .row_colors = undefined,
+ .row_count = 0,
+ };
+
+ for (cols, 0..) |col, i| {
+ t.col_widths[i] = col.name.len;
+ }
+
+ return t;
+ }
+
+ pub fn row(self: *Table, cells: []const []const u8) void {
+ self.rowColored(cells, null);
+ }
+
+ pub fn rowColored(self: *Table, cells: []const []const u8, cell_colors: ?[]const u32) void {
+ if (self.row_count >= MAX_ROWS) return;
+
+ for (cells, 0..) |cell, i| {
+ if (i >= self.columns.len) break;
+ self.rows[self.row_count][i] = cell;
+
+ if (cell_colors) |cc| {
+ self.row_colors[self.row_count][i] = cc[i];
+ } else {
+ self.row_colors[self.row_count][i] = self.columns[i].color;
+ }
+
+ if (cell.len > self.col_widths[i]) {
+ self.col_widths[i] = cell.len;
+ }
+ }
+
+ self.row_count += 1;
+ }
+
+ pub fn print(self: *Table) void {
+ for (self.columns, 0..) |col, i| {
+ _ = io.mark(io.stream, col.name, colors.white) catch {};
+ self.printPadding(self.col_widths[i] - col.name.len + 2);
+ }
+ _ = io.mark(io.stream, "\n", colors.white) catch {};
+
+ for (0..self.row_count) |r| {
+ for (0..self.columns.len) |c| {
+ const cell = self.rows[r][c];
+ const col = self.columns[c];
+ const color = self.row_colors[r][c];
+
+ if (col.alignment == .right) {
+ self.printPadding(self.col_widths[c] - cell.len);
+ _ = io.mark(io.stream, cell, color) catch {};
+ self.printPadding(2);
+ } else {
+ _ = io.mark(io.stream, cell, color) catch {};
+ self.printPadding(self.col_widths[c] - cell.len + 2);
+ }
+ }
+ _ = io.mark(io.stream, "\n", colors.white) catch {};
+ }
+ }
+
+ fn printPadding(self: *Table, count: usize) void {
+ _ = self;
+ var i: usize = 0;
+ while (i < count) : (i += 1) {
+ _ = io.mark(io.stream, " ", colors.white) catch {};
+ }
+ }
+};