1 /*
2  * Copyright (c) 2018-2019 Hanspeter Portner (dev@open-music-kontrollers.ch)
3  *
4  * This is free software: you can redistribute it and/or modify
5  * it under the terms of the Artistic License 2.0 as published by
6  * The Perl Foundation.
7  *
8  * This source is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  * Artistic License 2.0 for more details.
12  *
13  * You should have received a copy of the Artistic License 2.0
14  * along the source as a COPYING file. If not, obtain it from
15  * http://www.perlfoundation.org/artistic_license_2_0.
16  */
17 
18 #ifndef _D2TK_CORE_INTERNAL_H
19 #define _D2TK_CORE_INTERNAL_H
20 
21 #include <d2tk/core.h>
22 
23 #ifdef __cplusplus
24 extern "C" {
25 #endif
26 
27 #define D2TK_PAD_SIZE(size) ( ((size) + 7U) & (~7U) )
28 
29 typedef struct _d2tk_clip_t d2tk_clip_t;
30 typedef struct _d2tk_com_t d2tk_com_t;
31 
32 typedef void *(*d2tk_core_new_t)(const char *bundle_path);
33 typedef void (*d2tk_core_free_t)(void *data);
34 typedef int (*d2tk_core_context_t)(void *data, void *pctx);
35 typedef void (*d2tk_core_pre_t)(void *data, d2tk_core_t *core,
36 	d2tk_coord_t w, d2tk_coord_t h, unsigned pass);
37 typedef bool (*d2tk_core_post_t)(void *data, d2tk_core_t *core,
38 	d2tk_coord_t w, d2tk_coord_t h, unsigned pass);
39 typedef void (*d2tk_core_end_t)(void *data, d2tk_core_t *core,
40 	d2tk_coord_t w, d2tk_coord_t h);
41 typedef void (*d2tk_core_process_t)(void *data, d2tk_core_t *core,
42 	const d2tk_com_t *com, d2tk_coord_t xo, d2tk_coord_t yo,
43 	const d2tk_clip_t *clip, unsigned pass);
44 typedef void (*d2tk_core_sprite_free_t)(void *data, uint8_t type, uintptr_t body);
45 typedef int (*d2tk_core_text_extent_t)(void *data, size_t len, const char *buf,
46 	d2tk_coord_t h);
47 
48 typedef struct _d2tk_body_move_to_t d2tk_body_move_to_t;
49 typedef struct _d2tk_body_line_to_t d2tk_body_line_to_t;
50 typedef struct _d2tk_body_rect_t d2tk_body_rect_t;
51 typedef struct _d2tk_body_scissor_t d2tk_body_scissor_t;
52 typedef struct _d2tk_body_rounded_rect_t d2tk_body_rounded_rect_t;
53 typedef struct _d2tk_body_arc_t d2tk_body_arc_t;
54 typedef struct _d2tk_body_curve_to_t d2tk_body_curve_to_t;
55 typedef struct _d2tk_body_color_t d2tk_body_color_t;
56 typedef struct _d2tk_body_linear_gradient_t d2tk_body_linear_gradient_t;
57 typedef struct _d2tk_body_rotate_t d2tk_body_rotate_t;
58 typedef struct _d2tk_body_font_face_t d2tk_body_font_face_t;
59 typedef struct _d2tk_body_font_size_t d2tk_body_font_size_t;
60 typedef struct _d2tk_body_text_t d2tk_body_text_t;
61 typedef struct _d2tk_body_image_t d2tk_body_image_t;
62 typedef struct _d2tk_body_bitmap_surf_t d2tk_body_bitmap_surf_t;
63 typedef struct _d2tk_body_bitmap_t d2tk_body_bitmap_t;
64 typedef struct _d2tk_body_custom_t d2tk_body_custom_t;
65 typedef struct _d2tk_body_stroke_width_t d2tk_body_stroke_width_t;
66 typedef struct _d2tk_body_bbox_t d2tk_body_bbox_t;
67 typedef union _d2tk_body_t d2tk_body_t;
68 
69 struct _d2tk_clip_t {
70 	d2tk_coord_t x0;
71 	d2tk_coord_t y0;
72 	d2tk_coord_t x1;
73 	d2tk_coord_t y1;
74 	d2tk_coord_t w;
75 	d2tk_coord_t h;
76 };
77 
78 struct _d2tk_core_driver_t {
79 	d2tk_core_new_t new;
80 	d2tk_core_free_t free;
81 	d2tk_core_context_t context;
82 	d2tk_core_pre_t pre;
83 	d2tk_core_process_t process;
84 	d2tk_core_post_t post;
85 	d2tk_core_end_t end;
86 	d2tk_core_sprite_free_t sprite_free;
87 	d2tk_core_text_extent_t text_extent;
88 };
89 
90 struct _d2tk_body_move_to_t {
91 	d2tk_coord_t x;
92 	d2tk_coord_t y;
93 };
94 
95 struct _d2tk_body_line_to_t {
96 	d2tk_coord_t x;
97 	d2tk_coord_t y;
98 };
99 
100 struct _d2tk_body_rect_t {
101 	d2tk_coord_t x;
102 	d2tk_coord_t y;
103 	d2tk_coord_t w;
104 	d2tk_coord_t h;
105 };
106 
107 struct _d2tk_body_scissor_t {
108 	d2tk_coord_t x;
109 	d2tk_coord_t y;
110 	d2tk_coord_t w;
111 	d2tk_coord_t h;
112 };
113 
114 struct _d2tk_body_rounded_rect_t {
115 	d2tk_coord_t x;
116 	d2tk_coord_t y;
117 	d2tk_coord_t w;
118 	d2tk_coord_t h;
119 	d2tk_coord_t r;
120 };
121 
122 struct _d2tk_body_arc_t {
123 	d2tk_coord_t x;
124 	d2tk_coord_t y;
125 	d2tk_coord_t r;
126 	d2tk_coord_t a;
127 	d2tk_coord_t b;
128 	bool cw;
129 };
130 
131 struct _d2tk_body_curve_to_t {
132 	d2tk_coord_t x1;
133 	d2tk_coord_t y1;
134 	d2tk_coord_t x2;
135 	d2tk_coord_t y2;
136 	d2tk_coord_t x3;
137 	d2tk_coord_t y3;
138 };
139 
140 struct _d2tk_body_color_t {
141 	uint32_t rgba;
142 };
143 
144 struct _d2tk_body_linear_gradient_t {
145 	d2tk_point_t p [2];
146 	uint32_t rgba [2];
147 };
148 
149 struct _d2tk_body_rotate_t {
150 	d2tk_coord_t deg;
151 };
152 
153 struct _d2tk_body_font_face_t {
154 	char face [1]; // at least zero-terminator
155 };
156 
157 struct _d2tk_body_font_size_t {
158 	d2tk_coord_t size;
159 };
160 
161 struct _d2tk_body_text_t {
162 	d2tk_coord_t x;
163 	d2tk_coord_t y;
164 	d2tk_coord_t w;
165 	d2tk_coord_t h;
166 	d2tk_align_t align;
167 	char text [1]; // at least zero-terminator
168 };
169 
170 struct _d2tk_body_image_t {
171 	d2tk_coord_t x;
172 	d2tk_coord_t y;
173 	d2tk_coord_t w;
174 	d2tk_coord_t h;
175 	d2tk_align_t align;
176 	char path [1]; // at least zero-terminator
177 };
178 
179 struct _d2tk_body_bitmap_surf_t {
180 	uint32_t w;
181 	uint32_t h;
182 	uint32_t stride;
183 	const uint32_t *argb;
184 	uint64_t rev;
185 };
186 
187 struct _d2tk_body_bitmap_t {
188 	d2tk_coord_t x;
189 	d2tk_coord_t y;
190 	d2tk_coord_t w;
191 	d2tk_coord_t h;
192 	d2tk_align_t align;
193 	d2tk_body_bitmap_surf_t surf;
194 };
195 
196 struct _d2tk_body_custom_t {
197 	d2tk_coord_t x;
198 	d2tk_coord_t y;
199 	d2tk_coord_t w;
200 	d2tk_coord_t h;
201 	uint64_t dhash;
202 	const void *data;
203 	d2tk_core_custom_t custom;
204 };
205 
206 struct _d2tk_body_stroke_width_t {
207 	d2tk_coord_t width;
208 };
209 
210 struct _d2tk_body_bbox_t {
211 	bool dirty;
212 	bool cached;
213 	bool container;
214 	uint32_t hash;
215 	d2tk_clip_t clip;
216 };
217 
218 union _d2tk_body_t {
219 	d2tk_body_move_to_t move_to;
220 	d2tk_body_line_to_t line_to;
221 	d2tk_body_rect_t rect;
222 	d2tk_body_rounded_rect_t rounded_rect;
223 	d2tk_body_arc_t arc;
224 	d2tk_body_curve_to_t curve_to;
225 	d2tk_body_color_t color;
226 	d2tk_body_linear_gradient_t linear_gradient;
227 	d2tk_body_rotate_t rotate;
228 	d2tk_body_scissor_t scissor;
229 	d2tk_body_font_face_t font_face;
230 	d2tk_body_font_size_t font_size;
231 	d2tk_body_text_t text;
232 	d2tk_body_image_t image;
233 	d2tk_body_custom_t custom;
234 	d2tk_body_bitmap_t bitmap;
235 	d2tk_body_stroke_width_t stroke_width;
236 	d2tk_body_bbox_t bbox;
237 };
238 
239 typedef enum _d2tk_instr_t {
240 	D2TK_INSTR_LINE_TO,
241 	D2TK_INSTR_MOVE_TO,
242 	D2TK_INSTR_RECT,
243 	D2TK_INSTR_ROUNDED_RECT,
244 	D2TK_INSTR_ARC,
245 	D2TK_INSTR_CURVE_TO,
246 	D2TK_INSTR_COLOR,
247 	D2TK_INSTR_LINEAR_GRADIENT,
248 	D2TK_INSTR_ROTATE,
249 	D2TK_INSTR_STROKE,
250 	D2TK_INSTR_FILL,
251 	D2TK_INSTR_SAVE,
252 	D2TK_INSTR_RESTORE,
253 	D2TK_INSTR_BBOX,
254 	D2TK_INSTR_BEGIN_PATH,
255 	D2TK_INSTR_CLOSE_PATH,
256 	D2TK_INSTR_SCISSOR,
257 	D2TK_INSTR_RESET_SCISSOR,
258 	D2TK_INSTR_FONT_SIZE,
259 	D2TK_INSTR_FONT_FACE,
260 	D2TK_INSTR_TEXT,
261 	D2TK_INSTR_IMAGE,
262 	D2TK_INSTR_BITMAP,
263 	D2TK_INSTR_CUSTOM,
264 	D2TK_INSTR_STROKE_WIDTH
265 } d2tk_instr_t;
266 
267 struct _d2tk_com_t {
268 	uint32_t size;
269 	uint32_t instr;
270 	d2tk_body_t body [] __attribute__((aligned(8)));
271 };
272 
273 uintptr_t *
274 d2tk_core_get_sprite(d2tk_core_t *core, uint64_t hash, uint8_t type);
275 
276 const d2tk_com_t *
277 d2tk_com_begin_const(const d2tk_com_t *com);
278 
279 const d2tk_com_t *
280 d2tk_com_get_end_const(const d2tk_com_t *com);
281 
282 bool
283 d2tk_com_not_end_const(const d2tk_com_t *end, const d2tk_com_t *bbox);
284 
285 const d2tk_com_t *
286 d2tk_com_next_const(const d2tk_com_t *bbox);
287 
288 #define D2TK_COM_FOREACH_CONST(COM, BBOX) \
289 	for(const d2tk_com_t *(BBOX) = d2tk_com_begin_const((COM)), \
290 			*__end = d2tk_com_get_end_const((COM)); \
291 		d2tk_com_not_end_const(__end, (BBOX)); \
292 		(BBOX) = d2tk_com_next_const((BBOX)))
293 
294 uint32_t *
295 d2tk_core_get_pixels(d2tk_core_t *core, d2tk_rect_t *rect);
296 
297 void
298 d2tk_core_set_bg_color(d2tk_core_t *core, uint32_t rgba);
299 
300 uint32_t
301 d2tk_core_get_bg_color(d2tk_core_t *core);
302 
303 int
304 d2tk_core_get_font_path(d2tk_core_t *core, const char *bundle_path,
305 	const char *rel_path, size_t abs_len, char *abs_path);
306 
307 #ifdef __cplusplus
308 }
309 #endif
310 
311 #endif // _D2TK_CORE_INTERNAL_H
312