]> Gitweb @ Texas Instruments - Open Source Git Repositories - git.TI.com/gitweb - android/external-libkmsxx.git/blob - kms++util/src/drawing.cpp
Support RGB888
[android/external-libkmsxx.git] / kms++util / src / drawing.cpp
2 #include <kms++/kms++.h>
3 #include <kms++util/kms++util.h>
5 using namespace std;
7 namespace kms
8 {
9 void draw_rgb_pixel(IMappedFramebuffer& buf, unsigned x, unsigned y, RGB color)
10 {
11         switch (buf.format()) {
12         case PixelFormat::XRGB8888:
13         case PixelFormat::ARGB8888:
14         {
15                 uint32_t *p = (uint32_t*)(buf.map(0) + buf.stride(0) * y + x * 4);
16                 *p = color.argb8888();
17                 break;
18         }
19         case PixelFormat::XBGR8888:
20         case PixelFormat::ABGR8888:
21         {
22                 uint32_t *p = (uint32_t*)(buf.map(0) + buf.stride(0) * y + x * 4);
23                 *p = color.abgr8888();
24                 break;
25         }
26         case PixelFormat::RGB888:
27         {
28                 uint8_t *p = buf.map(0) + buf.stride(0) * y + x * 3;
29                 p[0] = color.r;
30                 p[1] = color.g;
31                 p[2] = color.b;
32                 break;
33         }
34         case PixelFormat::RGB565:
35         {
36                 uint16_t *p = (uint16_t*)(buf.map(0) + buf.stride(0) * y + x * 2);
37                 *p = color.rgb565();
38                 break;
39         }
40         default:
41                 throw std::invalid_argument("invalid pixelformat");
42         }
43 }
45 void draw_yuv422_macropixel(IMappedFramebuffer& buf, unsigned x, unsigned y, YUV yuv1, YUV yuv2)
46 {
47         ASSERT((x & 1) == 0);
49         uint8_t *p = (uint8_t*)(buf.map(0) + buf.stride(0) * y + x * 2);
51         uint8_t y0 = yuv1.y;
52         uint8_t y1 = yuv2.y;
53         uint8_t u = (yuv1.u + yuv2.u) / 2;
54         uint8_t v = (yuv1.v + yuv2.v) / 2;
56         switch (buf.format()) {
57         case PixelFormat::UYVY:
58                 p[0] = u;
59                 p[1] = y0;
60                 p[2] = v;
61                 p[3] = y1;
62                 break;
64         case PixelFormat::YUYV:
65                 p[0] = y0;
66                 p[1] = u;
67                 p[2] = y1;
68                 p[3] = v;
69                 break;
71         case PixelFormat::YVYU:
72                 p[0] = y0;
73                 p[1] = v;
74                 p[2] = y1;
75                 p[3] = u;
76                 break;
78         case PixelFormat::VYUY:
79                 p[0] = v;
80                 p[1] = y0;
81                 p[2] = u;
82                 p[3] = y1;
83                 break;
85         default:
86                 throw std::invalid_argument("invalid pixelformat");
87         }
88 }
90 void draw_yuv420_macropixel(IMappedFramebuffer& buf, unsigned x, unsigned y,
91                             YUV yuv1, YUV yuv2, YUV yuv3, YUV yuv4)
92 {
93         ASSERT((x & 1) == 0);
94         ASSERT((y & 1) == 0);
96         uint8_t *py1 = (uint8_t*)(buf.map(0) + buf.stride(0) * (y + 0) + x);
97         uint8_t *py2 = (uint8_t*)(buf.map(0) + buf.stride(0) * (y + 1) + x);
99         uint8_t *puv = (uint8_t*)(buf.map(1) + buf.stride(1) * (y / 2) + x);
101         uint8_t y0 = yuv1.y;
102         uint8_t y1 = yuv2.y;
103         uint8_t y2 = yuv3.y;
104         uint8_t y3 = yuv4.y;
105         uint8_t u = (yuv1.u + yuv2.u + yuv3.u + yuv4.u) / 4;
106         uint8_t v = (yuv1.v + yuv2.v + yuv3.v + yuv4.v) / 4;
108         switch (buf.format()) {
109         case PixelFormat::NV12:
110                 py1[0] = y0;
111                 py1[1] = y1;
112                 py2[0] = y2;
113                 py2[1] = y3;
114                 puv[0] = u;
115                 puv[1] = v;
116                 break;
118         case PixelFormat::NV21:
119                 py1[0] = y0;
120                 py1[1] = y1;
121                 py2[0] = y2;
122                 py2[1] = y3;
123                 puv[0] = v;
124                 puv[1] = u;
125                 break;
127         default:
128                 throw std::invalid_argument("invalid pixelformat");
129         }
132 void draw_rect(IMappedFramebuffer &fb, uint32_t x, uint32_t y, uint32_t w, uint32_t h, RGB color)
134         for (unsigned i = x; i < x + w; ++i) {
135                 for (unsigned j = y; j < y + h; ++j) {
136                         draw_rgb_pixel(fb, i, j, color);
137                 }
138         }
141 static bool get_char_pixel(char c, uint32_t x, uint32_t y)
143 #include "font_8x8.h"
145         uint8_t bits = fontdata_8x8[8 * c + y];
146         bool bit = (bits >> (7 - x)) & 1;
148         return bit;
151 static void draw_char(IMappedFramebuffer& buf, uint32_t xpos, uint32_t ypos, char c, RGB color)
153         unsigned x, y;
154         YUV yuvcolor = color.yuv();
156         switch (buf.format()) {
157         case PixelFormat::XRGB8888:
158         case PixelFormat::XBGR8888:
159         case PixelFormat::ARGB8888:
160         case PixelFormat::ABGR8888:
161         case PixelFormat::RGB888:
162         case PixelFormat::RGB565:
163                 for (y = 0; y < 8; y++) {
164                         for (x = 0; x < 8; x++) {
165                                 bool b = get_char_pixel(c, x, y);
167                                 draw_rgb_pixel(buf, xpos + x, ypos + y, b ? color : RGB());
168                         }
169                 }
170                 break;
172         case PixelFormat::UYVY:
173         case PixelFormat::YUYV:
174         case PixelFormat::YVYU:
175         case PixelFormat::VYUY:
176                 for (y = 0; y < 8; y++) {
177                         for (x = 0; x < 8; x += 2) {
178                                 bool b0 = get_char_pixel(c, x, y);
179                                 bool b1 = get_char_pixel(c, x + 1, y);
181                                 draw_yuv422_macropixel(buf, xpos + x, ypos + y,
182                                                        b0 ? yuvcolor : YUV(), b1 ? yuvcolor : YUV());
183                         }
184                 }
185                 break;
187         case PixelFormat::NV12:
188         case PixelFormat::NV21:
189                 for (y = 0; y < 8; y += 2) {
190                         for (x = 0; x < 8; x += 2) {
191                                 bool b00 = get_char_pixel(c, x, y);
192                                 bool b10 = get_char_pixel(c, x + 1, y);
193                                 bool b01 = get_char_pixel(c, x, y + 1);
194                                 bool b11 = get_char_pixel(c, x + 1, y + 1);
196                                 draw_yuv420_macropixel(buf, xpos + x, ypos + y,
197                                                        b00 ? yuvcolor : YUV(), b10 ? yuvcolor : YUV(),
198                                                        b01 ? yuvcolor : YUV(), b11 ? yuvcolor : YUV());
199                         }
200                 }
201                 break;
202         default:
203                 throw std::invalid_argument("unknown pixelformat");
204         }
207 void draw_text(IMappedFramebuffer& buf, uint32_t x, uint32_t y, const string& str, RGB color)
209         for(unsigned i = 0; i < str.size(); i++)
210                 draw_char(buf, (x + 8 * i), y, str[i], color);