ona/src/flow/states.zig
kayomn 99c3818477
All checks were successful
continuous-integration/drone/push Build is passing
Simplify 2D rendering interfaces
2024-07-17 23:32:10 +01:00

88 lines
1.8 KiB
Zig

const coral = @import("coral");
const std = @import("std");
pub const Table = struct {
arena: std.heap.ArenaAllocator,
table: coral.map.Hashed(TypeID, Entry, coral.map.enum_traits(TypeID)),
const Entry = struct {
ptr: *anyopaque,
};
pub fn deinit(self: *Table) void {
self.table.deinit();
self.arena.deinit();
self.* = undefined;
}
pub fn get(self: Table, comptime Resource: type) ?*Resource {
if (self.table.get(type_id(Resource))) |entry| {
return @ptrCast(@alignCast(entry.ptr));
}
return null;
}
pub fn init() Table {
return .{
.arena = std.heap.ArenaAllocator.init(coral.heap.allocator),
.table = .{.allocator = coral.heap.allocator},
};
}
pub fn set_get(self: *Table, value: anytype) std.mem.Allocator.Error!*@TypeOf(value) {
try self.set(value);
return self.get(@TypeOf(value)).?;
}
pub fn set(self: *Table, value: anytype) std.mem.Allocator.Error!void {
const Value = @TypeOf(value);
const value_id = type_id(Value);
if (self.table.get(value_id)) |entry| {
@as(*Value, @ptrCast(@alignCast(entry.ptr))).* = value;
} else {
const resource_allocator = self.arena.allocator();
const allocated_resource = try resource_allocator.create(Value);
errdefer resource_allocator.destroy(allocated_resource);
std.debug.assert(try self.table.emplace(value_id, .{
.ptr = allocated_resource,
}));
allocated_resource.* = value;
}
}
};
pub const ThreadRestriction = enum {
none,
main,
};
pub const TypeID = enum (usize) { _ };
pub fn type_id(comptime T: type) TypeID {
const TypeHandle = struct {
comptime {
_ = T;
}
var byte: u8 = 0;
};
return @enumFromInt(@intFromPtr(&TypeHandle.byte));
}
pub fn thread_restriction(comptime State: type) ThreadRestriction {
if (@hasDecl(State, "thread_restriction")) {
return State.thread_restriction;
}
return .none;
}