const freetype = @import("freetype"); const std = @import("std"); const c = @import("c.zig").c; const Face = @import("face.zig").Face; const Font = @import("font.zig").Font; const Error = @import("errors.zig").Error; // Use custom extern functions so that the proper freetype structs are used // without a ptrcast. These are only needed when interacting with freetype // C structs. extern fn hb_ft_face_create_referenced(ft_face: freetype.c.FT_Face) ?*c.hb_face_t; extern fn hb_ft_font_create_referenced(ft_face: freetype.c.FT_Face) ?*c.hb_font_t; extern fn hb_ft_font_get_face(font: ?*c.hb_font_t) freetype.c.FT_Face; /// Creates an hb_face_t face object from the specified FT_Face. /// /// This is the preferred variant of the hb_ft_face_create* function /// family, because it calls FT_Reference_Face() on ft_face , ensuring /// that ft_face remains alive as long as the resulting hb_face_t face /// object remains alive. Also calls FT_Done_Face() when the hb_face_t /// face object is destroyed. /// /// Use this version unless you know you have good reasons not to. pub fn createFace(face: freetype.c.FT_Face) Error!Face { const handle = hb_ft_face_create_referenced(face) orelse return Error.HarfbuzzFailed; return Face{ .handle = handle }; } /// Creates an hb_font_t font object from the specified FT_Face. pub fn createFont(face: freetype.c.FT_Face) Error!Font { const handle = hb_ft_font_create_referenced(face) orelse return Error.HarfbuzzFailed; return Font{ .handle = handle }; } /// Configures the font-functions structure of the specified hb_font_t font /// object to use FreeType font functions. /// /// In particular, you can use this function to configure an existing /// hb_face_t face object for use with FreeType font functions even if that /// hb_face_t face object was initially created with hb_face_create(), and /// therefore was not initially configured to use FreeType font functions. /// /// An hb_face_t face object created with hb_ft_face_create() is preconfigured /// for FreeType font functions and does not require this function to be used. pub fn setFontFuncs(font: Font) void { c.hb_ft_font_set_funcs(font.handle); } test { if (!@hasDecl(c, "hb_ft_font_create_referenced")) return error.SkipZigTest; const testing = std.testing; const testFont = freetype.testing.font_regular; const ftc = freetype.c; const ftok = ftc.FT_Err_Ok; var ft_lib: ftc.FT_Library = undefined; if (ftc.FT_Init_FreeType(&ft_lib) != ftok) return error.FreeTypeInitFailed; defer _ = ftc.FT_Done_FreeType(ft_lib); var ft_face: ftc.FT_Face = undefined; try testing.expect(ftc.FT_New_Memory_Face( ft_lib, testFont, @intCast(testFont.len), 0, &ft_face, ) == ftok); defer _ = ftc.FT_Done_Face(ft_face); var face = try createFace(ft_face); defer face.destroy(); var font = try createFont(ft_face); defer font.destroy(); setFontFuncs(font); }