freetype:harfbuzz: 100% blob and 50% buffer binding
This commit is contained in:
parent
d98bfab809
commit
2b7527b028
11 changed files with 502 additions and 52 deletions
|
|
@ -4,27 +4,37 @@ const Builder = std.build.Builder;
|
||||||
const ft_root = thisDir() ++ "/upstream/freetype";
|
const ft_root = thisDir() ++ "/upstream/freetype";
|
||||||
const ft_include_path = ft_root ++ "/include";
|
const ft_include_path = ft_root ++ "/include";
|
||||||
const hb_root = thisDir() ++ "/upstream/harfbuzz";
|
const hb_root = thisDir() ++ "/upstream/harfbuzz";
|
||||||
const hb_include_path = ft_root ++ "/src";
|
const hb_include_path = hb_root ++ "/src";
|
||||||
|
|
||||||
|
const utils_pkg = std.build.Pkg{
|
||||||
|
.name = "utils",
|
||||||
|
.source = .{ .path = thisDir() ++ "/src/utils.zig" },
|
||||||
|
};
|
||||||
|
|
||||||
pub const pkg = std.build.Pkg{
|
pub const pkg = std.build.Pkg{
|
||||||
.name = "freetype",
|
.name = "freetype",
|
||||||
.source = .{ .path = thisDir() ++ "/src/freetype/main.zig" },
|
.source = .{ .path = thisDir() ++ "/src/freetype/main.zig" },
|
||||||
|
.dependencies = &.{utils_pkg},
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const harfbuzz_pkg = std.build.Pkg{
|
pub const harfbuzz_pkg = std.build.Pkg{
|
||||||
.name = "harfbuzz",
|
.name = "harfbuzz",
|
||||||
.source = .{ .path = thisDir() ++ "/src/harfbuzz/main.zig" },
|
.source = .{ .path = thisDir() ++ "/src/harfbuzz/main.zig" },
|
||||||
|
.dependencies = &.{utils_pkg},
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const Options = struct {
|
pub const Options = struct {
|
||||||
harfbuzz: ?HarfbuzzOptions = null,
|
harfbuzz: ?HarfbuzzOptions = null,
|
||||||
freetype: FreetypeOptions = .{},
|
freetype: FreetypeOptions = .{},
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const FreetypeOptions = struct {
|
pub const FreetypeOptions = struct {
|
||||||
/// the path you specify freetype options
|
/// the path you specify freetype options
|
||||||
/// via `ftoptions.h` and `ftmodule.h`
|
/// via `ftoptions.h` and `ftmodule.h`
|
||||||
/// e.g `test/ft/`
|
/// e.g `test/ft/`
|
||||||
ft_config_path: ?[]const u8 = null,
|
ft_config_path: ?[]const u8 = null,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const HarfbuzzOptions = struct {};
|
pub const HarfbuzzOptions = struct {};
|
||||||
|
|
||||||
pub fn build(b: *std.build.Builder) !void {
|
pub fn build(b: *std.build.Builder) !void {
|
||||||
|
|
@ -34,8 +44,15 @@ pub fn build(b: *std.build.Builder) !void {
|
||||||
const freetype_tests = b.addTestSource(pkg.source);
|
const freetype_tests = b.addTestSource(pkg.source);
|
||||||
freetype_tests.setBuildMode(mode);
|
freetype_tests.setBuildMode(mode);
|
||||||
freetype_tests.setTarget(target);
|
freetype_tests.setTarget(target);
|
||||||
|
freetype_tests.addPackage(utils_pkg);
|
||||||
link(b, freetype_tests, .{});
|
link(b, freetype_tests, .{});
|
||||||
|
|
||||||
|
const harfbuzz_tests = b.addTestSource(harfbuzz_pkg.source);
|
||||||
|
harfbuzz_tests.setBuildMode(mode);
|
||||||
|
harfbuzz_tests.setTarget(target);
|
||||||
|
harfbuzz_tests.addPackage(utils_pkg);
|
||||||
|
link(b, harfbuzz_tests, .{ .harfbuzz = .{} });
|
||||||
|
|
||||||
const main_tests = b.addTest("test/main.zig");
|
const main_tests = b.addTest("test/main.zig");
|
||||||
main_tests.setBuildMode(mode);
|
main_tests.setBuildMode(mode);
|
||||||
main_tests.setTarget(target);
|
main_tests.setTarget(target);
|
||||||
|
|
@ -44,6 +61,7 @@ pub fn build(b: *std.build.Builder) !void {
|
||||||
|
|
||||||
const test_step = b.step("test", "Run library tests");
|
const test_step = b.step("test", "Run library tests");
|
||||||
test_step.dependOn(&freetype_tests.step);
|
test_step.dependOn(&freetype_tests.step);
|
||||||
|
test_step.dependOn(&harfbuzz_tests.step);
|
||||||
test_step.dependOn(&main_tests.step);
|
test_step.dependOn(&main_tests.step);
|
||||||
|
|
||||||
inline for ([_][]const u8{
|
inline for ([_][]const u8{
|
||||||
|
|
@ -80,6 +98,7 @@ pub fn link(b: *Builder, step: *std.build.LibExeObjStep, options: Options) void
|
||||||
const hb_lib = buildHarfbuzz(b, step, hb_options);
|
const hb_lib = buildHarfbuzz(b, step, hb_options);
|
||||||
hb_lib.linkLibrary(ft_lib);
|
hb_lib.linkLibrary(ft_lib);
|
||||||
step.linkLibrary(hb_lib);
|
step.linkLibrary(hb_lib);
|
||||||
|
step.addIncludePath(hb_include_path);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
const utils = @import("utils");
|
||||||
const c = @import("c.zig");
|
const c = @import("c.zig");
|
||||||
const utils = @import("utils.zig");
|
|
||||||
const intToError = @import("error.zig").intToError;
|
const intToError = @import("error.zig").intToError;
|
||||||
const Error = @import("error.zig").Error;
|
const Error = @import("error.zig").Error;
|
||||||
const GlyphSlot = @import("freetype.zig").GlyphSlot;
|
const GlyphSlot = @import("freetype.zig").GlyphSlot;
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
|
const utils = @import("utils");
|
||||||
const c = @import("c.zig");
|
const c = @import("c.zig");
|
||||||
const utils = @import("utils.zig");
|
|
||||||
const Face = @import("freetype.zig").Face;
|
const Face = @import("freetype.zig").Face;
|
||||||
|
|
||||||
pub const Color = c.FT_Color;
|
pub const Color = c.FT_Color;
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
const utils = @import("utils");
|
||||||
const c = @import("c.zig");
|
const c = @import("c.zig");
|
||||||
const utils = @import("utils.zig");
|
|
||||||
const intToError = @import("error.zig").intToError;
|
const intToError = @import("error.zig").intToError;
|
||||||
const Error = @import("error.zig").Error;
|
const Error = @import("error.zig").Error;
|
||||||
const Generic = @import("types.zig").Generic;
|
const Generic = @import("types.zig").Generic;
|
||||||
|
|
|
||||||
|
|
@ -8,31 +8,17 @@ pub const Glyph = @import("Glyph.zig");
|
||||||
pub const Stroker = @import("Stroker.zig");
|
pub const Stroker = @import("Stroker.zig");
|
||||||
pub const Error = @import("error.zig").Error;
|
pub const Error = @import("error.zig").Error;
|
||||||
|
|
||||||
const std = @import("std");
|
const utils = @import("utils");
|
||||||
|
|
||||||
fn refLiterallyAllDecls(comptime T: type) void {
|
|
||||||
switch (@typeInfo(T)) {
|
|
||||||
.Struct, .Union, .Opaque, .Enum => {
|
|
||||||
inline for (comptime std.meta.declarations(T)) |decl| {
|
|
||||||
if (decl.is_pub) {
|
|
||||||
refLiterallyAllDecls(@TypeOf(@field(T, decl.name)));
|
|
||||||
std.testing.refAllDecls(T);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
else => {},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
test {
|
test {
|
||||||
refLiterallyAllDecls(@This());
|
utils.refAllDecls(@This());
|
||||||
refLiterallyAllDecls(@import("color.zig"));
|
utils.refAllDecls(@import("color.zig"));
|
||||||
refLiterallyAllDecls(@import("error.zig"));
|
utils.refAllDecls(@import("error.zig"));
|
||||||
refLiterallyAllDecls(@import("utils.zig"));
|
utils.refAllDecls(@import("utils"));
|
||||||
refLiterallyAllDecls(@import("Face.zig"));
|
utils.refAllDecls(@import("Face.zig"));
|
||||||
refLiterallyAllDecls(@import("GlyphSlot.zig"));
|
utils.refAllDecls(@import("GlyphSlot.zig"));
|
||||||
refLiterallyAllDecls(@import("Library.zig"));
|
utils.refAllDecls(@import("Library.zig"));
|
||||||
refLiterallyAllDecls(@import("Outline.zig"));
|
utils.refAllDecls(@import("Outline.zig"));
|
||||||
refLiterallyAllDecls(Glyph);
|
utils.refAllDecls(Glyph);
|
||||||
refLiterallyAllDecls(Stroker);
|
utils.refAllDecls(Stroker);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
95
freetype/src/harfbuzz/blob.zig
Normal file
95
freetype/src/harfbuzz/blob.zig
Normal file
|
|
@ -0,0 +1,95 @@
|
||||||
|
const std = @import("std");
|
||||||
|
const c = @import("c.zig");
|
||||||
|
|
||||||
|
pub const MemoryMode = enum(u2) {
|
||||||
|
duplicate = c.HB_MEMORY_MODE_DUPLICATE,
|
||||||
|
readonly = c.HB_MEMORY_MODE_READONLY,
|
||||||
|
writable = c.HB_MEMORY_MODE_WRITABLE,
|
||||||
|
readonly_may_make_writable = c.HB_MEMORY_MODE_READONLY_MAY_MAKE_WRITABLE,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub const Blob = struct {
|
||||||
|
handle: *c.hb_blob_t,
|
||||||
|
|
||||||
|
pub fn init(data: []u8, mode: MemoryMode) ?Blob {
|
||||||
|
return Blob{
|
||||||
|
.handle = c.hb_blob_create_or_fail(data.ptr, @intCast(c_uint, data.len), @enumToInt(mode), null, null) orelse return null,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn initOrEmpty(data: []u8, mode: MemoryMode) Blob {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_blob_create(data.ptr, @intCast(c_uint, data.len), @enumToInt(mode), null, null).?,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn initFromFile(path: [*:0]const u8) ?Blob {
|
||||||
|
return Blob{
|
||||||
|
.handle = c.hb_blob_create_from_file_or_fail(path) orelse return null,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn initFromFileOrEmpty(path: [*:0]const u8) Blob {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_blob_create_from_file(path).?,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getEmpty() Blob {
|
||||||
|
return .{ .handle = c.hb_blob_get_empty().? };
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn createSubBlobOrEmpty(self: Blob, offset: u32, len: u32) Blob {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_blob_create_sub_blob(self.handle, offset, len).?,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn copyWritable(self: Blob) ?Blob {
|
||||||
|
return Blob{
|
||||||
|
.handle = c.hb_blob_copy_writable_or_fail(self.handle) orelse return null,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn deinit(self: Blob) void {
|
||||||
|
c.hb_blob_destroy(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getData(self: Blob, len: ?u32) []const u8 {
|
||||||
|
var l = len;
|
||||||
|
const data = c.hb_blob_get_data(self.handle, if (l) |_| &l.? else null);
|
||||||
|
return if (l) |_|
|
||||||
|
data[0..l.?]
|
||||||
|
else
|
||||||
|
std.mem.sliceTo(data, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getDataWritable(self: Blob, len: ?u32) ?[]const u8 {
|
||||||
|
var l = len;
|
||||||
|
const data = c.hb_blob_get_data(self.handle, if (l) |_| &l.? else null);
|
||||||
|
return if (data == null)
|
||||||
|
null
|
||||||
|
else if (l) |_|
|
||||||
|
data[0..l.?]
|
||||||
|
else
|
||||||
|
std.mem.sliceTo(data, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getLength(self: Blob) u32 {
|
||||||
|
return c.hb_blob_get_length(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn isImmutable(self: Blob) bool {
|
||||||
|
return c.hb_blob_is_immutable(self.handle) > 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn makeImmutable(self: Blob) void {
|
||||||
|
c.hb_blob_make_immutable(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn reference(self: Blob) Blob {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_blob_reference(self.handle).?,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
157
freetype/src/harfbuzz/buffer.zig
Normal file
157
freetype/src/harfbuzz/buffer.zig
Normal file
|
|
@ -0,0 +1,157 @@
|
||||||
|
const std = @import("std");
|
||||||
|
const utils = @import("utils");
|
||||||
|
const c = @import("c.zig");
|
||||||
|
const Direction = @import("common.zig").Direction;
|
||||||
|
const Script = @import("common.zig").Script;
|
||||||
|
const Language = @import("common.zig").Language;
|
||||||
|
|
||||||
|
pub const ContentType = enum(u2) {
|
||||||
|
invalid = c.HB_BUFFER_CONTENT_TYPE_INVALID,
|
||||||
|
unicode = c.HB_BUFFER_CONTENT_TYPE_UNICODE,
|
||||||
|
glyphs = c.HB_BUFFER_CONTENT_TYPE_GLYPHS,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub const Buffer = struct {
|
||||||
|
pub const Flags = packed struct {
|
||||||
|
bot: bool = false,
|
||||||
|
eot: bool = false,
|
||||||
|
preserve_default_ignorables: bool = false,
|
||||||
|
remove_default_ignorables: bool = false,
|
||||||
|
do_not_insert_dotted_circle: bool = false,
|
||||||
|
verify: bool = false,
|
||||||
|
produce_unsafe_to_concat: bool = false,
|
||||||
|
|
||||||
|
pub const Flag = enum(u21) {
|
||||||
|
bot = c.HB_BUFFER_FLAG_BOT,
|
||||||
|
eot = c.HB_BUFFER_FLAG_EOT,
|
||||||
|
preserve_default_ignorables = c.HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES,
|
||||||
|
remove_default_ignorables = c.HB_BUFFER_FLAG_REMOVE_DEFAULT_IGNORABLES,
|
||||||
|
do_not_insert_dotted_circle = c.HB_BUFFER_FLAG_DO_NOT_INSERT_DOTTED_CIRCLE,
|
||||||
|
verify = c.HB_BUFFER_FLAG_VERIFY,
|
||||||
|
produce_unsafe_to_concat = c.HB_BUFFER_FLAG_PRODUCE_UNSAFE_TO_CONCAT,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub fn from(bits: u21) Flags {
|
||||||
|
return utils.bitFieldsToStruct(Flags, Flag, bits);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn cast(flags: Flags) u21 {
|
||||||
|
return utils.structToBitFields(u21, Flag, flags);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
handle: *c.hb_buffer_t,
|
||||||
|
|
||||||
|
pub fn init() ?Buffer {
|
||||||
|
var b = c.hb_buffer_create();
|
||||||
|
if (c.hb_buffer_allocation_successful(b) < 1)
|
||||||
|
return null;
|
||||||
|
return Buffer{ .handle = b.? };
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getEmpty() Buffer {
|
||||||
|
return .{ .handle = c.hb_buffer_get_empty().? };
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn initSimilar(self: Buffer) ?Buffer {
|
||||||
|
var b = c.hb_buffer_create_similar(self.handle);
|
||||||
|
if (c.hb_buffer_allocation_successful(b) < 1)
|
||||||
|
return null;
|
||||||
|
return Buffer{ .handle = b.? };
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn reference(self: Buffer) Buffer {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_buffer_reference(self.handle).?,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn deinit(self: Buffer) void {
|
||||||
|
c.hb_buffer_destroy(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn reset(self: Buffer) void {
|
||||||
|
c.hb_buffer_reset(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn clearContents(self: Buffer) void {
|
||||||
|
c.hb_buffer_clear_contents(self.handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn preAllocate(self: Buffer, size: u32) error{OutOfMemory}!void {
|
||||||
|
if (c.hb_buffer_pre_allocate(self.handle, size) < 1)
|
||||||
|
return error.OutOfMemory;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn allocationSuccessful(self: Buffer) bool {
|
||||||
|
return c.hb_buffer_allocation_successful(self.handle) > 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn add(self: Buffer, codepoint: u32, cluster: usize) void {
|
||||||
|
c.hb_buffer_add(self.handle, codepoint, @intCast(c_uint, cluster));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn addCodepoints(self: Buffer, text: []const u32, item_offset: usize, item_length: usize) void {
|
||||||
|
c.hb_buffer_add_codepoints(self.handle, text.ptr, @intCast(c_int, text.len), @intCast(c_uint, item_offset), @intCast(c_int, item_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn addUTF32(self: Buffer, text: []const u32, item_offset: usize, item_length: usize) void {
|
||||||
|
c.hb_buffer_add_utf32(self.handle, text.ptr, @intCast(c_int, text.len), @intCast(c_uint, item_offset), @intCast(c_int, item_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn addUTF16(self: Buffer, text: []const u16, item_offset: usize, item_length: usize) void {
|
||||||
|
c.hb_buffer_add_utf16(self.handle, text.ptr, @intCast(c_int, text.len), @intCast(c_uint, item_offset), @intCast(c_int, item_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn addUTF8(self: Buffer, text: []const u8, item_offset: usize, item_length: usize) void {
|
||||||
|
c.hb_buffer_add_utf8(self.handle, text.ptr, @intCast(c_int, text.len), @intCast(c_uint, item_offset), @intCast(c_int, item_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn addLatin1(self: Buffer, text: []const u8, item_offset: usize, item_length: usize) void {
|
||||||
|
c.hb_buffer_add_latin1(self.handle, text.ptr, @intCast(c_int, text.len), @intCast(c_uint, item_offset), @intCast(c_int, item_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn append(self: Buffer, source: Buffer, start: usize, end: usize) void {
|
||||||
|
c.hb_buffer_append(self.handle, source.handle, @intCast(c_uint, start), @intCast(c_uint, end));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setContentType(self: Buffer, content_type: ContentType) void {
|
||||||
|
c.hb_buffer_set_content_type(self.handle, @enumToInt(content_type));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getContentType(self: Buffer) ContentType {
|
||||||
|
return @intToEnum(ContentType, c.hb_buffer_get_content_type(self.handle));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setDirection(self: Buffer, direction: Direction) void {
|
||||||
|
c.hb_buffer_set_direction(self.handle, @enumToInt(direction));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getDirection(self: Buffer) Direction {
|
||||||
|
return @intToEnum(Direction, c.hb_buffer_get_direction(self.handle));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setScript(self: Buffer, script: Script) void {
|
||||||
|
c.hb_buffer_set_script(self.handle, @enumToInt(script));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getScript(self: Buffer) Script {
|
||||||
|
return @intToEnum(Script, c.hb_buffer_get_script(self.handle));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setLanguage(self: Buffer, lang: Language) void {
|
||||||
|
c.hb_buffer_set_language(self.handle, @enumToInt(lang));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getLanguage(self: Buffer) Language {
|
||||||
|
return @intToEnum(Language, c.hb_buffer_get_language(self.handle));
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setFlags(self: Buffer, flags: Flags) void {
|
||||||
|
c.hb_buffer_set_flags(self.handle, flags.cast());
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn getFlags(self: Buffer) Flags {
|
||||||
|
return Flags.from(c.hb_buffer_get_flags(self.handle));
|
||||||
|
}
|
||||||
|
};
|
||||||
3
freetype/src/harfbuzz/c.zig
Normal file
3
freetype/src/harfbuzz/c.zig
Normal file
|
|
@ -0,0 +1,3 @@
|
||||||
|
pub usingnamespace @cImport({
|
||||||
|
@cInclude("hb.h");
|
||||||
|
});
|
||||||
191
freetype/src/harfbuzz/common.zig
Normal file
191
freetype/src/harfbuzz/common.zig
Normal file
|
|
@ -0,0 +1,191 @@
|
||||||
|
const std = @import("std");
|
||||||
|
const c = @import("c.zig");
|
||||||
|
|
||||||
|
pub const Direction = enum(u3) {
|
||||||
|
invalid = c.HB_DIRECTION_INVALID,
|
||||||
|
ltr = c.HB_DIRECTION_LTR,
|
||||||
|
rtl = c.HB_DIRECTION_RTL,
|
||||||
|
ttb = c.HB_DIRECTION_TTB,
|
||||||
|
bit = c.HB_DIRECTION_BTT,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub const Script = enum(u31) {
|
||||||
|
common = c.HB_SCRIPT_COMMON,
|
||||||
|
inherited = c.HB_SCRIPT_INHERITED,
|
||||||
|
unknown = c.HB_SCRIPT_UNKNOWN,
|
||||||
|
arabic = c.HB_SCRIPT_ARABIC,
|
||||||
|
armenian = c.HB_SCRIPT_ARMENIAN,
|
||||||
|
bengali = c.HB_SCRIPT_BENGALI,
|
||||||
|
cyrillic = c.HB_SCRIPT_CYRILLIC,
|
||||||
|
devanagari = c.HB_SCRIPT_DEVANAGARI,
|
||||||
|
georgian = c.HB_SCRIPT_GEORGIAN,
|
||||||
|
greek = c.HB_SCRIPT_GREEK,
|
||||||
|
gujarati = c.HB_SCRIPT_GUJARATI,
|
||||||
|
gurmukhi = c.HB_SCRIPT_GURMUKHI,
|
||||||
|
hangul = c.HB_SCRIPT_HANGUL,
|
||||||
|
han = c.HB_SCRIPT_HAN,
|
||||||
|
hebrew = c.HB_SCRIPT_HEBREW,
|
||||||
|
hiragana = c.HB_SCRIPT_HIRAGANA,
|
||||||
|
kannada = c.HB_SCRIPT_KANNADA,
|
||||||
|
katakana = c.HB_SCRIPT_KATAKANA,
|
||||||
|
lao = c.HB_SCRIPT_LAO,
|
||||||
|
latin = c.HB_SCRIPT_LATIN,
|
||||||
|
malayalam = c.HB_SCRIPT_MALAYALAM,
|
||||||
|
oriya = c.HB_SCRIPT_ORIYA,
|
||||||
|
tamil = c.HB_SCRIPT_TAMIL,
|
||||||
|
telugu = c.HB_SCRIPT_TELUGU,
|
||||||
|
thai = c.HB_SCRIPT_THAI,
|
||||||
|
tibetan = c.HB_SCRIPT_TIBETAN,
|
||||||
|
bopomofo = c.HB_SCRIPT_BOPOMOFO,
|
||||||
|
braille = c.HB_SCRIPT_BRAILLE,
|
||||||
|
canadian_syllabics = c.HB_SCRIPT_CANADIAN_SYLLABICS,
|
||||||
|
cherokee = c.HB_SCRIPT_CHEROKEE,
|
||||||
|
ethiopic = c.HB_SCRIPT_ETHIOPIC,
|
||||||
|
khmer = c.HB_SCRIPT_KHMER,
|
||||||
|
mongolian = c.HB_SCRIPT_MONGOLIAN,
|
||||||
|
myanmar = c.HB_SCRIPT_MYANMAR,
|
||||||
|
ogham = c.HB_SCRIPT_OGHAM,
|
||||||
|
runic = c.HB_SCRIPT_RUNIC,
|
||||||
|
sinhala = c.HB_SCRIPT_SINHALA,
|
||||||
|
syriac = c.HB_SCRIPT_SYRIAC,
|
||||||
|
thaana = c.HB_SCRIPT_THAANA,
|
||||||
|
yi = c.HB_SCRIPT_YI,
|
||||||
|
deseret = c.HB_SCRIPT_DESERET,
|
||||||
|
gothic = c.HB_SCRIPT_GOTHIC,
|
||||||
|
old_italic = c.HB_SCRIPT_OLD_ITALIC,
|
||||||
|
buhid = c.HB_SCRIPT_BUHID,
|
||||||
|
hanunoo = c.HB_SCRIPT_HANUNOO,
|
||||||
|
tagalog = c.HB_SCRIPT_TAGALOG,
|
||||||
|
tagbanwa = c.HB_SCRIPT_TAGBANWA,
|
||||||
|
cypriot = c.HB_SCRIPT_CYPRIOT,
|
||||||
|
limbu = c.HB_SCRIPT_LIMBU,
|
||||||
|
linear_b = c.HB_SCRIPT_LINEAR_B,
|
||||||
|
osmanya = c.HB_SCRIPT_OSMANYA,
|
||||||
|
shavian = c.HB_SCRIPT_SHAVIAN,
|
||||||
|
tai_le = c.HB_SCRIPT_TAI_LE,
|
||||||
|
ugaritic = c.HB_SCRIPT_UGARITIC,
|
||||||
|
buginese = c.HB_SCRIPT_BUGINESE,
|
||||||
|
coptic = c.HB_SCRIPT_COPTIC,
|
||||||
|
glagolitic = c.HB_SCRIPT_GLAGOLITIC,
|
||||||
|
kharoshthi = c.HB_SCRIPT_KHAROSHTHI,
|
||||||
|
new_tai_lue = c.HB_SCRIPT_NEW_TAI_LUE,
|
||||||
|
old_persian = c.HB_SCRIPT_OLD_PERSIAN,
|
||||||
|
syloti_nagri = c.HB_SCRIPT_SYLOTI_NAGRI,
|
||||||
|
tifinagh = c.HB_SCRIPT_TIFINAGH,
|
||||||
|
balinese = c.HB_SCRIPT_BALINESE,
|
||||||
|
cuneiform = c.HB_SCRIPT_CUNEIFORM,
|
||||||
|
nko = c.HB_SCRIPT_NKO,
|
||||||
|
phags_pa = c.HB_SCRIPT_PHAGS_PA,
|
||||||
|
phoenician = c.HB_SCRIPT_PHOENICIAN,
|
||||||
|
carian = c.HB_SCRIPT_CARIAN,
|
||||||
|
cham = c.HB_SCRIPT_CHAM,
|
||||||
|
kayah_li = c.HB_SCRIPT_KAYAH_LI,
|
||||||
|
lepcha = c.HB_SCRIPT_LEPCHA,
|
||||||
|
lycian = c.HB_SCRIPT_LYCIAN,
|
||||||
|
lydian = c.HB_SCRIPT_LYDIAN,
|
||||||
|
ol_chiki = c.HB_SCRIPT_OL_CHIKI,
|
||||||
|
rejang = c.HB_SCRIPT_REJANG,
|
||||||
|
saurashtra = c.HB_SCRIPT_SAURASHTRA,
|
||||||
|
sundanese = c.HB_SCRIPT_SUNDANESE,
|
||||||
|
vai = c.HB_SCRIPT_VAI,
|
||||||
|
avestan = c.HB_SCRIPT_AVESTAN,
|
||||||
|
bamum = c.HB_SCRIPT_BAMUM,
|
||||||
|
egyptian_hieroglyphs = c.HB_SCRIPT_EGYPTIAN_HIEROGLYPHS,
|
||||||
|
imperial_aramaic = c.HB_SCRIPT_IMPERIAL_ARAMAIC,
|
||||||
|
inscriptional_pahlavi = c.HB_SCRIPT_INSCRIPTIONAL_PAHLAVI,
|
||||||
|
inscriptional_parthian = c.HB_SCRIPT_INSCRIPTIONAL_PARTHIAN,
|
||||||
|
javanese = c.HB_SCRIPT_JAVANESE,
|
||||||
|
kaithi = c.HB_SCRIPT_KAITHI,
|
||||||
|
lisu = c.HB_SCRIPT_LISU,
|
||||||
|
meetei_mayek = c.HB_SCRIPT_MEETEI_MAYEK,
|
||||||
|
old_south_arabian = c.HB_SCRIPT_OLD_SOUTH_ARABIAN,
|
||||||
|
old_turkic = c.HB_SCRIPT_OLD_TURKIC,
|
||||||
|
samaritan = c.HB_SCRIPT_SAMARITAN,
|
||||||
|
tai_tham = c.HB_SCRIPT_TAI_THAM,
|
||||||
|
tai_viet = c.HB_SCRIPT_TAI_VIET,
|
||||||
|
batak = c.HB_SCRIPT_BATAK,
|
||||||
|
brahmi = c.HB_SCRIPT_BRAHMI,
|
||||||
|
mandaic = c.HB_SCRIPT_MANDAIC,
|
||||||
|
chakma = c.HB_SCRIPT_CHAKMA,
|
||||||
|
meroitic_cursive = c.HB_SCRIPT_MEROITIC_CURSIVE,
|
||||||
|
meroitic_hieroglyphs = c.HB_SCRIPT_MEROITIC_HIEROGLYPHS,
|
||||||
|
miao = c.HB_SCRIPT_MIAO,
|
||||||
|
sharada = c.HB_SCRIPT_SHARADA,
|
||||||
|
sora_sompeng = c.HB_SCRIPT_SORA_SOMPENG,
|
||||||
|
takri = c.HB_SCRIPT_TAKRI,
|
||||||
|
bassa_vah = c.HB_SCRIPT_BASSA_VAH,
|
||||||
|
caucasian_albanian = c.HB_SCRIPT_CAUCASIAN_ALBANIAN,
|
||||||
|
duployan = c.HB_SCRIPT_DUPLOYAN,
|
||||||
|
elbasan = c.HB_SCRIPT_ELBASAN,
|
||||||
|
grantha = c.HB_SCRIPT_GRANTHA,
|
||||||
|
khojki = c.HB_SCRIPT_KHOJKI,
|
||||||
|
khudawadi = c.HB_SCRIPT_KHUDAWADI,
|
||||||
|
linear_a = c.HB_SCRIPT_LINEAR_A,
|
||||||
|
mahajani = c.HB_SCRIPT_MAHAJANI,
|
||||||
|
manichaean = c.HB_SCRIPT_MANICHAEAN,
|
||||||
|
mende_kikakui = c.HB_SCRIPT_MENDE_KIKAKUI,
|
||||||
|
modi = c.HB_SCRIPT_MODI,
|
||||||
|
mro = c.HB_SCRIPT_MRO,
|
||||||
|
nabataean = c.HB_SCRIPT_NABATAEAN,
|
||||||
|
old_north_arabian = c.HB_SCRIPT_OLD_NORTH_ARABIAN,
|
||||||
|
old_permic = c.HB_SCRIPT_OLD_PERMIC,
|
||||||
|
pahawh_hmong = c.HB_SCRIPT_PAHAWH_HMONG,
|
||||||
|
palmyrene = c.HB_SCRIPT_PALMYRENE,
|
||||||
|
pau_cin_hau = c.HB_SCRIPT_PAU_CIN_HAU,
|
||||||
|
psalter_pahlavi = c.HB_SCRIPT_PSALTER_PAHLAVI,
|
||||||
|
siddham = c.HB_SCRIPT_SIDDHAM,
|
||||||
|
tirhuta = c.HB_SCRIPT_TIRHUTA,
|
||||||
|
warang_citi = c.HB_SCRIPT_WARANG_CITI,
|
||||||
|
ahom = c.HB_SCRIPT_AHOM,
|
||||||
|
anatolian_hieroglyphs = c.HB_SCRIPT_ANATOLIAN_HIEROGLYPHS,
|
||||||
|
hatran = c.HB_SCRIPT_HATRAN,
|
||||||
|
multani = c.HB_SCRIPT_MULTANI,
|
||||||
|
old_hungarian = c.HB_SCRIPT_OLD_HUNGARIAN,
|
||||||
|
signwriting = c.HB_SCRIPT_SIGNWRITING,
|
||||||
|
adlam = c.HB_SCRIPT_ADLAM,
|
||||||
|
bhaiksuki = c.HB_SCRIPT_BHAIKSUKI,
|
||||||
|
marchen = c.HB_SCRIPT_MARCHEN,
|
||||||
|
osage = c.HB_SCRIPT_OSAGE,
|
||||||
|
tangut = c.HB_SCRIPT_TANGUT,
|
||||||
|
newa = c.HB_SCRIPT_NEWA,
|
||||||
|
masaram_gondi = c.HB_SCRIPT_MASARAM_GONDI,
|
||||||
|
nushu = c.HB_SCRIPT_NUSHU,
|
||||||
|
soyombo = c.HB_SCRIPT_SOYOMBO,
|
||||||
|
zanabazar_square = c.HB_SCRIPT_ZANABAZAR_SQUARE,
|
||||||
|
dogra = c.HB_SCRIPT_DOGRA,
|
||||||
|
gunjala_gondi = c.HB_SCRIPT_GUNJALA_GONDI,
|
||||||
|
hanifi_rohingya = c.HB_SCRIPT_HANIFI_ROHINGYA,
|
||||||
|
makasar = c.HB_SCRIPT_MAKASAR,
|
||||||
|
medefaidrin = c.HB_SCRIPT_MEDEFAIDRIN,
|
||||||
|
old_sogdian = c.HB_SCRIPT_OLD_SOGDIAN,
|
||||||
|
sogdian = c.HB_SCRIPT_SOGDIAN,
|
||||||
|
elymaic = c.HB_SCRIPT_ELYMAIC,
|
||||||
|
nandinagari = c.HB_SCRIPT_NANDINAGARI,
|
||||||
|
nyiakeng_puachue_hmong = c.HB_SCRIPT_NYIAKENG_PUACHUE_HMONG,
|
||||||
|
wancho = c.HB_SCRIPT_WANCHO,
|
||||||
|
chorasmian = c.HB_SCRIPT_CHORASMIAN,
|
||||||
|
dives_akuru = c.HB_SCRIPT_DIVES_AKURU,
|
||||||
|
khitan_small_script = c.HB_SCRIPT_KHITAN_SMALL_SCRIPT,
|
||||||
|
yezidi = c.HB_SCRIPT_YEZIDI,
|
||||||
|
cypro_minoan = c.HB_SCRIPT_CYPRO_MINOAN,
|
||||||
|
old_uyghur = c.HB_SCRIPT_OLD_UYGHUR,
|
||||||
|
tangsa = c.HB_SCRIPT_TANGSA,
|
||||||
|
toto = c.HB_SCRIPT_TOTO,
|
||||||
|
vithkuqi = c.HB_SCRIPT_VITHKUQI,
|
||||||
|
math = c.HB_SCRIPT_MATH,
|
||||||
|
invalid = c.HB_SCRIPT_INVALID,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub const Language = struct {
|
||||||
|
handle: c.hb_language_t,
|
||||||
|
|
||||||
|
pub fn init(name: []const u8) Language {
|
||||||
|
return .{
|
||||||
|
.handle = c.hb_language_from_string(&name[0], name.len),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn toString(self: Language) [:0]const u8 {
|
||||||
|
return std.mem.span(c.hb_language_to_string(self.handle));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
@ -1 +1,10 @@
|
||||||
//
|
pub usingnamespace @import("blob.zig");
|
||||||
|
pub usingnamespace @import("buffer.zig");
|
||||||
|
pub usingnamespace @import("common.zig");
|
||||||
|
pub const c = @import("c.zig");
|
||||||
|
|
||||||
|
const utils = @import("utils");
|
||||||
|
|
||||||
|
test {
|
||||||
|
utils.refAllDecls(@This());
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,26 +20,16 @@ pub fn bitFieldsToStruct(comptime StructType: type, comptime EnumDataType: type,
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
const TestEnum = enum(u16) {
|
pub fn refAllDecls(comptime T: type) void {
|
||||||
filed_1 = (1 << 1),
|
switch (@typeInfo(T)) {
|
||||||
filed_2 = (1 << 2),
|
.Struct, .Union, .Opaque, .Enum => {
|
||||||
filed_3 = (1 << 3),
|
inline for (comptime std.meta.declarations(T)) |decl| {
|
||||||
};
|
if (decl.is_pub) {
|
||||||
|
refAllDecls(@TypeOf(@field(T, decl.name)));
|
||||||
const TestStruct = packed struct {
|
std.testing.refAllDecls(T);
|
||||||
filed_1: bool = false,
|
}
|
||||||
filed_2: bool = false,
|
}
|
||||||
filed_3: bool = false,
|
},
|
||||||
};
|
else => {},
|
||||||
|
}
|
||||||
test "struct fields to bit fields" {
|
|
||||||
try std.testing.expectEqual(@as(u16, (1 << 1) | (1 << 3)), structToBitFields(u16, TestEnum, TestStruct{
|
|
||||||
.filed_1 = true,
|
|
||||||
.filed_3 = true,
|
|
||||||
}));
|
|
||||||
try std.testing.expectEqual(@as(u16, 0), structToBitFields(u16, TestEnum, TestStruct{}));
|
|
||||||
}
|
|
||||||
|
|
||||||
test "bit fields to struct" {
|
|
||||||
try std.testing.expectEqual(TestStruct{ .filed_1 = true, .filed_2 = true, .filed_3 = false }, bitFieldsToStruct(TestStruct, TestEnum, (1 << 1) | (1 << 2)));
|
|
||||||
}
|
}
|
||||||
Loading…
Add table
Add a link
Reference in a new issue