libg15render
|
00001 /* 00002 This file is part of g15tools. 00003 00004 g15tools is free software; you can redistribute it and/or modify 00005 it under the terms of the GNU General Public License as published by 00006 the Free Software Foundation; either version 2 of the License, or 00007 (at your option) any later version. 00008 00009 g15tools is distributed in the hope that it will be useful, 00010 but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 GNU General Public License for more details. 00013 00014 You should have received a copy of the GNU General Public License 00015 along with g15lcd; if not, write to the Free Software 00016 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 00017 */ 00018 00019 #include <fcntl.h> 00020 #include "libg15render.h" 00021 00022 void 00023 swap (int *x, int *y) 00024 { 00025 int tmp; 00026 00027 tmp = *x; 00028 *x = *y; 00029 *y = tmp; 00030 } 00031 00044 void 00045 g15r_pixelReverseFill (g15canvas * canvas, int x1, int y1, int x2, int y2, 00046 int fill, int color) 00047 { 00048 int x = 0; 00049 int y = 0; 00050 00051 for (x = x1; x <= x2; ++x) 00052 { 00053 for (y = y1; y <= y2; ++y) 00054 { 00055 if (!fill) 00056 color = !g15r_getPixel (canvas, x, y); 00057 g15r_setPixel (canvas, x, y, color); 00058 } 00059 } 00060 } 00061 00073 void 00074 g15r_pixelOverlay (g15canvas * canvas, int x1, int y1, int width, int height, 00075 short colormap[]) 00076 { 00077 int i = 0; 00078 00079 for (i = 0; i < (width * height); ++i) 00080 { 00081 int color = (colormap[i] ? G15_COLOR_BLACK : G15_COLOR_WHITE); 00082 int x = x1 + i % width; 00083 int y = y1 + i / width; 00084 g15r_setPixel (canvas, x, y, color); 00085 } 00086 } 00087 00098 void 00099 g15r_drawLine (g15canvas * canvas, int px1, int py1, int px2, int py2, 00100 const int color) 00101 { 00102 /* 00103 * Bresenham's Line Algorithm 00104 * http://en.wikipedia.org/wiki/Bresenham's_algorithm 00105 */ 00106 00107 int steep = 0; 00108 00109 if (abs (py2 - py1) > abs (px2 - px1)) 00110 steep = 1; 00111 00112 if (steep) 00113 { 00114 swap (&px1, &py1); 00115 swap (&px2, &py2); 00116 } 00117 00118 if (px1 > px2) 00119 { 00120 swap (&px1, &px2); 00121 swap (&py1, &py2); 00122 } 00123 00124 int dx = px2 - px1; 00125 int dy = abs (py2 - py1); 00126 00127 int error = 0; 00128 int y = py1; 00129 int ystep = (py1 < py2) ? 1 : -1; 00130 int x = 0; 00131 00132 for (x = px1; x <= px2; ++x) 00133 { 00134 if (steep) 00135 g15r_setPixel (canvas, y, x, color); 00136 else 00137 g15r_setPixel (canvas, x, y, color); 00138 00139 error += dy; 00140 if (2 * error >= dx) 00141 { 00142 y += ystep; 00143 error -= dx; 00144 } 00145 } 00146 } 00147 00162 void 00163 g15r_pixelBox (g15canvas * canvas, int x1, int y1, int x2, int y2, int color, 00164 int thick, int fill) 00165 { 00166 int i = 0; 00167 for (i = 0; i < thick; ++i) 00168 { 00169 g15r_drawLine (canvas, x1, y1, x2, y1, color); /* Top */ 00170 g15r_drawLine (canvas, x1, y1, x1, y2, color); /* Left */ 00171 g15r_drawLine (canvas, x2, y1, x2, y2, color); /* Right */ 00172 g15r_drawLine (canvas, x1, y2, x2, y2, color); /* Bottom */ 00173 x1++; 00174 y1++; 00175 x2--; 00176 y2--; 00177 } 00178 00179 int x = 0, y = 0; 00180 00181 if (fill) 00182 { 00183 for (x = x1; x <= x2; ++x) 00184 for (y = y1; y <= y2; ++y) 00185 g15r_setPixel (canvas, x, y, color); 00186 } 00187 00188 } 00189 00202 void 00203 g15r_drawCircle (g15canvas * canvas, int x, int y, int r, int fill, int color) 00204 { 00205 int xx, yy, dd; 00206 00207 xx = 0; 00208 yy = r; 00209 dd = 2 * (1 - r); 00210 00211 while (yy >= 0) 00212 { 00213 if (!fill) 00214 { 00215 g15r_setPixel (canvas, x + xx, y - yy, color); 00216 g15r_setPixel (canvas, x + xx, y + yy, color); 00217 g15r_setPixel (canvas, x - xx, y - yy, color); 00218 g15r_setPixel (canvas, x - xx, y + yy, color); 00219 } 00220 else 00221 { 00222 g15r_drawLine (canvas, x - xx, y - yy, x + xx, y - yy, color); 00223 g15r_drawLine (canvas, x - xx, y + yy, x + xx, y + yy, color); 00224 } 00225 if (dd + yy > 0) 00226 { 00227 yy--; 00228 dd = dd - (2 * yy + 1); 00229 } 00230 if (xx > dd) 00231 { 00232 xx++; 00233 dd = dd + (2 * xx + 1); 00234 } 00235 } 00236 } 00237 00251 void 00252 g15r_drawRoundBox (g15canvas * canvas, int x1, int y1, int x2, int y2, 00253 int fill, int color) 00254 { 00255 int y, shave = 3; 00256 00257 if (shave > (x2 - x1) / 2) 00258 shave = (x2 - x1) / 2; 00259 if (shave > (y2 - y1) / 2) 00260 shave = (y2 - y1) / 2; 00261 00262 if ((x1 != x2) && (y1 != y2)) 00263 { 00264 if (fill) 00265 { 00266 g15r_drawLine (canvas, x1 + shave, y1, x2 - shave, y1, color); 00267 for (y = y1 + 1; y < y1 + shave; y++) 00268 g15r_drawLine (canvas, x1 + 1, y, x2 - 1, y, color); 00269 for (y = y1 + shave; y <= y2 - shave; y++) 00270 g15r_drawLine (canvas, x1, y, x2, y, color); 00271 for (y = y2 - shave + 1; y < y2; y++) 00272 g15r_drawLine (canvas, x1 + 1, y, x2 - 1, y, color); 00273 g15r_drawLine (canvas, x1 + shave, y2, x2 - shave, y2, color); 00274 if (shave == 4) 00275 { 00276 g15r_setPixel (canvas, x1 + 1, y1 + 1, 00277 color == 00278 G15_COLOR_WHITE ? G15_COLOR_BLACK : 00279 G15_COLOR_WHITE); 00280 g15r_setPixel (canvas, x1 + 1, y2 - 1, 00281 color == 00282 G15_COLOR_WHITE ? G15_COLOR_BLACK : 00283 G15_COLOR_WHITE); 00284 g15r_setPixel (canvas, x2 - 1, y1 + 1, 00285 color == 00286 G15_COLOR_WHITE ? G15_COLOR_BLACK : 00287 G15_COLOR_WHITE); 00288 g15r_setPixel (canvas, x2 - 1, y2 - 1, 00289 color == 00290 G15_COLOR_WHITE ? G15_COLOR_BLACK : 00291 G15_COLOR_WHITE); 00292 } 00293 } 00294 else 00295 { 00296 g15r_drawLine (canvas, x1 + shave, y1, x2 - shave, y1, color); 00297 g15r_drawLine (canvas, x1, y1 + shave, x1, y2 - shave, color); 00298 g15r_drawLine (canvas, x2, y1 + shave, x2, y2 - shave, color); 00299 g15r_drawLine (canvas, x1 + shave, y2, x2 - shave, y2, color); 00300 if (shave > 1) 00301 { 00302 g15r_drawLine (canvas, x1 + 1, y1 + 1, x1 + shave - 1, y1 + 1, 00303 color); 00304 g15r_drawLine (canvas, x2 - shave + 1, y1 + 1, x2 - 1, y1 + 1, 00305 color); 00306 g15r_drawLine (canvas, x1 + 1, y2 - 1, x1 + shave - 1, y2 - 1, 00307 color); 00308 g15r_drawLine (canvas, x2 - shave + 1, y2 - 1, x2 - 1, y2 - 1, 00309 color); 00310 g15r_drawLine (canvas, x1 + 1, y1 + 1, x1 + 1, y1 + shave - 1, 00311 color); 00312 g15r_drawLine (canvas, x1 + 1, y2 - 1, x1 + 1, y2 - shave + 1, 00313 color); 00314 g15r_drawLine (canvas, x2 - 1, y1 + 1, x2 - 1, y1 + shave - 1, 00315 color); 00316 g15r_drawLine (canvas, x2 - 1, y2 - 1, x2 - 1, y2 - shave + 1, 00317 color); 00318 } 00319 } 00320 } 00321 } 00322 00336 void 00337 g15r_drawBar (g15canvas * canvas, int x1, int y1, int x2, int y2, int color, 00338 int num, int max, int type) 00339 { 00340 float len, length; 00341 int x; 00342 if (max == 0) 00343 return; 00344 if (num > max) 00345 num = max; 00346 00347 if (type == 2) 00348 { 00349 y1 += 2; 00350 y2 -= 2; 00351 x1 += 2; 00352 x2 -= 2; 00353 } 00354 00355 len = ((float) max / (float) num); 00356 length = (x2 - x1) / len; 00357 00358 if (type == 1) 00359 { 00360 g15r_pixelBox (canvas, x1, y1 - type, x2, y2 + type, color ^ 1, 1, 1); 00361 g15r_pixelBox (canvas, x1, y1 - type, x2, y2 + type, color, 1, 0); 00362 } 00363 else if (type == 2) 00364 { 00365 g15r_pixelBox (canvas, x1 - 2, y1 - type, x2 + 2, y2 + type, color ^ 1, 00366 1, 1); 00367 g15r_pixelBox (canvas, x1 - 2, y1 - type, x2 + 2, y2 + type, color, 1, 00368 0); 00369 } 00370 else if (type == 3) 00371 { 00372 g15r_drawLine (canvas, x1, y1 - type, x1, y2 + type, color); 00373 g15r_drawLine (canvas, x2, y1 - type, x2, y2 + type, color); 00374 g15r_drawLine (canvas, x1, y1 + ((y2 - y1) / 2), x2, 00375 y1 + ((y2 - y1) / 2), color); 00376 } 00377 g15r_pixelBox (canvas, x1, y1, (int) ceil (x1 + length), y2, color, 1, 1); 00378 } 00379 00386 int 00387 g15r_loadWbmpSplash(g15canvas *canvas, char *filename) 00388 { 00389 int width=0, height=0; 00390 char *buf; 00391 00392 buf = g15r_loadWbmpToBuf(filename, 00393 &width, 00394 &height); 00395 00396 memcpy (canvas->buffer, buf, G15_BUFFER_LEN); 00397 return 0; 00398 } 00399 00410 void 00411 g15r_drawIcon(g15canvas *canvas, char *buf, int my_x, int my_y, int width, int height) 00412 { 00413 int y,x,val; 00414 unsigned int pixel_offset = 0; 00415 unsigned int byte_offset, bit_offset; 00416 00417 for (y=0; y < height - 1; y++) 00418 for (x=0; x < width - 1; x++) 00419 { 00420 pixel_offset = y * width + x; 00421 byte_offset = pixel_offset / BYTE_SIZE; 00422 bit_offset = 7 - (pixel_offset % BYTE_SIZE); 00423 00424 val = (buf[byte_offset] & (1 << bit_offset)) >> bit_offset; 00425 g15r_setPixel (canvas, x + my_x, y + my_y, val); 00426 } 00427 } 00428 00442 void 00443 g15r_drawSprite(g15canvas *canvas, char *buf, int my_x, int my_y, int width, int height, int start_x, int start_y, int total_width) 00444 { 00445 int y,x,val; 00446 unsigned int pixel_offset = 0; 00447 unsigned int byte_offset, bit_offset; 00448 00449 for (y=0; y < height - 1; y++) 00450 for (x=0; x < width - 1; x++) 00451 { 00452 pixel_offset = (y + start_y) * total_width + (x + start_x); 00453 byte_offset = pixel_offset / BYTE_SIZE; 00454 bit_offset = 7 - (pixel_offset % BYTE_SIZE); 00455 00456 val = (buf[byte_offset] & (1 << bit_offset)) >> bit_offset; 00457 g15r_setPixel (canvas, x + my_x, y + my_y, val); 00458 } 00459 } 00460 00468 char * 00469 g15r_loadWbmpToBuf(char *filename, int *img_width, int *img_height) 00470 { 00471 int wbmp_fd; 00472 int retval; 00473 int x,y,val; 00474 char *buf; 00475 unsigned int buflen,header=4; 00476 unsigned char headerbytes[5]; 00477 unsigned int pixel_offset = 0; 00478 unsigned int byte_offset, bit_offset; 00479 00480 wbmp_fd=open(filename,O_RDONLY); 00481 if(!wbmp_fd){ 00482 return NULL; 00483 } 00484 00485 retval=read(wbmp_fd,headerbytes,5); 00486 00487 if(retval){ 00488 if (headerbytes[2] & 1) { 00489 *img_width = ((unsigned char)headerbytes[2] ^ 1) | (unsigned char)headerbytes[3]; 00490 *img_height = headerbytes[4]; 00491 header = 5; 00492 } else { 00493 *img_width = headerbytes[2]; 00494 *img_height = headerbytes[3]; 00495 } 00496 00497 int byte_width = *img_width / 8; 00498 if (*img_width %8) 00499 byte_width++; 00500 00501 buflen = byte_width * (*img_height); 00502 00503 buf = (char *)malloc (buflen); 00504 if (buf == NULL) 00505 return NULL; 00506 00507 if (header == 4) 00508 buf[0]=headerbytes[4]; 00509 00510 retval=read(wbmp_fd,buf+(5-header),buflen); 00511 00512 close(wbmp_fd); 00513 } 00514 00515 /* now invert the image */ 00516 for (y = 0; y < *img_height; y++) 00517 for (x = 0; x < *img_width; x++) 00518 { 00519 pixel_offset = y * (*img_width) + x; 00520 byte_offset = pixel_offset / BYTE_SIZE; 00521 bit_offset = 7 - (pixel_offset % BYTE_SIZE); 00522 00523 val = (buf[byte_offset] & (1 << bit_offset)) >> bit_offset; 00524 00525 if (!val) 00526 buf[byte_offset] = buf[byte_offset] | 1 << bit_offset; 00527 else 00528 buf[byte_offset] = buf[byte_offset] & ~(1 << bit_offset); 00529 } 00530 00531 return buf; 00532 } 00533 00544 void 00545 g15r_drawBigNum (g15canvas * canvas, unsigned int x1, unsigned int y1, unsigned int x2, unsigned int y2, int color, int num) 00546 { 00547 x1 += 2; 00548 x2 -= 2; 00549 00550 switch(num){ 00551 case 0: 00552 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00553 g15r_pixelBox (canvas, x1 +5, y1 +5, x2 -5, y2 - 6, 1 - color, 1, 1); 00554 break; 00555 case 1: 00556 g15r_pixelBox (canvas, x2-5, y1, x2, y2 , color, 1, 1); 00557 g15r_pixelBox (canvas, x1, y1, x2 -5, y2, 1 - color, 1, 1); 00558 break; 00559 case 2: 00560 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00561 g15r_pixelBox (canvas, x1, y1+5, x2 -5, y1+((y2/2)-3), 1 - color, 1, 1); 00562 g15r_pixelBox (canvas, x1+5, y1+((y2/2)+3), x2 , y2-6, 1 - color, 1, 1); 00563 break; 00564 case 3: 00565 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00566 g15r_pixelBox (canvas, x1, y1+5, x2 -5, y1+((y2/2)-3), 1 - color, 1, 1); 00567 g15r_pixelBox (canvas, x1, y1+((y2/2)+3), x2-5 , y2-6, 1 - color, 1, 1); 00568 break; 00569 case 4: 00570 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00571 g15r_pixelBox (canvas, x1, y1+((y2/2)+3), x2 -5, y2, 1 - color, 1, 1); 00572 g15r_pixelBox (canvas, x1+5, y1, x2-5 , y1+((y2/2)-3), 1 - color, 1, 1); 00573 break; 00574 case 5: 00575 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00576 g15r_pixelBox (canvas, x1+5, y1+5, x2 , y1+((y2/2)-3), 1 - color, 1, 1); 00577 g15r_pixelBox (canvas, x1, y1+((y2/2)+3), x2-5 , y2-6, 1 - color, 1, 1); 00578 break; 00579 case 6: 00580 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00581 g15r_pixelBox (canvas, x1+5, y1+5, x2 , y1+((y2/2)-3), 1 - color, 1, 1); 00582 g15r_pixelBox (canvas, x1+5, y1+((y2/2)+3), x2-5 , y2-6, 1 - color, 1, 1); 00583 break; 00584 case 7: 00585 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00586 g15r_pixelBox (canvas, x1, y1+5, x2 -5, y2, 1 - color, 1, 1); 00587 break; 00588 case 8: 00589 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00590 g15r_pixelBox (canvas, x1+5, y1+5, x2-5 , y1+((y2/2)-3), 1 - color, 1, 1); 00591 g15r_pixelBox (canvas, x1+5, y1+((y2/2)+3), x2-5 , y2-6, 1 - color, 1, 1); 00592 break; 00593 case 9: 00594 g15r_pixelBox (canvas, x1, y1, x2, y2 , color, 1, 1); 00595 g15r_pixelBox (canvas, x1+5, y1+5, x2-5 , y1+((y2/2)-3), 1 - color, 1, 1); 00596 g15r_pixelBox (canvas, x1, y1+((y2/2)+3), x2-5 , y2, 1 - color, 1, 1); 00597 break; 00598 case 10: 00599 g15r_pixelBox (canvas, x2-5, y1+5, x2, y1+10 , color, 1, 1); 00600 g15r_pixelBox (canvas, x2-5, y2-10, x2, y2-5 , color, 1, 1); 00601 break; 00602 case 11: 00603 g15r_pixelBox (canvas, x1, y1+((y2/2)-2), x2, y1+((y2/2)+2), color, 1, 1); 00604 break; 00605 case 12: 00606 g15r_pixelBox (canvas, x2-5, y2-5, x2, y2 , color, 1, 1); 00607 break; 00608 } 00609 } 00610