Mercurial > MadButterfly
comparison src/shape_stext.c @ 397:55f38c2cdb8f
Refactor function of computing text extents
author | Thinker K.F. Li <thinker@branda.to> |
---|---|
date | Thu, 11 Jun 2009 08:20:39 +0800 |
parents | 7fe0b1ee92b6 |
children | aee0f66b1154 |
comparison
equal
deleted
inserted
replaced
396:7fe0b1ee92b6 | 397:55f38c2cdb8f |
---|---|
34 */ | 34 */ |
35 typedef cairo_text_extents_t mb_text_extents_t; | 35 typedef cairo_text_extents_t mb_text_extents_t; |
36 | 36 |
37 #define MBE_GET_X_ADV(ext) ((ext)->x_advance) | 37 #define MBE_GET_X_ADV(ext) ((ext)->x_advance) |
38 #define MBE_GET_Y_ADV(ext) ((ext)->y_advance) | 38 #define MBE_GET_Y_ADV(ext) ((ext)->y_advance) |
39 #define MBE_GET_X_BEARING(ext) ((ext)->x_bearing) | |
40 #define MBE_GET_Y_BEARING(ext) ((ext)->y_bearing) | |
39 #define MBE_GET_WIDTH(ext) ((ext)->width) | 41 #define MBE_GET_WIDTH(ext) ((ext)->width) |
40 #define MBE_GET_HEIGHT(ext) ((ext)->height) | 42 #define MBE_GET_HEIGHT(ext) ((ext)->height) |
41 | 43 |
42 /*! \brief Find out a font pattern. | 44 /*! \brief Find out a font pattern. |
43 * | 45 * |
129 * rotation. This function return a scaled font specified by a | 131 * rotation. This function return a scaled font specified by a |
130 * matrix that transform glyph from design space of the font to | 132 * matrix that transform glyph from design space of the font to |
131 * user space of cairo surface. | 133 * user space of cairo surface. |
132 */ | 134 */ |
133 static | 135 static |
134 mb_scaled_font_t *get_cairo_scaled_font(mb_font_face_t *face, | 136 mb_scaled_font_t *make_scaled_font_face_matrix(mb_font_face_t *face, |
135 co_aix *matrix) { | 137 co_aix *matrix) { |
136 cairo_font_face_t *scaled_font; | 138 cairo_font_face_t *scaled_font; |
137 cairo_matrix_t font_matrix; | 139 cairo_matrix_t font_matrix; |
138 static cairo_matir_t id = { | 140 static cairo_matir_t id = { |
139 1, 0, | 141 1, 0, |
140 0, 1, | 142 0, 1, |
162 | 164 |
163 return (mb_scaled_font_t *)scaled_font; | 165 return (mb_scaled_font_t *)scaled_font; |
164 } | 166 } |
165 | 167 |
166 static | 168 static |
167 void free_scaled_font(mb_scaled_font_t *scaled_font) { | 169 void scaled_font_free(mb_scaled_font_t *scaled_font) { |
168 cairo_scaled_font_destroy((cairo_scaled_font_t *)scaled_font); | 170 cairo_scaled_font_destroy((cairo_scaled_font_t *)scaled_font); |
169 } | 171 } |
170 | 172 |
171 static | 173 static |
172 void text_extents(mb_scaled_font_t *scaled_font, const char *txt, | 174 void compute_text_extents(mb_scaled_font_t *scaled_font, const char *txt, |
173 mb_text_extents_t *extents) { | 175 mb_text_extents_t *extents) { |
174 cairo_scaled_font_text_extents((cairo_scaled_font_t *)scaled_font, | 176 cairo_scaled_font_text_extents((cairo_scaled_font_t *)scaled_font, |
175 txt, | 177 txt, |
176 (cairo_text_extents_t *)extents); | 178 (cairo_text_extents_t *)extents); |
177 } | 179 } |
178 | 180 |
273 | 275 |
274 return p - txt; | 276 return p - txt; |
275 } | 277 } |
276 | 278 |
277 static | 279 static |
278 void compute_text_extents(char *txt, int txt_len, | 280 mb_scaled_font_t *make_scaled_font_face(sh_stext_t *txt_o, |
279 cairo_scaled_font_t *scaled_font, | |
280 cairo_text_extents_t *extents) { | |
281 char saved; | |
282 | |
283 saved = txt[txt_len]; | |
284 txt[txt_len] = 0; | |
285 cairo_scaled_font_text_extents(scaled_font, txt, extents); | |
286 txt[txt_len] = saved; | |
287 } | |
288 | |
289 static | |
290 cairo_scaled_font_t *make_scaled_font_face(sh_stext_t *txt_o, | |
291 cairo_font_face_t *face, | 281 cairo_font_face_t *face, |
292 co_aix shift_x, co_aix shift_y, | 282 co_aix shift_x, co_aix shift_y, |
293 co_aix font_sz) { | 283 co_aix font_sz) { |
294 cairo_matrix_t cmtx; | 284 co_aix matrix[6], scaled_matrix[6]; |
295 static cairo_matrix_t cid; | 285 co_aix *aggr; |
296 static cairo_font_options_t *fopt = NULL; | 286 mb_scaled_font_t *scaled; |
297 co_aix *matrix; | 287 |
298 cairo_scaled_font_t *scaled; | 288 aggr = sh_get_aggr_matrix((shape_t *)txt_o); |
289 matrix[0] = font_sz; | |
290 matrix[1] = 0; | |
291 matrix[2] = shift_x; | |
292 matrix[3] = 0; | |
293 matrix[4] = font_sz; | |
294 matrix[5] += shift_y; | |
295 matrix_mul(aggr, matrix, scaled_matrix); | |
296 | |
297 scaled = make_scaled_font_face_matrix(face, scaled_matrix); | |
298 | |
299 return scaled; | |
300 } | |
301 | |
302 static | |
303 void compute_styled_extents(sh_stext_t *txt_o) { | |
304 mb_text_extents_t sub_extents, full_extents; | |
305 mb_text_extents_t *ext; | |
306 mb_style_blk_t *blk; | |
307 int blk_txt_len; | |
308 mb_scaled_font_t *scaled_font; | |
309 char *txt, saved; | |
310 co_aix shift_x, shift_y; | |
299 int i; | 311 int i; |
300 | 312 |
301 if(fopt == NULL) { | 313 memset(&full_extents, sizeof(mb_text_extents_t), 0); |
302 cairo_matrix_init_identify(&cid); | 314 |
303 fopt = cairo_font_options_create(); | |
304 if(fopt == NULL) | |
305 return NULL; | |
306 } | |
307 | |
308 matrix = sh_get_aggr_matrix((shape_t *)txt_o); | |
309 i = 0; | |
310 cmtx.xx = matrix[i++]; | |
311 cmtx.xy = matrix[i++]; | |
312 cmtx.x0 = matrix[i++] + shift_x; | |
313 cmtx.yx = matrix[i++]; | |
314 cmtx.yy = matrix[i++]; | |
315 cmtx.y0 = matrix[i] + shift_y; | |
316 | |
317 scaled = cairo_scaled_font_create(face, &cmtx, &cid, fopt); | |
318 | |
319 return scaled; | |
320 } | |
321 | |
322 static | |
323 void compute_extents(sh_stext_t *txt_o) { | |
324 co_aix adv_x, adv_y; | |
325 cairo_text_extents_t extents; | |
326 mb_style_blk_t *blk; | |
327 cairo_scaled_font_t *scaled_font; | |
328 char *txt; | |
329 co_aix shift_x, shift_y; | |
330 int blk_txt_len; | |
331 int i; | |
332 | |
333 adv_x = adv_y = 0; | |
334 blk = txt_o->style_blks; | 315 blk = txt_o->style_blks; |
335 scaled_font = txt_o->scaled_fonts; | 316 scaled_font = txt_o->scaled_fonts; |
336 txt = (char *)txt_o->txt; | 317 txt = (char *)txt_o->txt; |
337 shift_x = txt_o->x; | 318 ext = &full_extents; |
338 shift_y = txt_o->y; | |
339 for(i = 0; i < txt_o->nblks; i++) { | 319 for(i = 0; i < txt_o->nblks; i++) { |
340 *scaled_font = make_scaled_fonts(txt_o, blk->face, | 320 shift_x = txt_o->x + full_extents.x_adv; |
341 shift_x, shift_y, font_sz); | 321 shift_y = txt_o->y + full_extents.y_adv; |
322 | |
323 *scaled_font = make_scaled_font_face(txt_o, blk->face, | |
324 shift_x, shift_y, font_sz); | |
342 ASSERT(*scaled_font != NULL); | 325 ASSERT(*scaled_font != NULL); |
343 | 326 |
344 blk_txt_len = compute_utf8_chars_sz(txt, blk->n_chars); | 327 blk_txt_len = compute_utf8_chars_sz(txt, blk->n_chars); |
345 ASSERT(blk_txt_len != ERR); | 328 ASSERT(blk_txt_len != ERR); |
346 | 329 |
347 compute_text_extents(txt, blk_txt_len, *scaled_font, &extents); | 330 saved = txt[blk_txt_len]; |
348 adv_x += extents.x_advance; | 331 txt[blk_txt_len] = 0; |
349 adv_y += extents.y_advance; | 332 compute_text_extents(scaled_font, txt, &extents); |
333 txt[blk_txt_len] = saved; | |
334 | |
335 adv_x += MBE_GET_X_ADV(&extents); | |
336 adv_y += MBE_GET_Y_ADV(&extents); | |
350 | 337 |
351 scaled_font++; | 338 scaled_font++; |
352 blk++; | 339 blk++; |
353 txt += blk_txt_len; | 340 txt += blk_txt_len; |
341 ext = &sub_extents; | |
354 } | 342 } |
355 } | 343 } |
356 | 344 |
357 /* | 345 /* |
358 * What we have to do in sh_stext_transform() is | 346 * What we have to do in sh_stext_transform() is |