xref: /inferno-os/libfreetype/freetype.c (revision 37da2899f40661e3e9631e497da8dc59b971cbd0)
1 #include "freetype/freetype.h"
2 #include "freetype.h"
3 
4 static char* fterrstr(int);
5 
6 char*
ftnewface(char * path,int index,FTface * f,FTfaceinfo * finfo)7 ftnewface(char *path, int index, FTface *f, FTfaceinfo *finfo)
8 {
9 	FT_Library ft_lib;
10 	FT_Face ft_face;
11 	char *err;
12 
13 	err = fterrstr(FT_Init_FreeType(&ft_lib));
14 	if (err != nil)
15 		return err;
16 
17 	err = fterrstr(FT_New_Face(ft_lib, path, index, &ft_face));
18 	if (err != nil) {
19 		FT_Done_FreeType(ft_lib);
20 		return err;
21 	}
22 
23 	f->ft_lib = ft_lib;
24 	f->ft_face = ft_face;
25 	finfo->nfaces = ft_face->num_faces;
26 	finfo->index = ft_face->face_index;
27 	finfo->style = ft_face->style_flags;
28 	finfo->height = (FT_MulFix(ft_face->height, ft_face->size->metrics.y_scale)+32)/64;
29 	finfo->ascent = (FT_MulFix(ft_face->ascender, ft_face->size->metrics.y_scale)+32)/64;
30 	finfo->familyname = ft_face->family_name;
31 	finfo->stylename = ft_face->style_name;
32 	return nil;
33 }
34 
35 char*
ftloadmemface(void * buf,int nbytes,int index,FTface * f,FTfaceinfo * finfo)36 ftloadmemface(void *buf, int nbytes, int index, FTface *f, FTfaceinfo *finfo)
37 {
38 	USED(buf);
39 	USED(f);
40 	USED(finfo);
41 	return "not implemented";
42 }
43 
44 char*
ftsetcharsize(FTface f,int pt,int hdpi,int vdpi,FTfaceinfo * finfo)45 ftsetcharsize(FTface f, int pt, int hdpi, int vdpi, FTfaceinfo *finfo)
46 {
47 	FT_Face ft_face = f.ft_face;
48 	char *err;
49 
50 	err = fterrstr(FT_Set_Char_Size(ft_face, 0, pt, hdpi, vdpi));
51 	if (err != nil)
52 		return err;
53 	finfo->height = (FT_MulFix(ft_face->height, ft_face->size->metrics.y_scale)+32)/64;
54 	finfo->ascent = (FT_MulFix(ft_face->ascender, ft_face->size->metrics.y_scale)+32)/64;
55 	return nil;
56 }
57 
58 void
ftsettransform(FTface f,FTmatrix * m,FTvector * v)59 ftsettransform(FTface f, FTmatrix *m, FTvector *v)
60 {
61 	/* FTMatrix and FTVector are compatible with FT_Matrix and FT_Vector */
62 	FT_Set_Transform(f.ft_face, (FT_Matrix*)m, (FT_Vector*)v);
63 }
64 
65 int
fthaschar(FTface f,int c)66 fthaschar(FTface f, int c)
67 {
68 	return FT_Get_Char_Index(f.ft_face, c) != 0;
69 }
70 
71 char*
ftloadglyph(FTface f,int ix,FTglyph * g)72 ftloadglyph(FTface f, int ix, FTglyph *g)
73 {
74 	FT_Face ft_face = f.ft_face;
75 	FT_GlyphSlot ft_glyph;
76 	char *err;
77 
78 	ix = FT_Get_Char_Index(ft_face, ix);
79 	err = fterrstr(FT_Load_Glyph(ft_face, ix, FT_LOAD_NO_BITMAP|FT_LOAD_RENDER|FT_LOAD_CROP_BITMAP));
80 	if (err != nil)
81 		return err;
82 
83 	ft_glyph = ft_face->glyph;
84 	g->top = ft_glyph->bitmap_top;
85 	g->left = ft_glyph->bitmap_left;
86 	g->height = ft_glyph->bitmap.rows;
87 	g->width = ft_glyph->bitmap.width;
88 	g->advx = ft_glyph->advance.x;
89 	g->advy = ft_glyph->advance.y;
90 	g->bpr = ft_glyph->bitmap.pitch;
91 	g->bitmap = ft_glyph->bitmap.buffer;
92 	return nil;
93 }
94 
95 void
ftdoneface(FTface f)96 ftdoneface(FTface f)
97 {
98 	if (f.ft_face != nil)
99 		FT_Done_Face(f.ft_face);
100 	if (f.ft_lib != nil)
101 		FT_Done_FreeType(f.ft_lib);
102 }
103 
104 /*
105  * get the freetype error strings
106  */
107 
108 typedef struct FTerr FTerr;
109 struct FTerr {
110 	int		code;
111 	char*	text;
112 };
113 
114 #define FT_NOERRORDEF_(l,c,t)
115 #define FT_ERRORDEF_(l,c,t)	c,t,
116 
117 static FTerr fterrs[] = {
118 #include "freetype/fterrdef.h"
119 	-1, "",
120 };
121 
122 static char*
fterrstr(int code)123 fterrstr(int code)
124 {
125 	int i;
126 	if (code == 0)
127 		return nil;
128 	for (i = 0; fterrs[i].code > 0; i++) {
129 		if (fterrs[i].code == code)
130 			return fterrs[i].text;
131 	}
132 	return "unknown FreeType error";
133 }
134 
135