1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83
| /** * draw_jpeg - Display a jpeg picture from (0, 0) on framebuffer * @name: picture name(foo.jpg) */ int draw_jpeg(char *name) { struct jpeg_decompress_struct cinfo; struct jpeg_error_mgr jerr; FILE *infile; unsigned char *buffer; int x, y;
unsigned char *tmp_buf; unsigned long size; int ret;
if ((infile = fopen(name, "rb")) == NULL) { fprintf(stderr, "open %s failed\n", name); return -1; } cinfo.err = jpeg_std_error(&jerr); jpeg_create_decompress(&cinfo);
// 获取图片文件大小 fseek(infile, 0L, SEEK_END); size = ftell(infile); rewind(infile); tmp_buf = (unsigned char *)malloc(sizeof(char) * size); if (tmp_buf == NULL) { printf("malloc failed.\n"); return -1; } ret = fread(tmp_buf, 1, size, infile); if (ret != size) { printf("read jpeg file error.\n"); return -1; } // memory jpeg_mem_src(&cinfo, tmp_buf, size); // 指定图片在内存的地址及大小
//jpeg_stdio_src(&cinfo, infile); // 指定图片文件 jpeg_read_header(&cinfo, TRUE); jpeg_start_decompress(&cinfo);
if ((cinfo.output_width > fb_width) || (cinfo.output_height > fb_height)) { printf("too large JPEG file,cannot display\n"); return -1; } buffer = (unsigned char *) malloc(cinfo.output_width * cinfo.output_components); //printf("%d %d\n", cinfo.output_width, cinfo.output_components); /*eg, 240 3(rgb888)*/ x = y = 0; while (cinfo.output_scanline < cinfo.output_height) { jpeg_read_scanlines(&cinfo, &buffer, 1); if (fb_depth == 16) { unsigned short color; for (x=0; x < cinfo.output_width; x++) { // LCD为rgb565格式 color = make16color(buffer[x*3], buffer[x*3+1], buffer[x*3+2]); fb_pixel(x, y, color); } } else if (fb_depth == 24) { // not test memcpy((unsigned char *) fb_mem + y * fb_width * 3, buffer, cinfo.output_width * cinfo.output_components); } y++; // next scanline }
jpeg_finish_decompress(&cinfo); jpeg_destroy_decompress(&cinfo);
fclose(infile);
free(tmp_buf);
free(buffer); return 0; }
|