57 lines
1.2 KiB
Zig
57 lines
1.2 KiB
Zig
const std = @import("std");
|
|
|
|
pub const Error = error {};
|
|
|
|
vtable: *const VTable,
|
|
w: *std.Io.Writer,
|
|
|
|
const Self = @This();
|
|
|
|
pub const VTable = struct {
|
|
printField: *const fn (
|
|
ptr: *Self,
|
|
comptime field: []const u8,
|
|
comptime fmt: []const u8,
|
|
args: anytype,
|
|
) Error!void,
|
|
};
|
|
|
|
pub fn printField(
|
|
self: *const Self,
|
|
comptime field: []const u8,
|
|
value: anytype,
|
|
) Error!void {
|
|
self.vtable.field(self, field);
|
|
self.vtable.value(self, value);
|
|
}
|
|
|
|
pub const IndentedFormatter = struct {
|
|
indent: u8 = 0,
|
|
depth: usize = 0,
|
|
|
|
interface: Self,
|
|
|
|
pub fn init(w: *std.Io.Writer) IndentedFormatter {
|
|
return .{
|
|
.interface = .{
|
|
.vtable = &.{
|
|
.printField = IndentedFormatter.printField,
|
|
},
|
|
.w = w,
|
|
},
|
|
};
|
|
}
|
|
|
|
fn printField(
|
|
f: *Self,
|
|
comptime field: []const u8,
|
|
comptime fmt: []const u8,
|
|
args: anytype,
|
|
) Error!void {
|
|
const self: *IndentedFormatter = @alignCast(@fieldParentPtr("interface", f));
|
|
|
|
_ = try self.interface.w.splatByteAll(' ', self.indent * self.depth);
|
|
try self.interface.w.print(field ++ ": " ++ fmt ++ "\n", args);
|
|
}
|
|
};
|
|
|