1 /***************************************************************************
2 * Copyright (c) 2024 Microsoft Corporation
3 *
4 * This program and the accompanying materials are made available under the
5 * terms of the MIT License which is available at
6 * https://opensource.org/licenses/MIT.
7 *
8 * SPDX-License-Identifier: MIT
9 **************************************************************************/
10
11
12 /**************************************************************************/
13 /**************************************************************************/
14 /** */
15 /** GUIX Component */
16 /** */
17 /** Utility (Utility) */
18 /** */
19 /**************************************************************************/
20
21 #define GX_SOURCE_CODE
22
23 /* Include necessary system files. */
24
25 #include "gx_api.h"
26 #include "gx_system.h"
27 #include "gx_utility.h"
28 #include "gx_canvas.h"
29
30 #define DRAW_PIXEL if (data & mask) \
31 { \
32 *write_data = 0xff; \
33 } \
34 write_data++; \
35 mask = mask >> 1;
36
37 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
38 #define DRAW_REVERSED_PIXEL if (data & mask) \
39 { \
40 *write_data = 0xff; \
41 } \
42 write_data++; \
43 mask = (GX_UBYTE)(mask << 1);
44 #endif
45
46 /**************************************************************************/
47 /* */
48 /* FUNCTION RELEASE */
49 /* */
50 /* _gx_utility_string_to_alphamap PORTABLE C */
51 /* 6.1.3 */
52 /* AUTHOR */
53 /* */
54 /* Kenneth Maxwell, Microsoft Corporation */
55 /* */
56 /* DESCRIPTION (Deprecated) */
57 /* */
58 /* This function draws text to an 8bpp memory alphamap. */
59 /* */
60 /* INPUT */
61 /* */
62 /* text Pointer to string */
63 /* font Font for text drawing */
64 /* textmap Pointer to pixemap structure */
65 /* */
66 /* OUTPUT */
67 /* */
68 /* status Completion status */
69 /* */
70 /* CALLS */
71 /* */
72 /* _gx_utility_string_length_check Validate string length */
73 /* _gx_utility_string_to_alphamap_ext New version of this function */
74 /* */
75 /* CALLED BY */
76 /* */
77 /* Application Software */
78 /* */
79 /* RELEASE HISTORY */
80 /* */
81 /* DATE NAME DESCRIPTION */
82 /* */
83 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
84 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
85 /* resulting in version 6.1 */
86 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
87 /* display rotation support, */
88 /* resulting in version 6.1.3 */
89 /* */
90 /**************************************************************************/
91 #if defined(GX_ENABLE_DEPRECATED_STRING_API)
_gx_utility_string_to_alphamap(GX_CONST GX_CHAR * text,GX_CONST GX_FONT * font,GX_PIXELMAP * textmap)92 UINT _gx_utility_string_to_alphamap(GX_CONST GX_CHAR *text, GX_CONST GX_FONT *font, GX_PIXELMAP *textmap)
93 {
94 UINT status;
95 UINT length;
96 GX_STRING string;
97
98 string.gx_string_ptr = text;
99 status = _gx_utility_string_length_check(text, &length, GX_MAX_STRING_LENGTH);
100 if (status == GX_SUCCESS)
101 {
102 string.gx_string_length = length;
103 status = _gx_utility_string_to_alphamap_ext(&string, font, textmap);
104 }
105 return status;
106 }
107 #endif
108
109 /**************************************************************************/
110 /* */
111 /* FUNCTION RELEASE */
112 /* */
113 /* _gx_utility_string_to_alphamap_ext PORTABLE C */
114 /* 6.1.3 */
115 /* AUTHOR */
116 /* */
117 /* Kenneth Maxwell, Microsoft Corporation */
118 /* */
119 /* DESCRIPTION (Deprecated) */
120 /* */
121 /* This function draws text to an 8bpp memory alphamap. */
122 /* */
123 /* INPUT */
124 /* */
125 /* text Pointer to string */
126 /* font Font for text drawing */
127 /* textmap Pointer to pixemap structure */
128 /* */
129 /* OUTPUT */
130 /* */
131 /* status Completion status */
132 /* */
133 /* CALLS */
134 /* */
135 /* _gx_system_string_width_get Get width of the string in */
136 /* pixels */
137 /* _gx_canvas_text_draw Draw glyphs on canvas */
138 /* _gx_utility_string_to_alphamap Convert string to alpha-map */
139 /* _gx_utiity_pixelmap_rotate Rotate alphaap to desired */
140 /* angle */
141 /* _gx_canvas_pixelmap_draw Draw text alphamap */
142 /* _gx_system_memory_free Free memory used for rotated */
143 /* alphamap and canvas */
144 /* */
145 /* CALLED BY */
146 /* */
147 /* Application Software */
148 /* */
149 /* RELEASE HISTORY */
150 /* */
151 /* DATE NAME DESCRIPTION */
152 /* */
153 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
154 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
155 /* resulting in version 6.1 */
156 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
157 /* display rotation support, */
158 /* resulting in version 6.1.3 */
159 /* */
160 /**************************************************************************/
_gx_utility_string_to_alphamap_ext(GX_CONST GX_STRING * string,GX_CONST GX_FONT * font,GX_PIXELMAP * textmap)161 UINT _gx_utility_string_to_alphamap_ext(GX_CONST GX_STRING *string, GX_CONST GX_FONT *font, GX_PIXELMAP *textmap)
162 {
163 GX_VALUE alphamap_width;
164 GX_VALUE alphamap_height;
165 UINT status;
166 GX_CONST GX_FONT *font_page = font;
167 GX_CHAR_CODE char_val;
168 GX_CONST GX_GLYPH *glyph;
169 GX_BOOL first_glyph = GX_TRUE;
170 GX_STRING string_copy;
171
172 #ifdef GX_UTF8_SUPPORT
173 UINT glyph_len;
174 #endif
175
176 string_copy = *string;
177 _gx_system_string_width_get_ext(font, &string_copy, &alphamap_width);
178
179 while (string_copy.gx_string_length)
180 {
181 #ifdef GX_UTF8_SUPPORT
182 _gx_utility_utf8_string_character_get(&string_copy, &char_val, &glyph_len);
183 #else
184 char_val = (GX_CHAR_CODE)(*string_copy.gx_string_ptr);
185 string_copy.gx_string_ptr++;
186 string_copy.gx_string_length--;
187 #endif /* GX_UTF8_SUPPORT */
188
189 if (!char_val)
190 {
191 break;
192 }
193
194 if (first_glyph || string_copy.gx_string_ptr[0] == GX_NULL)
195 {
196 while (font_page)
197 {
198 if (font_page -> gx_font_first_glyph <= char_val &&
199 font_page -> gx_font_last_glyph >= char_val)
200 {
201 break;
202 }
203 font_page = font_page -> gx_font_next_page;
204 }
205
206 if (font_page)
207 {
208 glyph = &font_page -> gx_font_glyphs.gx_font_normal_glyphs[char_val - font_page -> gx_font_first_glyph];
209
210 if (first_glyph)
211 {
212 first_glyph = GX_FALSE;
213
214 if (glyph -> gx_glyph_leading < 0)
215 {
216 alphamap_width = (GX_VALUE)(alphamap_width - glyph -> gx_glyph_leading);
217 }
218 }
219 else
220 {
221 /* Last glyph. */
222 alphamap_width = (GX_VALUE)(alphamap_width + glyph -> gx_glyph_leading);
223
224 if (glyph -> gx_glyph_width > glyph -> gx_glyph_advance)
225 {
226 alphamap_width = (GX_VALUE)(alphamap_width + glyph -> gx_glyph_width - glyph -> gx_glyph_advance);
227 }
228 }
229 }
230 }
231 }
232
233 alphamap_height = font -> gx_font_line_height;
234
235 if (alphamap_width && alphamap_height)
236 {
237 /* create an alphamap into which to draw the text */
238 status = _gx_utility_alphamap_create(alphamap_width, alphamap_height, textmap);
239 if (status == GX_SUCCESS)
240 {
241 /* Draw the text into our temporary canvas */
242 _gx_utility_string_to_alphamap_draw(string, font, textmap);
243 }
244 }
245 else
246 {
247 status = GX_FAILURE;
248 }
249
250 return status;
251 }
252
253
254
255 /**************************************************************************/
256 /* */
257 /* FUNCTION RELEASE */
258 /* */
259 /* _gx_utility_glyph_8bpp_to_alphamap_draw PORTABLE C */
260 /* 6.1.3 */
261 /* AUTHOR */
262 /* */
263 /* Kenneth Maxwell, Microsoft Corporation */
264 /* */
265 /* DESCRIPTION */
266 /* */
267 /* Internal helper function that renders 8bpp glyph into alpha-map */
268 /* memory. */
269 /* */
270 /* INPUT */
271 /* */
272 /* map Pixelmap that the glyph is */
273 /* drawn to */
274 /* xpos X-coord where the glyph is */
275 /* drawn to */
276 /* ypos Y-coord where the glyph is */
277 /* darwn to */
278 /* glyph Pointer to glyph structure */
279 /* */
280 /* OUTPUT */
281 /* */
282 /* status Completion status */
283 /* */
284 /* CALLS */
285 /* */
286 /* None */
287 /* */
288 /* CALLED BY */
289 /* */
290 /* GUIX Internal Code */
291 /* */
292 /* RELEASE HISTORY */
293 /* */
294 /* DATE NAME DESCRIPTION */
295 /* */
296 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
297 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
298 /* resulting in version 6.1 */
299 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
300 /* display rotation support, */
301 /* resulting in version 6.1.3 */
302 /* */
303 /**************************************************************************/
_gx_utility_glyph_8bpp_to_alphamap_draw(GX_PIXELMAP * map,INT xpos,INT ypos,GX_CONST GX_GLYPH * glyph)304 VOID _gx_utility_glyph_8bpp_to_alphamap_draw(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph)
305 {
306 GX_UBYTE *read_data;
307 GX_UBYTE *read_row;
308 GX_UBYTE *write_data;
309 GX_UBYTE *write_row;
310 UINT row;
311 UINT col;
312 UINT pixel_width = 0;
313 UINT y_height;
314 USHORT write_stride;
315
316 if (map -> gx_pixelmap_flags & (GX_PIXELMAP_ROTATED_90 | GX_PIXELMAP_ROTATED_270))
317 {
318 write_stride = (USHORT)map -> gx_pixelmap_height;
319 pixel_width = glyph -> gx_glyph_height;
320 y_height = glyph -> gx_glyph_width;
321 GX_SWAP_VALS(xpos, ypos)
322
323 if (map -> gx_pixelmap_flags & GX_PIXELMAP_ROTATED_90)
324 {
325 ypos = (map -> gx_pixelmap_width - ypos - glyph -> gx_glyph_width);
326 }
327 else
328 {
329 xpos = (map -> gx_pixelmap_height - xpos - glyph -> gx_glyph_height);
330 }
331 }
332 else
333 {
334 write_stride = (USHORT)map -> gx_pixelmap_width;
335 pixel_width = glyph -> gx_glyph_width;
336 y_height = glyph -> gx_glyph_height;
337 }
338
339 read_row = (GX_UBYTE *)glyph -> gx_glyph_map;
340
341 write_row = (GX_UBYTE *)map -> gx_pixelmap_data;
342 write_row += ypos * write_stride;
343 write_row += xpos;
344
345 for (row = 0; row < y_height; row++)
346 {
347 read_data = read_row;
348 write_data = write_row;
349
350 for (col = 0; col < pixel_width; col++)
351 {
352 *write_data++ = *read_data++;
353 }
354 read_row += pixel_width;
355 write_row += write_stride;
356 }
357 }
358
359 /**************************************************************************/
360 /* */
361 /* FUNCTION RELEASE */
362 /* */
363 /* _gx_utility_glyph_4bpp_to_alphamap_draw PORTABLE C */
364 /* 6.1.3 */
365 /* AUTHOR */
366 /* */
367 /* Kenneth Maxwell, Microsoft Corporation */
368 /* */
369 /* DESCRIPTION */
370 /* */
371 /* Internal helper function that renders 4bpp glyph into alpha-map */
372 /* memory. */
373 /* */
374 /* INPUT */
375 /* */
376 /* map Pixelmap that the glyph is */
377 /* drawn to */
378 /* xpos X-coord where the glyph is */
379 /* drawn to */
380 /* ypos Y-coord where the glyph is */
381 /* darwn to */
382 /* glyph Pointer to glyph structure */
383 /* */
384 /* OUTPUT */
385 /* */
386 /* status Completion status */
387 /* */
388 /* CALLS */
389 /* */
390 /* None */
391 /* */
392 /* CALLED BY */
393 /* */
394 /* GUIX Internal Code */
395 /* */
396 /* RELEASE HISTORY */
397 /* */
398 /* DATE NAME DESCRIPTION */
399 /* */
400 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
401 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
402 /* resulting in version 6.1 */
403 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
404 /* display rotation support, */
405 /* resulting in version 6.1.3 */
406 /* */
407 /**************************************************************************/
_gx_utility_glyph_4bpp_to_alphamap_draw(GX_PIXELMAP * map,INT xpos,INT ypos,GX_CONST GX_GLYPH * glyph)408 VOID _gx_utility_glyph_4bpp_to_alphamap_draw(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph)
409 {
410 GX_UBYTE *read_data;
411 GX_UBYTE *read_row;
412 GX_UBYTE *write_data;
413 GX_UBYTE *write_row;
414 UINT row;
415 UINT col;
416 UINT pixel_width = 0;
417 UINT read_stride;
418 USHORT write_stride;
419 UINT y_height;
420 GX_UBYTE data;
421
422 if (map -> gx_pixelmap_flags & (GX_PIXELMAP_ROTATED_90 | GX_PIXELMAP_ROTATED_270))
423 {
424 write_stride = (USHORT)map -> gx_pixelmap_height;
425 pixel_width = glyph -> gx_glyph_height;
426 y_height = glyph -> gx_glyph_width;
427
428 GX_SWAP_VALS(xpos, ypos)
429
430 if (map -> gx_pixelmap_flags & GX_PIXELMAP_ROTATED_90)
431 {
432 ypos = (INT)map -> gx_pixelmap_width - (INT)ypos - (INT)y_height;
433 }
434 else
435 {
436 xpos = (INT)map -> gx_pixelmap_height - (INT)xpos - (INT)pixel_width;
437 }
438 }
439 else
440 {
441 pixel_width = (USHORT)glyph -> gx_glyph_width;
442 y_height = glyph -> gx_glyph_height;
443 write_stride = (USHORT)map -> gx_pixelmap_width;
444 }
445
446 read_row = (GX_UBYTE *)glyph -> gx_glyph_map;
447 write_row = (GX_UBYTE *)map -> gx_pixelmap_data;
448 write_row += ypos * write_stride;
449 write_row += xpos;
450
451 read_stride = (pixel_width + 1) / 2;
452
453 for (row = 0; row < y_height; row++)
454 {
455 read_data = read_row;
456 write_data = write_row;
457
458 for (col = 0; col < pixel_width; col++)
459 {
460 data = *read_data++;
461
462 *write_data++ = (GX_UBYTE)((data & 0xf0) | (data >> 4));
463 col++;
464
465 if (col < pixel_width)
466 {
467 *write_data++ = (GX_UBYTE)((data << 4) | (data & 0x0f));
468 }
469 }
470 read_row += read_stride;
471 write_row += write_stride;
472 }
473 }
474
475 /**************************************************************************/
476 /* */
477 /* FUNCTION RELEASE */
478 /* */
479 /* _gx_utility_glyph_reversed_4bpp_to_alphamap_draw PORTABLE C */
480 /* 6.1.3 */
481 /* AUTHOR */
482 /* */
483 /* Kenneth Maxwell, Microsoft Corporation */
484 /* */
485 /* DESCRIPTION */
486 /* */
487 /* Internal helper function that renders 4bpp reversed bit order glyph */
488 /* into alpha-map memory. */
489 /* */
490 /* INPUT */
491 /* */
492 /* map Pixelmap that the glyph is */
493 /* drawn to */
494 /* xpos X-coord where the glyph is */
495 /* drawn to */
496 /* ypos Y-coord where the glyph is */
497 /* darwn to */
498 /* glyph Pointer to glyph structure */
499 /* */
500 /* OUTPUT */
501 /* */
502 /* status Completion status */
503 /* */
504 /* CALLS */
505 /* */
506 /* None */
507 /* */
508 /* CALLED BY */
509 /* */
510 /* GUIX Internal Code */
511 /* */
512 /* RELEASE HISTORY */
513 /* */
514 /* DATE NAME DESCRIPTION */
515 /* */
516 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
517 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
518 /* resulting in version 6.1 */
519 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
520 /* display rotation support, */
521 /* resulting in version 6.1.3 */
522 /* 06-02-2021 Kenneth Maxwell Modified comment(s), added */
523 /* rename RENESAS_DAVE2D */
524 /* support conditional, */
525 /* resulting in version 6.1.7 */
526 /* */
527 /**************************************************************************/
528 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
_gx_utility_glyph_reversed_4bpp_to_alphamap_draw(GX_PIXELMAP * map,INT xpos,INT ypos,GX_CONST GX_GLYPH * glyph)529 VOID _gx_utility_glyph_reversed_4bpp_to_alphamap_draw(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph)
530 {
531 GX_UBYTE *read_data;
532 GX_UBYTE *read_row;
533 GX_UBYTE *write_data;
534 GX_UBYTE *write_row;
535 UINT row;
536 UINT col;
537 UINT pixel_width = 0;
538 UINT byte_width;
539 UINT y_height;
540 USHORT write_stride;
541 GX_UBYTE data;
542
543
544 if (map -> gx_pixelmap_flags & (GX_PIXELMAP_ROTATED_90 | GX_PIXELMAP_ROTATED_270))
545 {
546 write_stride = (USHORT)map -> gx_pixelmap_height;
547 pixel_width = glyph -> gx_glyph_height;
548 y_height = glyph -> gx_glyph_width;
549
550 GX_SWAP_VALS(xpos, ypos)
551
552 if (map -> gx_pixelmap_flags & GX_PIXELMAP_ROTATED_90)
553 {
554 ypos = (INT)map -> gx_pixelmap_width - (INT)ypos - (INT)y_height;
555 }
556 else
557 {
558 xpos = (INT)map -> gx_pixelmap_height - (INT)xpos - (INT)pixel_width;
559 }
560 }
561 else
562 {
563 pixel_width = glyph -> gx_glyph_width;
564 y_height = glyph -> gx_glyph_height;
565 write_stride = (USHORT)map -> gx_pixelmap_width;
566 }
567
568 read_row = (GX_UBYTE *)glyph -> gx_glyph_map;
569 write_row = (GX_UBYTE *)map -> gx_pixelmap_data;
570 write_row += ypos * write_stride;
571 write_row += xpos;
572
573 byte_width = (pixel_width + 1) / 2;
574
575
576 for (row = 0; row < y_height; row++)
577 {
578 read_data = read_row;
579 write_data = write_row;
580
581 for (col = 0; col < pixel_width; col++)
582 {
583 data = *read_data++;
584
585 *write_data++ = (GX_UBYTE)((data << 4) | (data & 0x0f));
586 col++;
587
588 if (col < pixel_width)
589 {
590 *write_data++ = (GX_UBYTE)((data & 0xf0) | (data >> 4));
591 }
592 }
593 read_row += byte_width;
594 write_row += write_stride;
595 }
596 }
597 #endif
598
599 /**************************************************************************/
600 /* */
601 /* FUNCTION RELEASE */
602 /* */
603 /* _gx_utility_glyph_1bpp_to_alphamap_draw PORTABLE C */
604 /* 6.1.3 */
605 /* AUTHOR */
606 /* */
607 /* Kenneth Maxwell, Microsoft Corporation */
608 /* */
609 /* DESCRIPTION */
610 /* */
611 /* Internal helper function that renders 1bpp glyph into alpha-map */
612 /* memory. */
613 /* */
614 /* INPUT */
615 /* */
616 /* map Pixelmap that the glyph is */
617 /* drawn to */
618 /* xpos X-coord where the glyph is */
619 /* drawn to */
620 /* ypos Y-coord where the glyph is */
621 /* darwn to */
622 /* glyph Pointer to glyph structure */
623 /* */
624 /* OUTPUT */
625 /* */
626 /* status Completion status */
627 /* */
628 /* CALLS */
629 /* */
630 /* None */
631 /* */
632 /* CALLED BY */
633 /* */
634 /* GUIX Internal Code */
635 /* */
636 /* RELEASE HISTORY */
637 /* */
638 /* DATE NAME DESCRIPTION */
639 /* */
640 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
641 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
642 /* resulting in version 6.1 */
643 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
644 /* display rotation support, */
645 /* resulting in version 6.1.3 */
646 /* */
647 /**************************************************************************/
_gx_utility_glyph_1bpp_to_alphamap_draw(GX_PIXELMAP * map,INT xpos,INT ypos,GX_CONST GX_GLYPH * glyph)648 VOID _gx_utility_glyph_1bpp_to_alphamap_draw(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph)
649 {
650 GX_UBYTE *read_data;
651 GX_UBYTE *read_row;
652 GX_UBYTE *write_data;
653 GX_UBYTE *write_row;
654 UINT row;
655 UINT col;
656 UINT y_height;
657 GX_UBYTE glyph_width;
658 GX_UBYTE data;
659 UINT pixel_in_first_byte = 8;
660 UINT pixel_in_last_byte;
661 UINT num_bits;
662 UINT num_bytes;
663 USHORT write_stride;
664 GX_UBYTE mask;
665
666 if (map -> gx_pixelmap_flags & (GX_PIXELMAP_ROTATED_90 | GX_PIXELMAP_ROTATED_270))
667 {
668 write_stride = (USHORT)map -> gx_pixelmap_height;
669 y_height = glyph -> gx_glyph_width;
670 glyph_width = (USHORT)glyph -> gx_glyph_height;
671 GX_SWAP_VALS(xpos, ypos)
672
673 if (map -> gx_pixelmap_flags & GX_PIXELMAP_ROTATED_90)
674 {
675 ypos = (map -> gx_pixelmap_width - ypos - glyph -> gx_glyph_width);
676 }
677 else
678 {
679 xpos = (map -> gx_pixelmap_height - xpos - glyph -> gx_glyph_height);
680 }
681 }
682 else
683 {
684 write_stride = (USHORT)map -> gx_pixelmap_width;
685 y_height = glyph -> gx_glyph_height;
686 glyph_width = glyph -> gx_glyph_width;
687 }
688
689 pixel_in_last_byte = ((UINT)glyph_width) & 0x7;
690 if (pixel_in_last_byte == 0)
691 {
692 pixel_in_last_byte = 8;
693 }
694
695 num_bytes = (((UINT)glyph_width) + 7) >> 3;
696
697 if (num_bytes == 1)
698 {
699 pixel_in_first_byte = pixel_in_last_byte;
700 }
701
702 read_row = (GX_UBYTE *)glyph -> gx_glyph_map;
703
704 write_row = (GX_UBYTE *)map -> gx_pixelmap_data;
705 write_row += ypos * write_stride;
706 write_row += xpos;
707
708 for (row = 0; row < y_height; row++)
709 {
710 read_data = read_row;
711 write_data = write_row;
712 num_bits = pixel_in_first_byte;
713
714 for (col = 0; col < num_bytes; col++)
715 {
716 data = *read_data++;
717 mask = 0x80;
718
719 if ((col == (num_bytes - 1)) && (num_bytes > 1))
720 {
721 num_bits = pixel_in_last_byte;
722 }
723
724 switch (num_bits)
725 {
726 case 8:
727 DRAW_PIXEL;
728 /* fallthrough */
729 case 7:
730 DRAW_PIXEL;
731 /* fallthrough */
732 case 6:
733 DRAW_PIXEL;
734 /* fallthrough */
735 case 5:
736 DRAW_PIXEL;
737 /* fallthrough */
738 case 4:
739 DRAW_PIXEL;
740 /* fallthrough */
741 case 3:
742 DRAW_PIXEL;
743 /* fallthrough */
744 case 2:
745 DRAW_PIXEL;
746 /* fallthrough */
747 default:
748 if (data & mask)
749 {
750 *write_data = 0xff;
751 }
752 write_data++;
753 break;
754 }
755 }
756
757 read_row += num_bytes;
758 write_row += write_stride;
759 }
760 }
761
762 /**************************************************************************/
763 /* */
764 /* FUNCTION RELEASE */
765 /* */
766 /* _gx_utility_glyph_reversed_1bpp_to_alphamap_draw PORTABLE C */
767 /* 6.1.3 */
768 /* AUTHOR */
769 /* */
770 /* Kenneth Maxwell, Microsoft Corporation */
771 /* */
772 /* DESCRIPTION */
773 /* */
774 /* Internal helper function that renders 1bpp reveresed bit order */
775 /* glyph into alpha-map memory. */
776 /* */
777 /* INPUT */
778 /* */
779 /* map Pixelmap that the glyph is */
780 /* drawn to */
781 /* xpos X-coord where the glyph is */
782 /* drawn to */
783 /* ypos Y-coord where the glyph is */
784 /* darwn to */
785 /* glyph Pointer to glyph structure */
786 /* */
787 /* OUTPUT */
788 /* */
789 /* status Completion status */
790 /* */
791 /* CALLS */
792 /* */
793 /* None */
794 /* */
795 /* CALLED BY */
796 /* */
797 /* GUIX Internal Code */
798 /* */
799 /* RELEASE HISTORY */
800 /* */
801 /* DATE NAME DESCRIPTION */
802 /* */
803 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
804 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
805 /* resulting in version 6.1 */
806 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
807 /* display rotation support, */
808 /* resulting in version 6.1.3 */
809 /* 06-02-2021 Kenneth Maxwell Modified comment(s), */
810 /* rename RENESAS_DAVE2D */
811 /* support conditional, */
812 /* resulting in version 6.1.7 */
813 /* */
814 /**************************************************************************/
815 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
_gx_utility_glyph_reversed_1bpp_to_alphamap_draw(GX_PIXELMAP * map,INT xpos,INT ypos,GX_CONST GX_GLYPH * glyph)816 VOID _gx_utility_glyph_reversed_1bpp_to_alphamap_draw(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph)
817 {
818 GX_UBYTE *read_data;
819 GX_UBYTE *read_row;
820 GX_UBYTE *write_data;
821 GX_UBYTE *write_row;
822 UINT row;
823 UINT col;
824 UINT y_height;
825 GX_UBYTE glyph_width;
826 GX_UBYTE data;
827 UINT pixel_in_first_byte = 8;
828 UINT pixel_in_last_byte;
829 UINT num_bits;
830 UINT num_bytes;
831 USHORT write_stride;
832 GX_UBYTE mask;
833
834 if (map -> gx_pixelmap_flags & (GX_PIXELMAP_ROTATED_90 | GX_PIXELMAP_ROTATED_270))
835 {
836 write_stride = (USHORT)map -> gx_pixelmap_height;
837 y_height = glyph -> gx_glyph_width;
838 glyph_width = glyph -> gx_glyph_height;
839 GX_SWAP_VALS(xpos, ypos)
840
841 if (map -> gx_pixelmap_flags & GX_PIXELMAP_ROTATED_90)
842 {
843 ypos = (map -> gx_pixelmap_width - ypos - glyph -> gx_glyph_width);
844 }
845 else
846 {
847 xpos = (map -> gx_pixelmap_height - xpos - glyph -> gx_glyph_height);
848 }
849 }
850 else
851 {
852 write_stride = (USHORT)map -> gx_pixelmap_width;
853 y_height = glyph -> gx_glyph_height;
854 glyph_width = glyph -> gx_glyph_width;
855 }
856
857 pixel_in_last_byte = ((UINT)glyph_width) & 0x7;
858 if (pixel_in_last_byte == 0)
859 {
860 pixel_in_last_byte = 8;
861 }
862
863 num_bytes = (((UINT)glyph_width) + 7) >> 3;
864
865 if (num_bytes == 1)
866 {
867 pixel_in_first_byte = pixel_in_last_byte;
868 }
869
870 read_row = (GX_UBYTE *)glyph -> gx_glyph_map;
871
872 write_row = (GX_UBYTE *)map -> gx_pixelmap_data;
873 write_row += ypos * write_stride;
874 write_row += xpos;
875
876 for (row = 0; row < y_height; row++)
877 {
878 read_data = read_row;
879 write_data = write_row;
880 num_bits = pixel_in_first_byte;
881
882 for (col = 0; col < num_bytes; col++)
883 {
884 data = *read_data++;
885 mask = 0x01;
886
887 if ((col == (num_bytes - 1)) && (num_bytes > 1))
888 {
889 num_bits = pixel_in_last_byte;
890 }
891
892 switch (num_bits)
893 {
894 case 8:
895 DRAW_REVERSED_PIXEL;
896 /* fallthrough */
897 case 7:
898 DRAW_REVERSED_PIXEL;
899 /* fallthrough */
900 case 6:
901 DRAW_REVERSED_PIXEL;
902 /* fallthrough */
903 case 5:
904 DRAW_REVERSED_PIXEL;
905 /* fallthrough */
906 case 4:
907 DRAW_REVERSED_PIXEL;
908 /* fallthrough */
909 case 3:
910 DRAW_REVERSED_PIXEL;
911 /* fallthrough */
912 case 2:
913 DRAW_REVERSED_PIXEL;
914 /* fallthrough */
915 default:
916 if (data & mask)
917 {
918 *write_data = 0xff;
919 }
920 write_data++;
921 break;
922 }
923 }
924
925 read_row += num_bytes;
926 write_row += write_stride;
927 }
928 }
929 #endif
930
931 /**************************************************************************/
932 /* */
933 /* FUNCTION RELEASE */
934 /* */
935 /* _gx_utility_string_to_alphamap_draw PORTABLE C */
936 /* 6.1.3 */
937 /* AUTHOR */
938 /* */
939 /* Kenneth Maxwell, Microsoft Corporation */
940 /* */
941 /* DESCRIPTION */
942 /* */
943 /* Internal helper function that renders entire string to alpha-map */
944 /* memory. */
945 /* */
946 /* INPUT */
947 /* */
948 /* text Pointer to string */
949 /* font Font for text drawing */
950 /* map Pointer to pixemap structure */
951 /* */
952 /* OUTPUT */
953 /* */
954 /* status Completion status */
955 /* */
956 /* CALLS */
957 /* */
958 /* _gx_utility_glyph_8bpp_to_alphamap_draw */
959 /* Render 8bpp glyph to alphamap */
960 /* _gx_utility_glyph_4bpp_to_alphamap_draw */
961 /* Render 4bpp glyph to alphamap */
962 /* _gx_utility_glyph_1bpp_to_alphamap_draw */
963 /* Render 1bpp glyph to alphamap */
964 /* _gx_utility_utf8_string_character_get Parse utf8 string to */
965 /* to multibyte glyph */
966 /* _gx_utility_string_length_check Test string length */
967 /* */
968 /* CALLED BY */
969 /* */
970 /* GUIX Internal Code */
971 /* */
972 /* RELEASE HISTORY */
973 /* */
974 /* DATE NAME DESCRIPTION */
975 /* */
976 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
977 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
978 /* resulting in version 6.1 */
979 /* 12-31-2020 Kenneth Maxwell Modified comment(s), added */
980 /* display rotation support, */
981 /* resulting in version 6.1.3 */
982 /* 06-02-2021 Kenneth Maxwell Modified comment(s), */
983 /* rename RENESAS_DAVE2D */
984 /* support conditional, */
985 /* resulting in version 6.1.7 */
986 /* */
987 /**************************************************************************/
_gx_utility_string_to_alphamap_draw(GX_CONST GX_STRING * string,GX_CONST GX_FONT * font,GX_PIXELMAP * map)988 VOID _gx_utility_string_to_alphamap_draw(GX_CONST GX_STRING *string, GX_CONST GX_FONT *font, GX_PIXELMAP *map)
989 {
990 INT xpos;
991 int y_offset;
992 GX_CONST GX_GLYPH *glyph;
993 GX_CONST GX_FONT *font_page;
994 GX_CHAR_CODE glyph_index;
995 GX_CHAR_CODE char_val;
996 GX_BOOL first_char = GX_TRUE;
997 INT leading;
998 GX_STRING string_copy;
999 VOID (*glyph_draw)(GX_PIXELMAP *map, INT xpos, INT ypos, GX_CONST GX_GLYPH *glyph);
1000
1001 #ifdef GX_UTF8_SUPPORT
1002 UINT glyph_len;
1003 #endif /* GX_UTF8_SUPPORT */
1004
1005 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
1006 if (font -> gx_font_format & GX_FONT_FORMAT_COMPRESSED)
1007 {
1008 /* Not supported. */
1009 return;
1010 }
1011 #endif
1012
1013 xpos = 0;
1014 string_copy = *string;
1015
1016 if (font -> gx_font_format & GX_FONT_FORMAT_ROTATED_90)
1017 {
1018 map -> gx_pixelmap_flags |= GX_PIXELMAP_ROTATED_90;
1019 }
1020 else if (font -> gx_font_format & GX_FONT_FORMAT_ROTATED_270)
1021 {
1022 map -> gx_pixelmap_flags |= GX_PIXELMAP_ROTATED_270;
1023 }
1024
1025 switch (font -> gx_font_format & GX_FONT_FORMAT_BPP_MASK)
1026 {
1027 case GX_FONT_FORMAT_8BPP:
1028 glyph_draw = _gx_utility_glyph_8bpp_to_alphamap_draw;
1029 break;
1030
1031 case GX_FONT_FORMAT_4BPP:
1032 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
1033 if (font -> gx_font_format & GX_FONT_FORMAT_REVERSED_ORDER)
1034 {
1035 glyph_draw = _gx_utility_glyph_reversed_4bpp_to_alphamap_draw;
1036 }
1037 else
1038 {
1039 #endif
1040 glyph_draw = _gx_utility_glyph_4bpp_to_alphamap_draw;
1041 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
1042 }
1043 #endif
1044 break;
1045
1046 case GX_FONT_FORMAT_1BPP:
1047 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
1048 if (font -> gx_font_format & GX_FONT_FORMAT_REVERSED_ORDER)
1049 {
1050 glyph_draw = _gx_utility_glyph_reversed_1bpp_to_alphamap_draw;
1051 }
1052 else
1053 {
1054 #endif
1055 glyph_draw = _gx_utility_glyph_1bpp_to_alphamap_draw;
1056 #if defined(GX_RENESAS_DAVE2D_FONT_SUPPORT)
1057 }
1058 #endif
1059 break;
1060
1061 default:
1062 glyph_draw = GX_NULL;
1063 break;
1064 }
1065
1066 if (glyph_draw == GX_NULL)
1067 {
1068 return;
1069 }
1070
1071 while (string_copy.gx_string_length)
1072 {
1073 #ifdef GX_UTF8_SUPPORT
1074 _gx_utility_utf8_string_character_get(&string_copy, &char_val, &glyph_len);
1075 #else
1076 char_val = (GX_CHAR_CODE)(*string_copy.gx_string_ptr);
1077 string_copy.gx_string_ptr++;
1078 string_copy.gx_string_length--;
1079 #endif /* GX_UTF8_SUPPORT */
1080
1081 if (!char_val)
1082 {
1083 break;
1084 }
1085
1086 font_page = font;
1087
1088 while (font_page)
1089 {
1090 if (font_page -> gx_font_first_glyph <= char_val &&
1091 font_page -> gx_font_last_glyph >= char_val)
1092 {
1093 break;
1094 }
1095 font_page = font_page -> gx_font_next_page;
1096 }
1097 if (font_page)
1098 {
1099 glyph_index = (GX_CHAR_CODE)(char_val - font_page -> gx_font_first_glyph);
1100 glyph = &font_page -> gx_font_glyphs.gx_font_normal_glyphs[glyph_index];
1101 y_offset = font_page -> gx_font_baseline - glyph -> gx_glyph_ascent;
1102
1103 leading = glyph -> gx_glyph_leading;
1104 if (first_char)
1105 {
1106 first_char = GX_FALSE;
1107
1108 leading = 0;
1109 }
1110 glyph_draw(map, xpos + leading, y_offset, glyph);
1111 xpos += glyph -> gx_glyph_advance;
1112 }
1113 }
1114 }
1115
1116