root / proj / src / font.c @ 184
History | View | Annotate | Download (4.71 KB)
1 | 182 | up20180642 | #include <lcom/lcf.h> |
---|---|---|---|
2 | |||
3 | #include "font.h" |
||
4 | |||
5 | 183 | up20180642 | #include "xpm_utils.h" |
6 | #include "graph.h" |
||
7 | #include "utils.h" |
||
8 | #include "errors.h" |
||
9 | |||
10 | 182 | up20180642 | struct glyph{
|
11 | uint16_t w, h; |
||
12 | uint8_t *map; |
||
13 | }; |
||
14 | 183 | up20180642 | typedef struct glyph glyph_t; |
15 | static glyph_t* (glyph_ctor)(const char **xpm){ |
||
16 | if(xpm == NULL) return NULL; |
||
17 | 182 | up20180642 | glyph_t *ret = malloc(sizeof(glyph_t));
|
18 | if(ret == NULL) return NULL; |
||
19 | enum xpm_image_type type = XPM_8_8_8_8;
|
||
20 | xpm_image_t img; |
||
21 | ret->map = xpm_load((xpm_map_t)xpm, type, &img); |
||
22 | if(ret->map == NULL){ |
||
23 | free(ret); |
||
24 | return NULL; |
||
25 | } |
||
26 | ret->w = img.width; |
||
27 | ret->h = img.height; |
||
28 | return ret;
|
||
29 | } |
||
30 | 183 | up20180642 | static void (glyph_dtor)(glyph_t *p){ |
31 | 182 | up20180642 | if(p == NULL) return; |
32 | free(p->map); |
||
33 | free(p); |
||
34 | } |
||
35 | 183 | up20180642 | static int (glyph_draw_to_alpha_buffer)(const glyph_t *p, int16_t x, int16_t y, uint8_t *alp_buf, uint16_t W, uint16_t H){ |
36 | if(p == NULL) return NULL_PTR; |
||
37 | int r;
|
||
38 | for(int16_t h = 0; h < p->h; ++h){ |
||
39 | for(int16_t w = 0; w < p->w; ++w){ |
||
40 | uint32_t c = *((uint32_t*)p->map + w + h*p->w); |
||
41 | uint8_t a = GET_ALP(c); |
||
42 | //c = c & 0xFF000000;
|
||
43 | //if(c != 0) printf("%d %d 0x%X\n", w, h, c);
|
||
44 | //else printf("%d %d <========================\n");
|
||
45 | |||
46 | r = graph_set_pixel_alpha_buffer(x+w, y-p->h+h, a, alp_buf, W, H); |
||
47 | |||
48 | |||
49 | //r = graph_set_pixel_alpha(x+w, y-p->h+h, GET_COLOR(c), GET_ALP(c));
|
||
50 | |||
51 | //printf("%d %d 0x%X\n", x, y, *(buf+(x+y*p->w)*sizeof(uint32_t)));
|
||
52 | if(r != SUCCESS && r != OUT_OF_RANGE) return r; |
||
53 | } |
||
54 | } |
||
55 | return SUCCESS;
|
||
56 | } |
||
57 | |||
58 | struct font{
|
||
59 | size_t nchars; |
||
60 | glyph_t **glyphs; |
||
61 | }; |
||
62 | #include "sprite.h" |
||
63 | #include "rectangle.h" |
||
64 | font_t* (font_ctor)(const char *s){ |
||
65 | font_t *ret = malloc(sizeof(font_t));
|
||
66 | if(ret == NULL) return NULL; |
||
67 | ret->nchars = 128;
|
||
68 | ret->glyphs = malloc(ret->nchars*sizeof(glyph_t*));
|
||
69 | if(ret->glyphs == NULL){ |
||
70 | free(ret->glyphs); |
||
71 | free(ret); |
||
72 | return NULL; |
||
73 | } |
||
74 | char filepath[1024]; |
||
75 | for(size_t i = 0; i < ret->nchars; ++i){ |
||
76 | sprintf(filepath, "%s/ascii%03d.xpm2", s, i);
|
||
77 | char **xpm = xpm_load_xpm2(filepath);
|
||
78 | ret->glyphs[i] = glyph_ctor((const char**)xpm); |
||
79 | } |
||
80 | return ret;
|
||
81 | } |
||
82 | void (font_dtor)(font_t *p){
|
||
83 | if(p == NULL) return; |
||
84 | for(size_t i = 0; i < p->nchars; ++i) |
||
85 | glyph_dtor(p->glyphs[i]); |
||
86 | free(p->glyphs); |
||
87 | free(p); |
||
88 | } |
||
89 | |||
90 | struct text{
|
||
91 | const font_t *fnt;
|
||
92 | char *txt;
|
||
93 | int16_t x, y; |
||
94 | int size;
|
||
95 | uint32_t color; |
||
96 | }; |
||
97 | text_t* (text_ctor)(const font_t *fnt, const char *txt){ |
||
98 | if(fnt == NULL) return NULL; |
||
99 | text_t *ret = malloc(sizeof(text_t));
|
||
100 | if(ret == NULL) return NULL; |
||
101 | ret->fnt = fnt; |
||
102 | ret->txt = NULL;
|
||
103 | text_set_text(ret, txt); |
||
104 | ret->x = 0;
|
||
105 | ret->y = 0;
|
||
106 | ret->size = 70;
|
||
107 | ret->color = BLACK; |
||
108 | return ret;
|
||
109 | } |
||
110 | void (text_dtor)(text_t *p){
|
||
111 | if(p == NULL) return; |
||
112 | free(p->txt); |
||
113 | free(p); |
||
114 | } |
||
115 | void (text_set_text) (text_t *p, const char *txt){ |
||
116 | size_t sz = strlen(txt); |
||
117 | p->txt = realloc(p->txt, (sz+1)*sizeof(char)); |
||
118 | if(p->txt == NULL) return; |
||
119 | strcpy(p->txt, txt); |
||
120 | } |
||
121 | void (text_set_pos) (text_t *p, int16_t x, int16_t y){ p->x = x; p->y = y; }
|
||
122 | void (text_set_size) (text_t *p, unsigned size ){ p->size = size; } |
||
123 | void (text_set_color)(text_t *p, uint32_t color ){ p->color = color; }
|
||
124 | void (text_draw)(const text_t *p){ |
||
125 | printf("-%s-\n", p->txt);
|
||
126 | const size_t len = strlen(p->txt);
|
||
127 | uint16_t W = 0, H = 0; |
||
128 | for(size_t i = 0; i < len; ++i){ |
||
129 | const glyph_t *g = p->fnt->glyphs[(size_t)p->txt[i]];
|
||
130 | if(g != NULL){ W += g->w; H = max(H, g->h); } |
||
131 | } |
||
132 | printf("%d %d\n", W, H);
|
||
133 | |||
134 | uint8_t *alp_buf = malloc(W*H); |
||
135 | |||
136 | { |
||
137 | int16_t y = H; |
||
138 | int16_t x = 0;
|
||
139 | for(size_t i = 0; i < len; ++i){ |
||
140 | const glyph_t *g = p->fnt->glyphs[(size_t)p->txt[i]];
|
||
141 | if(g != NULL){ |
||
142 | if(glyph_draw_to_alpha_buffer(g, x, y, alp_buf, W, H)) return; |
||
143 | x += g->w; |
||
144 | } |
||
145 | } |
||
146 | } |
||
147 | double factor = (double)p->size/(double)H; |
||
148 | |||
149 | uint16_t newH = H*factor; |
||
150 | uint16_t newW = W*factor; |
||
151 | |||
152 | for(size_t newy = 0; newy < newH; ++newy){ |
||
153 | size_t y = newy/factor; |
||
154 | for(size_t newx = 0; newx < newW; ++newx){ |
||
155 | size_t x = newx/factor; |
||
156 | *(alp_buf+newx+newy*W) = *(alp_buf+x+y*W); |
||
157 | (void)x;
|
||
158 | (void)y;
|
||
159 | } |
||
160 | } |
||
161 | |||
162 | printf("L163\n");
|
||
163 | for(int16_t y = 0; y < newH; ++y){ //printf("L163,%d\n", y); |
||
164 | for(int16_t x = 0; x < newW; ++x){ //if(y > 147) printf("L164, %d %d\n", x, y); |
||
165 | uint8_t a = *(alp_buf+x+y*W); //if(y > 147) printf("L165\n");
|
||
166 | graph_set_pixel_alpha(x+p->x,y+p->y,p->color, a); //if(y > 147) printf("L166\n");
|
||
167 | } |
||
168 | } |
||
169 | printf("L170\n");
|
||
170 | free(alp_buf); |
||
171 | printf("L172\n");
|
||
172 | } |