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 /**   Display Management (Display)                                        */
18 /**                                                                       */
19 /**************************************************************************/
20 
21 #define GX_SOURCE_CODE
22 
23 
24 /* Include necessary system files.  */
25 
26 #include "gx_api.h"
27 #include "gx_display.h"
28 #include "gx_context.h"
29 
30 #if defined(GX_BRUSH_ALPHA_SUPPORT)
31 /**************************************************************************/
32 /*                                                                        */
33 /*  FUNCTION                                               RELEASE        */
34 /*                                                                        */
35 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_blend       */
36 /*                                                        PORTABLE C      */
37 /*                                                           6.1          */
38 /*  AUTHOR                                                                */
39 /*                                                                        */
40 /*    Kenneth Maxwell, Microsoft Corporation                              */
41 /*                                                                        */
42 /*  DESCRIPTION                                                           */
43 /*                                                                        */
44 /*    Internal helper function that handles blending of uncompressed      */
45 /*    pixelmap file with alpha channel by lines.                          */
46 /*                                                                        */
47 /*  INPUT                                                                 */
48 /*                                                                        */
49 /*    context                               Drawing context               */
50 /*    xstart                                x-coord of line left          */
51 /*    xend                                  x-coord of line right         */
52 /*    y                                     y-coord of line top           */
53 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
54 /*    alpha                                 Alpha value                   */
55 /*                                                                        */
56 /*  OUTPUT                                                                */
57 /*                                                                        */
58 /*    None                                                                */
59 /*                                                                        */
60 /*  CALLS                                                                 */
61 /*                                                                        */
62 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
63 /*                                            blend function              */
64 /*                                                                        */
65 /*  CALLED BY                                                             */
66 /*                                                                        */
67 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
68 /*                                                                        */
69 /*  RELEASE HISTORY                                                       */
70 /*                                                                        */
71 /*    DATE              NAME                      DESCRIPTION             */
72 /*                                                                        */
73 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
74 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
75 /*                                            resulting in version 6.1    */
76 /*                                                                        */
77 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_blend(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info,GX_UBYTE alpha)78 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_blend(GX_DRAW_CONTEXT *context,
79                                                                           INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info, GX_UBYTE alpha)
80 {
81 INT                xval;
82 GX_COLOR           color;
83 GX_CONST GX_COLOR *get;
84 GX_PIXELMAP       *pixelmap;
85 GX_VALUE           pic_width;
86 GX_VALUE           offset;
87 
88     pixelmap = info -> pixelmap;
89 
90     pic_width = pixelmap -> gx_pixelmap_width;
91 
92     if ((info -> draw) && (xstart <= xend))
93     {
94         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
95 
96         /* Calculate the map offset in x-axis. */
97         offset = (GX_VALUE)(info -> x_offset % pic_width);
98 
99         for (xval = xstart; xval <= xend; xval++)
100         {
101             /*get points to the start postion of this row. So we need to calculate its position.*/
102             color = *(get + offset);
103 
104             if (color & 0xff000000)
105             {
106                 _gx_display_driver_32argb_pixel_blend(context, xval, y, color, alpha);
107             }
108             offset++;
109             if (offset >= pic_width)
110             {
111                 offset = (GX_VALUE)(offset - pic_width);
112             }
113         }
114     }
115 
116     /*This line is drawn. Update the pointer position for next row.*/
117     info -> current_pixel_ptr += (UINT)pic_width * sizeof(GX_COLOR);
118 }
119 
120 /**************************************************************************/
121 /*                                                                        */
122 /*  FUNCTION                                               RELEASE        */
123 /*                                                                        */
124 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_blend         */
125 /*                                                        PORTABLE C      */
126 /*                                                           6.1          */
127 /*  AUTHOR                                                                */
128 /*                                                                        */
129 /*    Kenneth Maxwell, Microsoft Corporation                              */
130 /*                                                                        */
131 /*  DESCRIPTION                                                           */
132 /*                                                                        */
133 /*    Internal helper function that handles writing of raw pixlemap file  */
134 /*      with brush alpha by line.                                         */
135 /*                                                                        */
136 /*  INPUT                                                                 */
137 /*                                                                        */
138 /*    context                               Drawing context               */
139 /*    xstart                                x-coord of line left          */
140 /*    xend                                  x-coord of line right         */
141 /*    y                                     y-coord of line top           */
142 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
143 /*    alpha                                 Alpha value                   */
144 /*                                                                        */
145 /*  OUTPUT                                                                */
146 /*                                                                        */
147 /*    None                                                                */
148 /*                                                                        */
149 /*  CALLS                                                                 */
150 /*                                                                        */
151 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
152 /*                                            blend function              */
153 /*                                                                        */
154 /*  CALLED BY                                                             */
155 /*                                                                        */
156 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
157 /*                                                                        */
158 /*  RELEASE HISTORY                                                       */
159 /*                                                                        */
160 /*    DATE              NAME                      DESCRIPTION             */
161 /*                                                                        */
162 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
163 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
164 /*                                            resulting in version 6.1    */
165 /*                                                                        */
166 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_raw_blend(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info,GX_UBYTE alpha)167 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_blend(GX_DRAW_CONTEXT *context,
168                                                                         INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info, GX_UBYTE alpha)
169 {
170 INT                xval;
171 INT                offset;
172 INT                pic_width;
173 GX_CONST GX_COLOR *get;
174 GX_COLOR           pixel;
175 GX_PIXELMAP       *pixelmap;
176 
177     pixelmap = info -> pixelmap;
178 
179     pic_width = pixelmap -> gx_pixelmap_width;
180 
181     if ((info -> draw) && (xstart <= xend))
182     {
183         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
184 
185         /* Calculate map offset in x-axis. */
186         offset = (info -> x_offset % pic_width);
187 
188         for (xval = xstart; xval <= xend; xval++)
189         {
190             /* get points to the start postion of this row. So we need to calculate its position. */
191             pixel = *(get + offset);
192             _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, alpha);
193             offset++;
194             if (offset >= pic_width)
195             {
196                 offset -= pic_width;
197             }
198         }
199     }
200 
201     /* This line is drawn. Update the pointer position for next row. */
202     info -> current_pixel_ptr += (UINT)pic_width * sizeof(GX_COLOR);
203 }
204 
205 /**************************************************************************/
206 /*                                                                        */
207 /*  FUNCTION                                               RELEASE        */
208 /*                                                                        */
209 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_blend  */
210 /*                                                        PORTABLE C      */
211 /*                                                           6.1          */
212 /*  AUTHOR                                                                */
213 /*                                                                        */
214 /*    Kenneth Maxwell, Microsoft Corporation                              */
215 /*                                                                        */
216 /*  DESCRIPTION                                                           */
217 /*                                                                        */
218 /*    Internal helper function that handles writing of compressed         */
219 /*    pixlemap file without alpha channel with brush alpha by line.       */
220 /*                                                                        */
221 /*  INPUT                                                                 */
222 /*                                                                        */
223 /*    context                               Drawing context               */
224 /*    xstart                                x-coord of line left          */
225 /*    xend                                  x-coord of line right         */
226 /*    y                                     y-coord of line top           */
227 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
228 /*    alpha                                 Alpha value                   */
229 /*                                                                        */
230 /*  OUTPUT                                                                */
231 /*                                                                        */
232 /*    None                                                                */
233 /*                                                                        */
234 /*  CALLS                                                                 */
235 /*                                                                        */
236 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
237 /*                                            blend function              */
238 /*                                                                        */
239 /*  CALLED BY                                                             */
240 /*                                                                        */
241 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
242 /*                                                                        */
243 /*  RELEASE HISTORY                                                       */
244 /*                                                                        */
245 /*    DATE              NAME                      DESCRIPTION             */
246 /*                                                                        */
247 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
248 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
249 /*                                            resulting in version 6.1    */
250 /*                                                                        */
251 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_blend(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info,GX_UBYTE alpha)252 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_blend(GX_DRAW_CONTEXT *context,
253                                                                                INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info, GX_UBYTE alpha)
254 {
255 INT                start_pos;
256 INT                xval;
257 GX_UBYTE           count;
258 GX_COLOR           pixel;
259 GX_PIXELMAP       *pixelmap;
260 GX_CONST GX_COLOR *get = GX_NULL;
261 GX_CONST GX_UBYTE *get_count = GX_NULL;
262 
263     pixelmap = info -> pixelmap;
264 
265     if ((info -> draw) && (xstart <= xend))
266     {
267         /* This means it's the draw operation. */
268         /* Skip the invisible pixels.*/
269         start_pos = xstart - (info -> x_offset % pixelmap -> gx_pixelmap_width);
270 
271         /* Repeat the draw operation to fill the whole dirty area. */
272         while (start_pos <= xend)
273         {
274             xval = start_pos;
275 
276             /* Start from where we need to repeat. */
277             get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
278             get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
279 
280             while (xval < start_pos + pixelmap -> gx_pixelmap_width)
281             {
282                 count = *get_count++;
283                 if (count & 0x80)
284                 {
285                     count = (GX_UBYTE)((count & 0x7f) + 1);
286 
287                     pixel = *get++;
288                     while (count--)
289                     {
290                         if (xval >= xstart && xval <= xend)
291                         {
292                             _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, alpha);
293                         }
294                         xval++;
295                     }
296                 }
297                 else
298                 {
299                     count++;
300                     while (count--)
301                     {
302                         pixel = *get++;
303                         if (xval >= xstart && xval <= xend)
304                         {
305                             _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, alpha);
306                         }
307                         xval++;
308                     }
309                 }
310             }
311             start_pos += pixelmap -> gx_pixelmap_width;
312         }
313     }
314     else
315     {
316         /* Just do skip operation here. */
317         xval = 0;
318         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
319         get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
320         while (xval < pixelmap -> gx_pixelmap_width)
321         {
322             count = *get_count++;
323             if (count & 0x80)
324             {
325                 count = (GX_UBYTE)((count & 0x7f) + 1);
326                 get++;
327             }
328             else
329             {
330                 count++;
331                 get += count;
332             }
333             xval += count;
334         }
335     }
336 
337     /* This line is drawn. cache the pointer for next line draw. */
338     info -> current_pixel_ptr = (GX_UBYTE *)get;
339     info -> current_aux_ptr = (GX_UBYTE *)get_count;
340 }
341 
342 /**************************************************************************/
343 /*                                                                        */
344 /*  FUNCTION                                               RELEASE        */
345 /*                                                                        */
346 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_c_a_blend         */
347 /*                                                        PORTABLE C      */
348 /*                                                           6.1          */
349 /*  AUTHOR                                                                */
350 /*                                                                        */
351 /*    Kenneth Maxwell, Microsoft Corporation                              */
352 /*                                                                        */
353 /*  DESCRIPTION                                                           */
354 /*                                                                        */
355 /*    Internal helper function that handles writing of compressed         */
356 /*    pixlemap file with alpha channel with brush alpha for one line.     */
357 /*                                                                        */
358 /*  INPUT                                                                 */
359 /*                                                                        */
360 /*    context                               Drawing context               */
361 /*    xstart                                x-coord of line left          */
362 /*    xend                                  x-coord of line right         */
363 /*    y                                     y-coord of line top           */
364 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
365 /*    alpha                                 Alpha value                   */
366 /*                                                                        */
367 /*  OUTPUT                                                                */
368 /*                                                                        */
369 /*    None                                                                */
370 /*                                                                        */
371 /*  CALLS                                                                 */
372 /*                                                                        */
373 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
374 /*                                            blend function              */
375 /*                                                                        */
376 /*  CALLED BY                                                             */
377 /*                                                                        */
378 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
379 /*                                                                        */
380 /*  RELEASE HISTORY                                                       */
381 /*                                                                        */
382 /*    DATE              NAME                      DESCRIPTION             */
383 /*                                                                        */
384 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
385 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
386 /*                                            resulting in version 6.1    */
387 /*                                                                        */
388 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_blend(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info,GX_UBYTE alpha)389 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_blend(GX_DRAW_CONTEXT *context,
390                                                                                      INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info, GX_UBYTE alpha)
391 {
392 INT                xval;
393 GX_UBYTE           count;
394 INT                start_pos;
395 GX_COLOR           pixel;
396 GX_CONST GX_COLOR *get = GX_NULL;
397 GX_CONST GX_UBYTE *get_count = GX_NULL;
398 GX_PIXELMAP       *pixelmap;
399 
400     pixelmap = info -> pixelmap;
401 
402     if ((info -> draw) && (xstart <= xend))
403     {
404         /* Calculate draw start position. */
405         start_pos = xstart - (info -> x_offset % pixelmap -> gx_pixelmap_width);
406 
407         /* Repeat the draw operation to fill the whole dirty area. */
408         while (start_pos <= xend)
409         {
410             xval = start_pos;
411 
412             /* Start from where we need to repeat. */
413             get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
414             get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
415 
416             while (xval < start_pos + pixelmap -> gx_pixelmap_width)
417             {
418                 count = *get_count++;
419                 if (count & 0x80)
420                 {
421                     count = (GX_UBYTE)((count & 0x7f) + 1);
422                     pixel = *get++;
423                     while (count--)
424                     {
425                         if (pixel & 0xff000000)
426                         {
427                             if (xval >= xstart && xval <= xend)
428                             {
429                                 _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, alpha);
430                             }
431                         }
432                         xval++;
433                     }
434                 }
435                 else
436                 {
437                     count++;
438                     while (count--)
439                     {
440                         pixel = *get++;
441                         if (pixel & 0xff000000)
442                         {
443                             if (xval >= xstart && xval <= xend)
444                             {
445                                 _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, alpha);
446                             }
447                         }
448                         xval++;
449                     }
450                 }
451             }
452             start_pos += pixelmap -> gx_pixelmap_width;
453         }
454     }
455     else
456     {
457         /* Just do skip operation here. */
458         xval = 0;
459         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
460         get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
461         while (xval < pixelmap -> gx_pixelmap_width)
462         {
463             count = *get_count++;
464             if (count & 0x80)
465             {
466                 count = (GX_UBYTE)((count & 0x7f) + 1);
467                 get++;
468             }
469             else
470             {
471                 count++;
472                 get += count;
473             }
474             xval += count;
475         }
476     }
477 
478     /* This line is drawn. cache the pointer for next line draw. */
479     info -> current_pixel_ptr = (GX_UBYTE *)get;
480     info -> current_aux_ptr = (GX_UBYTE *)get_count;
481 }
482 #endif
483 
484 /**************************************************************************/
485 /*                                                                        */
486 /*  FUNCTION                                               RELEASE        */
487 /*                                                                        */
488 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_write       */
489 /*                                                        PORTABLE C      */
490 /*                                                           6.1          */
491 /*  AUTHOR                                                                */
492 /*                                                                        */
493 /*    Kenneth Maxwell, Microsoft Corporation                              */
494 /*                                                                        */
495 /*  DESCRIPTION                                                           */
496 /*                                                                        */
497 /*    Internal helper function that handles writing of uncompressed       */
498 /*    pixlemap file with alpha channel for one line.                      */
499 /*                                                                        */
500 /*  INPUT                                                                 */
501 /*                                                                        */
502 /*    context                               Drawing context               */
503 /*    xstart                                x-coord of line left          */
504 /*    xend                                  x-coord of line right         */
505 /*    y                                     y-coord of line top           */
506 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
507 /*                                                                        */
508 /*  OUTPUT                                                                */
509 /*                                                                        */
510 /*    None                                                                */
511 /*                                                                        */
512 /*  CALLS                                                                 */
513 /*                                                                        */
514 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
515 /*                                            blend function              */
516 /*    _gx_display_driver_32argb_pixel_write Basic display driver pixel    */
517 /*                                            write function              */
518 /*                                                                        */
519 /*  CALLED BY                                                             */
520 /*                                                                        */
521 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
522 /*                                                                        */
523 /*  RELEASE HISTORY                                                       */
524 /*                                                                        */
525 /*    DATE              NAME                      DESCRIPTION             */
526 /*                                                                        */
527 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
528 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
529 /*                                            resulting in version 6.1    */
530 /*                                                                        */
531 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_write(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info)532 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_write(GX_DRAW_CONTEXT *context,
533                                                                           INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info)
534 {
535 INT                xval;
536 GX_COLOR           color;
537 GX_CONST GX_COLOR *get;
538 UCHAR              alpha_value;
539 GX_PIXELMAP       *pixelmap;
540 GX_VALUE           pic_width;
541 GX_VALUE           offset;
542 
543     pixelmap = info -> pixelmap;
544 
545     pic_width = pixelmap -> gx_pixelmap_width;
546 
547     if ((info -> draw) && (xstart <= xend))
548     {
549         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
550 
551         /* calculate the offset. */
552         offset = (GX_VALUE)(info -> x_offset % pic_width);
553 
554         for (xval = xstart; xval <= xend; xval++)
555         {
556             /* get points to the start postion of this row. So we need to calculate its position. */
557             color = *(get + offset);
558             alpha_value = (GX_UBYTE)((color >> 24) & 0xff);
559             if (alpha_value)
560             {
561                 if (alpha_value == 255)
562                 {
563                     _gx_display_driver_32bpp_pixel_write(context, xval, y, color);
564                 }
565                 else
566                 {
567                     _gx_display_driver_32argb_pixel_blend(context, xval, y, color, 0xff);
568                 }
569             }
570             offset++;
571             if (offset >= pic_width)
572             {
573                 offset = (GX_VALUE)(offset - pic_width);
574             }
575         }
576     }
577 
578     /* This line is drawn. Update the pointer position for next row. */
579     info -> current_pixel_ptr += (UINT)pic_width * sizeof(GX_COLOR);
580 }
581 
582 /**************************************************************************/
583 /*                                                                        */
584 /*  FUNCTION                                               RELEASE        */
585 /*                                                                        */
586 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_write         */
587 /*                                                        PORTABLE C      */
588 /*                                                           6.1          */
589 /*  AUTHOR                                                                */
590 /*                                                                        */
591 /*    Kenneth Maxwell, Microsoft Corporation                              */
592 /*                                                                        */
593 /*  DESCRIPTION                                                           */
594 /*                                                                        */
595 /*    Internal helper function that handles writing of raw pixlemap file  */
596 /*    for one line.                                                       */
597 /*                                                                        */
598 /*  INPUT                                                                 */
599 /*                                                                        */
600 /*    context                               Drawing context               */
601 /*    xstart                                x-coord of line left          */
602 /*    xend                                  x-coord of line right         */
603 /*    y                                     y-coord of line top           */
604 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
605 /*                                                                        */
606 /*  OUTPUT                                                                */
607 /*                                                                        */
608 /*    None                                                                */
609 /*                                                                        */
610 /*  CALLS                                                                 */
611 /*                                                                        */
612 /*    None                                                                */
613 /*                                                                        */
614 /*  CALLED BY                                                             */
615 /*                                                                        */
616 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
617 /*                                                                        */
618 /*  RELEASE HISTORY                                                       */
619 /*                                                                        */
620 /*    DATE              NAME                      DESCRIPTION             */
621 /*                                                                        */
622 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
623 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
624 /*                                            resulting in version 6.1    */
625 /*                                                                        */
626 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_raw_write(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info)627 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_write(GX_DRAW_CONTEXT *context,
628                                                                         INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info)
629 {
630 INT                xval;
631 INT                offset;
632 INT                pic_width;
633 GX_CONST GX_COLOR *get;
634 GX_COLOR          *put;
635 GX_PIXELMAP       *pixelmap;
636 
637     pixelmap = info -> pixelmap;
638 
639     pic_width = pixelmap -> gx_pixelmap_width;
640 
641     if ((info -> draw) && (xstart <= xend))
642     {
643         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
644         put = (GX_COLOR *)context -> gx_draw_context_memory;
645         put += y * context -> gx_draw_context_pitch + xstart;
646 
647         /* calculate the offset. */
648         offset = (info -> x_offset % pic_width);
649 
650         for (xval = xstart; xval <= xend; xval++)
651         {
652             /* get points to the start postion of this row. So we need to calculate its position. */
653             *put++ = *(get + offset);
654             offset++;
655             if (offset >= pic_width)
656             {
657                 offset -= pic_width;
658             }
659         }
660     }
661 
662     /* This line is drawn. Update the pointer position for next row. */
663     info -> current_pixel_ptr += (UINT)pic_width * sizeof(GX_COLOR);
664 }
665 
666 /**************************************************************************/
667 /*                                                                        */
668 /*  FUNCTION                                               RELEASE        */
669 /*                                                                        */
670 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_write  */
671 /*                                                        PORTABLE C      */
672 /*                                                           6.1          */
673 /*  AUTHOR                                                                */
674 /*                                                                        */
675 /*    Kenneth Maxwell, Microsoft Corporation                              */
676 /*                                                                        */
677 /*  DESCRIPTION                                                           */
678 /*                                                                        */
679 /*    Internal helper function that handles writing of compressed         */
680 /*    pixlemap file without alpha channel for one line.                   */
681 /*                                                                        */
682 /*  INPUT                                                                 */
683 /*                                                                        */
684 /*    context                               Drawing context               */
685 /*    xstart                                x-coord of line left          */
686 /*    xend                                  x-coord of line right         */
687 /*    y                                     y-coord of line top           */
688 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
689 /*                                                                        */
690 /*  OUTPUT                                                                */
691 /*                                                                        */
692 /*    None                                                                */
693 /*                                                                        */
694 /*  CALLS                                                                 */
695 /*                                                                        */
696 /*    None                                                                */
697 /*                                                                        */
698 /*  CALLED BY                                                             */
699 /*                                                                        */
700 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
701 /*                                                                        */
702 /*  RELEASE HISTORY                                                       */
703 /*                                                                        */
704 /*    DATE              NAME                      DESCRIPTION             */
705 /*                                                                        */
706 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
707 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
708 /*                                            resulting in version 6.1    */
709 /*                                                                        */
710 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_write(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info)711 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_write(GX_DRAW_CONTEXT *context,
712                                                                                INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info)
713 {
714 INT                start_pos;
715 INT                xval;
716 GX_UBYTE           count;
717 GX_COLOR           pixel;
718 GX_CONST GX_COLOR *get = GX_NULL;
719 GX_COLOR          *put;
720 GX_CONST GX_UBYTE *get_count = GX_NULL;
721 GX_PIXELMAP       *pixelmap;
722 
723     pixelmap = info -> pixelmap;
724 
725     if ((info -> draw) && (xstart <= xend))
726     {
727         /* Calculate draw start position. */
728         start_pos = xstart - (info -> x_offset % pixelmap -> gx_pixelmap_width);
729 
730         put = (GX_COLOR *)context -> gx_draw_context_memory;
731         put += y * context -> gx_draw_context_pitch + start_pos;
732 
733         /* Repeat the draw operation to fill the whole dirty area. */
734         while (start_pos <= xend)
735         {
736             xval = start_pos;
737 
738             /* Start from where we need to repeat. */
739             get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
740             get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
741 
742             while (xval < start_pos + pixelmap -> gx_pixelmap_width)
743             {
744                 count = *get_count++;
745                 if (count & 0x80)
746                 {
747                     count = (GX_UBYTE)((count & 0x7f) + 1);
748 
749                     pixel = *get++;
750                     while (count--)
751                     {
752                         if (xval >= xstart && xval <= xend)
753                         {
754                             *put = pixel;
755                         }
756                         xval++;
757                         put++;
758                     }
759                 }
760                 else
761                 {
762                     count++;
763                     while (count--)
764                     {
765                         pixel = *get++;
766                         if (xval >= xstart && xval <= xend)
767                         {
768                             *put = pixel;
769                         }
770                         xval++;
771                         put++;
772                     }
773                 }
774             }
775             start_pos += pixelmap -> gx_pixelmap_width;
776         }
777     }
778     else
779     {
780         /* Just do skip operation here. */
781         xval = 0;
782         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
783         get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
784         while (xval < pixelmap -> gx_pixelmap_width)
785         {
786             count = *get_count++;
787             if (count & 0x80)
788             {
789                 count = (GX_UBYTE)((count & 0x7f) + 1);
790                 get++;
791             }
792             else
793             {
794                 count++;
795                 get += count;
796             }
797             xval += count;
798         }
799     }
800 
801     /* This line is drawn. cache the pointer for next line draw. */
802     info -> current_pixel_ptr = (GX_UBYTE *)get;
803     info -> current_aux_ptr = (GX_UBYTE *)get_count;
804 }
805 
806 /**************************************************************************/
807 /*                                                                        */
808 /*  FUNCTION                                               RELEASE        */
809 /*                                                                        */
810 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_c_a_write         */
811 /*                                                        PORTABLE C      */
812 /*                                                           6.1          */
813 /*  AUTHOR                                                                */
814 /*                                                                        */
815 /*    Kenneth Maxwell, Microsoft Corporation                              */
816 /*                                                                        */
817 /*  DESCRIPTION                                                           */
818 /*                                                                        */
819 /*    Internal helper function that handles writing of compressed         */
820 /*    pixlemap file with alpha channel.                                   */
821 /*                                                                        */
822 /*  INPUT                                                                 */
823 /*                                                                        */
824 /*    context                               Drawing context               */
825 /*    xstart                                x-coord of line left          */
826 /*    xend                                  x-coord of line right         */
827 /*    y                                     y-coord of line top           */
828 /*    info                                  GX_FILL_PIXELMAP_INFO struct  */
829 /*                                                                        */
830 /*  OUTPUT                                                                */
831 /*                                                                        */
832 /*    None                                                                */
833 /*                                                                        */
834 /*  CALLS                                                                 */
835 /*                                                                        */
836 /*    _gx_display_driver_32argb_pixel_blend Basic display driver pixel    */
837 /*                                            blend function              */
838 /*    _gx_display_driver_32argb_pixel_write Basic display driver pixel    */
839 /*                                            write function              */
840 /*                                                                        */
841 /*  CALLED BY                                                             */
842 /*                                                                        */
843 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
844 /*                                                                        */
845 /*  RELEASE HISTORY                                                       */
846 /*                                                                        */
847 /*    DATE              NAME                      DESCRIPTION             */
848 /*                                                                        */
849 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
850 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
851 /*                                            resulting in version 6.1    */
852 /*                                                                        */
853 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_write(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info)854 static VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_write(GX_DRAW_CONTEXT *context,
855                                                                                      INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info)
856 {
857 INT                xval;
858 GX_UBYTE           count;
859 INT                start_pos;
860 GX_UBYTE           alpha_value;
861 GX_COLOR           pixel;
862 GX_CONST GX_COLOR *get = GX_NULL;
863 GX_CONST GX_UBYTE *get_count = GX_NULL;
864 GX_PIXELMAP       *pixelmap;
865 
866     pixelmap = info -> pixelmap;
867 
868     if ((info -> draw) && (xstart <= xend))
869     {
870         /* Calculate draw start position. */
871         start_pos = xstart - (info -> x_offset % pixelmap -> gx_pixelmap_width);
872 
873         /* Repeat the draw operation to fill the whole dirty area. */
874         while (start_pos <= xend)
875         {
876             xval = start_pos;
877 
878             /* Start from where we need to repeat. */
879             get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
880             get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
881 
882             while (xval < start_pos + pixelmap -> gx_pixelmap_width)
883             {
884                 count = *get_count++;
885                 if (count & 0x80)
886                 {
887                     count = (GX_UBYTE)((count & 0x7f) + 1);
888                     pixel = *get++;
889                     alpha_value = (GX_UBYTE)((pixel >> 24) & 0xff);
890                     while (count--)
891                     {
892                         if (alpha_value)
893                         {
894                             if (xval >= xstart && xval <= xend)
895                             {
896                                 _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, 0xff);
897                             }
898                         }
899                         xval++;
900                     }
901                 }
902                 else
903                 {
904                     count++;
905                     while (count--)
906                     {
907                         pixel = *get++;
908                         alpha_value = (GX_UBYTE)((pixel >> 24) & 0xff);
909                         if (alpha_value)
910                         {
911                             if (xval >= xstart && xval <= xend)
912                             {
913                                 if (alpha_value == 0xff)
914                                 {
915                                     _gx_display_driver_32bpp_pixel_write(context, xval, y, pixel);
916                                 }
917                                 else
918                                 {
919                                     _gx_display_driver_32argb_pixel_blend(context, xval, y, pixel, 0xff);
920                                 }
921                             }
922                         }
923                         xval++;
924                     }
925                 }
926             }
927             start_pos += pixelmap -> gx_pixelmap_width;
928         }
929     }
930     else
931     {
932         /* Just do skip operation here. */
933         xval = 0;
934         get = (GX_CONST GX_COLOR *)info -> current_pixel_ptr;
935         get_count = (GX_CONST GX_UBYTE *)info -> current_aux_ptr;
936         while (xval < pixelmap -> gx_pixelmap_width)
937         {
938             count = *get_count++;
939             if (count & 0x80)
940             {
941                 count = (GX_UBYTE)((count & 0x7f) + 1);
942                 get++;
943             }
944             else
945             {
946                 count++;
947                 get += count;
948             }
949             xval += count;
950         }
951     }
952 
953     /* This line is drawn. cache the pointer for next line draw. */
954     info -> current_pixel_ptr = (GX_UBYTE *)get;
955     info -> current_aux_ptr = (GX_UBYTE *)get_count;
956 }
957 
958 /**************************************************************************/
959 /*                                                                        */
960 /*  FUNCTION                                               RELEASE        */
961 /*                                                                        */
962 /*    _gx_display_driver_32bpp_horizontal_pixelmap_line_draw              */
963 /*                                                        PORTABLE C      */
964 /*                                                           6.1          */
965 /*  AUTHOR                                                                */
966 /*                                                                        */
967 /*    Kenneth Maxwell, Microsoft Corporation                              */
968 /*                                                                        */
969 /*  DESCRIPTION                                                           */
970 /*                                                                        */
971 /*    32bpp screen driver horizontal pixelmap line drawing function that  */
972 /*    handles compressed or uncompress, with or without alpha channel.    */
973 /*                                                                        */
974 /*  INPUT                                                                 */
975 /*                                                                        */
976 /*    context                               Drawing context               */
977 /*    xstart                                x-coord of line left          */
978 /*    xend                                  x-coord of line right         */
979 /*    y                                     y-coord of line top           */
980 /*    pixelmap                              Pointer to GX_PIXELMAP struct */
981 /*                                                                        */
982 /*  OUTPUT                                                                */
983 /*                                                                        */
984 /*    None                                                                */
985 /*                                                                        */
986 /*  CALLS                                                                 */
987 /*                                                                        */
988 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_c_a_write        */
989 /*                                          Real display driver pixelmap  */
990 /*                                            line draw function          */
991 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_write      */
992 /*                                          Real display driver pixelmap  */
993 /*                                            line draw function          */
994 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_write */
995 /*                                          Real display driver pixelmap  */
996 /*                                            line draw function          */
997 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_write        */
998 /*                                          Real display driver pixelmap  */
999 /*                                            line draw function          */
1000 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_c_a_blend        */
1001 /*                                          Real display driver pixelmap  */
1002 /*                                            line draw function          */
1003 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_a_blend          */
1004 /*                                          Real display driver pixelmap  */
1005 /*                                            line draw function          */
1006 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_c_blend          */
1007 /*                                          Real display driver pixelmap  */
1008 /*                                            line draw function          */
1009 /*     _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_blend        */
1010 /*                                          Real display driver pixelmap  */
1011 /*                                            line draw function          */
1012 /*                                                                        */
1013 /*  CALLED BY                                                             */
1014 /*                                                                        */
1015 /*    GUIX Internal Code                                                  */
1016 /*                                                                        */
1017 /*  RELEASE HISTORY                                                       */
1018 /*                                                                        */
1019 /*    DATE              NAME                      DESCRIPTION             */
1020 /*                                                                        */
1021 /*  05-19-2020     Kenneth Maxwell          Initial Version 6.0           */
1022 /*  09-30-2020     Kenneth Maxwell          Modified comment(s),          */
1023 /*                                            resulting in version 6.1    */
1024 /*                                                                        */
1025 /**************************************************************************/
_gx_display_driver_32bpp_horizontal_pixelmap_line_draw(GX_DRAW_CONTEXT * context,INT xstart,INT xend,INT y,GX_FILL_PIXELMAP_INFO * info)1026 VOID _gx_display_driver_32bpp_horizontal_pixelmap_line_draw(GX_DRAW_CONTEXT *context,
1027                                                             INT xstart, INT xend, INT y, GX_FILL_PIXELMAP_INFO *info)
1028 {
1029 #if defined GX_BRUSH_ALPHA_SUPPORT
1030 GX_UBYTE alpha;
1031 
1032     alpha = context -> gx_draw_context_brush.gx_brush_alpha;
1033     if ((alpha == 0) || (info -> pixelmap == GX_NULL))
1034     {
1035         /* Nothing to drawn. Just return. */
1036         return;
1037     }
1038 
1039     if (alpha != 0xff)
1040     {
1041         if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_COMPRESSED)
1042         {
1043             if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_ALPHA)
1044             {
1045                 /* compressed*/
1046                 _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_blend(context, xstart, xend, y, info, alpha);
1047             }
1048             else
1049             {
1050                 /* compressed*/
1051                 _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_blend(context, xstart, xend, y, info, alpha);
1052             }
1053         }
1054         else
1055         {
1056             if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_ALPHA)
1057             {
1058                 /* no compression */
1059                 _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_blend(context, xstart, xend, y, info, alpha);
1060             }
1061             else
1062             {
1063                 /* no compression */
1064                 _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_blend(context, xstart, xend, y, info, alpha);
1065             }
1066         }
1067 
1068         /*Current pixelmap has gone over, so the offset pointer should be reset.*/
1069         if (info -> current_pixel_ptr >= info -> pixelmap -> gx_pixelmap_data + info -> pixelmap -> gx_pixelmap_data_size)
1070         {
1071             info -> current_pixel_ptr = (GX_UBYTE *)info -> pixelmap -> gx_pixelmap_data;
1072             info -> current_aux_ptr = (GX_UBYTE *)info -> pixelmap -> gx_pixelmap_aux_data;
1073         }
1074         return;
1075     }
1076 
1077 #endif
1078 
1079     if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_COMPRESSED)
1080     {
1081         if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_ALPHA)
1082         {
1083             /* compressed*/
1084             _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_alpha_write(context, xstart, xend, y, info);
1085         }
1086         else
1087         {
1088             /* compressed*/
1089             _gx_display_driver_32bpp_horizontal_pixelmap_line_compressed_write(context, xstart, xend, y, info);
1090         }
1091     }
1092     else
1093     {
1094         if (info -> pixelmap -> gx_pixelmap_flags & GX_PIXELMAP_ALPHA)
1095         {
1096             /* no compression */
1097             _gx_display_driver_32bpp_horizontal_pixelmap_line_alpha_write(context, xstart, xend, y, info);
1098         }
1099         else
1100         {
1101             /* no compression */
1102             _gx_display_driver_32bpp_horizontal_pixelmap_line_raw_write(context, xstart, xend, y, info);
1103         }
1104     }
1105 
1106     /*Current pixelmap has gone over, so the offset pointer should be reset.*/
1107     if (info -> current_pixel_ptr >= info -> pixelmap -> gx_pixelmap_data + info -> pixelmap -> gx_pixelmap_data_size)
1108     {
1109         info -> current_pixel_ptr = (GX_UBYTE *)info ->  pixelmap -> gx_pixelmap_data;
1110         info -> current_aux_ptr = (GX_UBYTE *)info ->  pixelmap -> gx_pixelmap_aux_data;
1111     }
1112 }
1113 
1114