aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/evas/src/modules/engines/gl_common/evas_gl_font.c
diff options
context:
space:
mode:
Diffstat (limited to 'libraries/evas/src/modules/engines/gl_common/evas_gl_font.c')
-rw-r--r--libraries/evas/src/modules/engines/gl_common/evas_gl_font.c203
1 files changed, 203 insertions, 0 deletions
diff --git a/libraries/evas/src/modules/engines/gl_common/evas_gl_font.c b/libraries/evas/src/modules/engines/gl_common/evas_gl_font.c
new file mode 100644
index 0000000..e5f3a4a
--- /dev/null
+++ b/libraries/evas/src/modules/engines/gl_common/evas_gl_font.c
@@ -0,0 +1,203 @@
1#include "evas_gl_private.h"
2
3void *
4evas_gl_font_texture_new(void *context, RGBA_Font_Glyph *fg)
5{
6 Evas_Engine_GL_Context *gc = context;
7 Evas_GL_Texture *tex;
8 DATA8 *data;
9 int w, h, j, nw;
10 DATA8 *ndata;
11 int fh;
12
13 if (fg->ext_dat) return fg->ext_dat; // FIXME: one engine at a time can do this :(
14
15 w = fg->glyph_out->bitmap.width;
16 h = fg->glyph_out->bitmap.rows;
17 if ((w == 0) || (h == 0)) return NULL;
18
19 data = fg->glyph_out->bitmap.buffer;
20 j = fg->glyph_out->bitmap.pitch;
21 if (j < w) j = w;
22
23 nw = ((w + 3) / 4) * 4;
24 ndata = alloca(nw *h);
25 if (!ndata) return NULL;
26 if (fg->glyph_out->bitmap.num_grays == 256)
27 {
28 int x, y;
29 DATA8 *p1, *p2;
30
31 for (y = 0; y < h; y++)
32 {
33 p1 = data + (j * y);
34 p2 = ndata + (nw * y);
35 for (x = 0; x < w; x++)
36 {
37 *p2 = *p1;
38 p1++;
39 p2++;
40 }
41 }
42 }
43 else if (fg->glyph_out->bitmap.num_grays == 0)
44 {
45 DATA8 *tmpbuf = NULL, *dp, *tp, bits;
46 int bi, bj, end;
47 const DATA8 bitrepl[2] = {0x0, 0xff};
48
49 tmpbuf = alloca(w);
50 if (tmpbuf)
51 {
52 int x, y;
53 DATA8 *p1, *p2;
54
55 for (y = 0; y < h; y++)
56 {
57 p1 = tmpbuf;
58 p2 = ndata + (nw * y);
59 tp = tmpbuf;
60 dp = data + (y * fg->glyph_out->bitmap.pitch);
61 for (bi = 0; bi < w; bi += 8)
62 {
63 bits = *dp;
64 if ((w - bi) < 8) end = w - bi;
65 else end = 8;
66 for (bj = 0; bj < end; bj++)
67 {
68 *tp = bitrepl[(bits >> (7 - bj)) & 0x1];
69 tp++;
70 }
71 dp++;
72 }
73 for (x = 0; x < w; x++)
74 {
75 *p2 = *p1;
76 p1++;
77 p2++;
78 }
79 }
80 }
81 }
82// fh = h;
83 fh = fg->fi->max_h;
84 tex = evas_gl_common_texture_alpha_new(gc, ndata, w, h, fh);
85 tex->sx1 = ((double)(tex->x)) / (double)tex->pt->w;
86 tex->sy1 = ((double)(tex->y)) / (double)tex->pt->h;
87 tex->sx2 = ((double)(tex->x + tex->w)) / (double)tex->pt->w;
88 tex->sy2 = ((double)(tex->y + tex->h)) / (double)tex->pt->h;
89 return tex;
90}
91
92void
93evas_gl_font_texture_free(void *tex)
94{
95 if (!tex) return;
96 evas_gl_common_texture_free(tex);
97}
98
99void
100evas_gl_font_texture_draw(void *context, void *surface __UNUSED__, void *draw_context, RGBA_Font_Glyph *fg, int x, int y)
101{
102 Evas_Engine_GL_Context *gc = context;
103 RGBA_Draw_Context *dc = draw_context;
104 Evas_GL_Texture *tex;
105 Cutout_Rects *rects;
106 Cutout_Rect *rct;
107 int r, g, b, a;
108 double ssx, ssy, ssw, ssh;
109 int c, cx, cy, cw, ch;
110 int i;
111 int sx, sy, sw, sh;
112
113 if (dc != gc->dc) return;
114 tex = fg->ext_dat;
115 if (!tex) return;
116 a = (dc->col.col >> 24) & 0xff;
117 if (a == 0) return;
118 r = (dc->col.col >> 16) & 0xff;
119 g = (dc->col.col >> 8 ) & 0xff;
120 b = (dc->col.col ) & 0xff;
121 sx = 0; sy = 0; sw = tex->w, sh = tex->h;
122 if ((!gc->dc->cutout.rects) ||
123 ((gc->shared->info.tune.cutout.max > 0) &&
124 (gc->dc->cutout.active > gc->shared->info.tune.cutout.max)))
125 {
126 if (gc->dc->clip.use)
127 {
128 int nx, ny, nw, nh;
129
130 nx = x; ny = y; nw = tex->w; nh = tex->h;
131 RECTS_CLIP_TO_RECT(nx, ny, nw, nh,
132 gc->dc->clip.x, gc->dc->clip.y,
133 gc->dc->clip.w, gc->dc->clip.h);
134 if ((nw < 1) || (nh < 1)) return;
135 if ((nx == x) && (ny == y) && (nw == tex->w) && (nh == tex->h))
136 {
137 evas_gl_common_context_font_push(gc, tex,
138 0.0, 0.0, 0.0, 0.0,
139// sx, sy, sw, sh,
140 x, y, tex->w, tex->h,
141 r, g, b, a);
142 return;
143 }
144 ssx = (double)sx + ((double)(sw * (nx - x)) / (double)(tex->w));
145 ssy = (double)sy + ((double)(sh * (ny - y)) / (double)(tex->h));
146 ssw = ((double)sw * (double)(nw)) / (double)(tex->w);
147 ssh = ((double)sh * (double)(nh)) / (double)(tex->h);
148 evas_gl_common_context_font_push(gc, tex,
149 ssx, ssy, ssw, ssh,
150 nx, ny, nw, nh,
151 r, g, b, a);
152 }
153 else
154 {
155 evas_gl_common_context_font_push(gc, tex,
156 0.0, 0.0, 0.0, 0.0,
157// sx, sy, sw, sh,
158 x, y, tex->w, tex->h,
159 r, g, b, a);
160 }
161 return;
162 }
163 /* save out clip info */
164 c = gc->dc->clip.use; cx = gc->dc->clip.x; cy = gc->dc->clip.y; cw = gc->dc->clip.w; ch = gc->dc->clip.h;
165 evas_common_draw_context_clip_clip(gc->dc, 0, 0, gc->w, gc->h);
166 evas_common_draw_context_clip_clip(gc->dc, x, y, tex->w, tex->h);
167 /* our clip is 0 size.. abort */
168 if ((gc->dc->clip.w <= 0) || (gc->dc->clip.h <= 0))
169 {
170 gc->dc->clip.use = c; gc->dc->clip.x = cx; gc->dc->clip.y = cy; gc->dc->clip.w = cw; gc->dc->clip.h = ch;
171 return;
172 }
173 rects = evas_common_draw_context_apply_cutouts(dc);
174 for (i = 0; i < rects->active; ++i)
175 {
176 int nx, ny, nw, nh;
177
178 rct = rects->rects + i;
179 nx = x; ny = y; nw = tex->w; nh = tex->h;
180 RECTS_CLIP_TO_RECT(nx, ny, nw, nh, rct->x, rct->y, rct->w, rct->h);
181 if ((nw < 1) || (nh < 1)) continue;
182 if ((nx == x) && (ny == y) && (nw == tex->w) && (nh == tex->h))
183 {
184 evas_gl_common_context_font_push(gc, tex,
185 0.0, 0.0, 0.0, 0.0,
186// sx, sy, sw, sh,
187 x, y, tex->w, tex->h,
188 r, g, b, a);
189 continue;
190 }
191 ssx = (double)sx + ((double)(sw * (nx - x)) / (double)(tex->w));
192 ssy = (double)sy + ((double)(sh * (ny - y)) / (double)(tex->h));
193 ssw = ((double)sw * (double)(nw)) / (double)(tex->w);
194 ssh = ((double)sh * (double)(nh)) / (double)(tex->h);
195 evas_gl_common_context_font_push(gc, tex,
196 ssx, ssy, ssw, ssh,
197 nx, ny, nw, nh,
198 r, g, b, a);
199 }
200 evas_common_draw_context_apply_clear_cutouts(rects);
201 /* restore clip info */
202 gc->dc->clip.use = c; gc->dc->clip.x = cx; gc->dc->clip.y = cy; gc->dc->clip.w = cw; gc->dc->clip.h = ch;
203}