const std = @import("std"); const core = @import("core"); const Name = core.Name; pub var gLocDbRef: ?*anyopaque = null; pub var gLocDbInterface: *LocDbInterface = undefined; pub const LocDbErrors = error{ OutOfMemory, UnableToSetLocalization, UnknownError, }; pub const LocDbInterface = struct { // Fetches the localized version of the string if it exists setLocalization: *const fn (*anyopaque, Name) LocDbErrors!void, getLocalized: *const fn (*anyopaque, u32) ?[]const u8, createEntry: *const fn (*anyopaque, u32, []const u8) LocDbErrors!u32, pub fn from(comptime TargetType: type) void { const W = struct { pub fn getLocalized(pointer: *anyopaque, key: u32) ?[]const u8 { var ptr = @as(*TargetType, @ptrCast(@alignCast(pointer))); return ptr.getLocalized(key); } pub fn createEntry(pointer: *anyopaque, key: u32, source: []const u8) LocDbErrors!u32 { var ptr = @as(*TargetType, @ptrCast(@alignCast(pointer))); try ptr.createEntry(key, source); } pub fn setLocalization(pointer: *anyopaque, name: Name) LocDbErrors!void { var ptr = @as(*TargetType, @ptrCast(@alignCast(pointer))); try ptr.setLocalization(name); } }; return @This(){ .getLocalized = W.getLocalized, .createEntry = W.createEntry, .setLocalization = W.setLocalization, }; } }; pub fn setupLocDb(ref: *anyopaque, interface: *LocDbInterface) void { gLocDbRef = ref; gLocDbInterface = interface; } // Anything display should probably be utilizing Text instead of just a normal []const u8, pub const LocText = struct { utf8: []const u8, localized: ?[]const u8 = null, locKey: u32 = 0, pub fn getRead(self: @This()) []const u8 { if (self.localized) |localized| { return localized; } if (gLocDbRef) |locdb| { return gLocDbInterface.getLocalized(locdb, self.locKey).?; } return self.utf8; } pub fn get(self: *@This()) []const u8 { if (self.localized) |localized| { return localized; } if (gLocDbRef) |locdb| { self.localized = gLocDbInterface.getLocalized(locdb, self.locKey); return self.localized.?; } return self.utf8; } pub fn fromUtf8(text: []const u8) @This() { return .{ .utf8 = text, }; } pub fn fromUtf8Z(text: []const u8) @This() { for (text, 0..) |ch, i| { if (ch == 0) { var slice: []const u8 = undefined; slice.ptr = text.ptr; slice.len = i; return .{ .utf8 = slice, }; } } return .{ .utf8 = text, }; } }; // text construction macro pub fn MakeText(comptime utf8: []const u8) LocText { return LocText.fromUtf8(utf8); }