diff --git a/Makefile b/Makefile index a996ea0c8..1eecadaa2 100644 --- a/Makefile +++ b/Makefile @@ -9,6 +9,7 @@ KPVCRLIBDIR=kpvcrlib CRENGINEDIR=$(KPVCRLIBDIR)/crengine FREETYPEDIR=$(MUPDFDIR)/thirdparty/freetype-2.4.10 +JPEGDIR=$(MUPDFDIR)/thirdparty/jpeg-9 LFSDIR=luafilesystem POPENNSDIR=popen-noshell @@ -111,7 +112,7 @@ POPENNSLIB := $(POPENNSDIR)/libpopen_noshell.a all: kpdfview VERSION?=$(shell git describe HEAD) -kpdfview: kpdfview.o einkfb.o pdf.o blitbuffer.o drawcontext.o input.o $(POPENNSLIB) util.o ft.o lfs.o mupdfimg.o $(MUPDFLIBS) $(THIRDPARTYLIBS) $(LUALIB) djvu.o $(DJVULIBS) cre.o $(CRENGINELIBS) +kpdfview: kpdfview.o einkfb.o pdf.o blitbuffer.o drawcontext.o input.o $(POPENNSLIB) util.o ft.o lfs.o mupdfimg.o $(MUPDFLIBS) $(THIRDPARTYLIBS) $(LUALIB) djvu.o $(DJVULIBS) cre.o $(CRENGINELIBS) pic.o pic_jpeg.o echo $(VERSION) > git-rev $(CC) \ $(CFLAGS) \ @@ -131,6 +132,8 @@ kpdfview: kpdfview.o einkfb.o pdf.o blitbuffer.o drawcontext.o input.o $(POPENNS $(LUALIB) \ djvu.o \ $(DJVULIBS) \ + pic.o \ + pic_jpeg.o \ cre.o \ $(CRENGINELIBS) \ $(STATICLIBSTDCPP) \ @@ -155,6 +158,12 @@ kpdfview.o pdf.o blitbuffer.o util.o drawcontext.o einkfb.o input.o mupdfimg.o: djvu.o: %.o: %.c $(CC) -c $(KPDFREADER_CFLAGS) -I$(DJVUDIR)/ $< -o $@ +pic.o: %.o: %.c + $(CC) -c $(KPDFREADER_CFLAGS) $< -o $@ + +pic_jpeg.o: %.o: %.c + $(CC) -c $(KPDFREADER_CFLAGS) -I$(JPEGDIR)/ -I$(MUPDFDIR)/scripts/ $< -o $@ + cre.o: %.o: %.cpp $(CC) -c $(CFLAGS) -I$(CRENGINEDIR)/crengine/include/ -I$(LUADIR)/src $< -o $@ diff --git a/pic.c b/pic.c index 0934c76fd..9e3d1d2c4 100644 --- a/pic.c +++ b/pic.c @@ -19,13 +19,12 @@ #include #include #include -#include #include -#include "jpeglib.h" #include "blitbuffer.h" #include "drawcontext.h" #include "pic.h" +#include "pic_jpeg.h" #define MIN(a, b) ((a) < (b) ? (a) : (b)) #define MAX(a, b) ((a) > (b) ? (a) : (b)) @@ -42,66 +41,6 @@ typedef struct PicPage { PicDocument *doc; } PicPage; -struct my_error_mgr { - struct jpeg_error_mgr pub; - jmp_buf setjmp_buffer; -}; - -typedef struct my_error_mgr *my_error_ptr; - -METHODDEF(void) my_error_exit(j_common_ptr cinfo) -{ - my_error_ptr myerr = (my_error_ptr) cinfo->err; - (*cinfo->err->output_message) (cinfo); - longjmp(myerr->setjmp_buffer, 1); -} - -uint8_t *readJPEG(const char *fname, int *width, int *height, int *components) -{ - struct jpeg_decompress_struct cinfo; - struct my_error_mgr jerr; - FILE *infile; - JSAMPARRAY buffer; - int row_stride; - long cont; - JSAMPLE *image_buffer; - - if ((infile = fopen(fname, "r")) == NULL) return NULL; - cinfo.err = jpeg_std_error(&jerr.pub); - jerr.pub.error_exit = my_error_exit; - if (setjmp(jerr.setjmp_buffer)) { - jpeg_destroy_decompress(&cinfo); - fclose(infile); - return NULL; - } - jpeg_create_decompress(&cinfo); - jpeg_stdio_src(&cinfo, infile); - (void) jpeg_read_header(&cinfo, TRUE); - (void) jpeg_start_decompress(&cinfo); - row_stride = cinfo.output_width * cinfo.output_components; - buffer = (*cinfo.mem->alloc_sarray) - ((j_common_ptr) & cinfo, JPOOL_IMAGE, row_stride, 1); - - image_buffer = (JSAMPLE *) malloc(cinfo.image_width*cinfo.image_height*cinfo.output_components); - if (image_buffer == NULL) return NULL; - *width = cinfo.image_width; - *height = cinfo.image_height; - - //cont = cinfo.output_height - 1; - cont = 0; - while (cinfo.output_scanline < cinfo.output_height) { - (void) jpeg_read_scanlines(&cinfo, buffer, 1); - memcpy(image_buffer + cinfo.image_width * cinfo.output_components * cont, buffer[0], row_stride); - cont++; - } - - (void) jpeg_finish_decompress(&cinfo); - jpeg_destroy_decompress(&cinfo); - fclose(infile); - *components = cinfo.output_components; - return (uint8_t *)image_buffer; -} - /* Uses luminance match for approximating the human perception of colour, * as per http://en.wikipedia.org/wiki/Grayscale#Converting_color_to_grayscale * L = 0.299*Red + 0.587*Green + 0.114*Blue */ @@ -129,7 +68,7 @@ static int openDocument(lua_State *L) { luaL_getmetatable(L, "picdocument"); lua_setmetatable(L, -2); - uint8_t *raw_image = readJPEG(filename, &width, &height, &components); + uint8_t *raw_image = jpegLoadFile(filename, &width, &height, &components); if (!raw_image) return luaL_error(L, "Cannot open jpeg file"); diff --git a/pic_jpeg.c b/pic_jpeg.c new file mode 100644 index 000000000..18e5eab38 --- /dev/null +++ b/pic_jpeg.c @@ -0,0 +1,84 @@ +/* + KindlePDFViewer: JPEG support for Picture Viewer module + Copyright (C) 2012 Tigran Aivazian + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include +#include +#include +#include + +#include "jpeglib.h" + +struct my_error_mgr { + struct jpeg_error_mgr pub; + jmp_buf setjmp_buffer; +}; + +typedef struct my_error_mgr *my_error_ptr; + +METHODDEF(void) my_error_exit(j_common_ptr cinfo) +{ + my_error_ptr myerr = (my_error_ptr) cinfo->err; + (*cinfo->err->output_message) (cinfo); + longjmp(myerr->setjmp_buffer, 1); +} + +uint8_t *jpegLoadFile(const char *fname, int *width, int *height, int *components) +{ + struct jpeg_decompress_struct cinfo; + struct my_error_mgr jerr; + FILE *infile; + JSAMPARRAY buffer; + int row_stride; + long cont; + JSAMPLE *image_buffer; + + if ((infile = fopen(fname, "r")) == NULL) return NULL; + cinfo.err = jpeg_std_error(&jerr.pub); + jerr.pub.error_exit = my_error_exit; + if (setjmp(jerr.setjmp_buffer)) { + jpeg_destroy_decompress(&cinfo); + fclose(infile); + return NULL; + } + jpeg_create_decompress(&cinfo); + jpeg_stdio_src(&cinfo, infile); + (void) jpeg_read_header(&cinfo, TRUE); + (void) jpeg_start_decompress(&cinfo); + row_stride = cinfo.output_width * cinfo.output_components; + buffer = (*cinfo.mem->alloc_sarray) + ((j_common_ptr) & cinfo, JPOOL_IMAGE, row_stride, 1); + + image_buffer = (JSAMPLE *) malloc(cinfo.image_width*cinfo.image_height*cinfo.output_components); + if (image_buffer == NULL) return NULL; + *width = cinfo.image_width; + *height = cinfo.image_height; + + //cont = cinfo.output_height - 1; + cont = 0; + while (cinfo.output_scanline < cinfo.output_height) { + (void) jpeg_read_scanlines(&cinfo, buffer, 1); + memcpy(image_buffer + cinfo.image_width * cinfo.output_components * cont, buffer[0], row_stride); + cont++; + } + + (void) jpeg_finish_decompress(&cinfo); + jpeg_destroy_decompress(&cinfo); + fclose(infile); + *components = cinfo.output_components; + return (uint8_t *)image_buffer; +} diff --git a/pic_jpeg.h b/pic_jpeg.h new file mode 100644 index 000000000..22be93d45 --- /dev/null +++ b/pic_jpeg.h @@ -0,0 +1,30 @@ +/* + KindlePDFViewer: Interface to JPEG module for picture viewer + Copyright (C) 2012 Tigran Aivazian + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ +#ifndef _PIC_JPEG_H +#define _PIC_JPEG_H + +/* each new image format must provide fmtLoadFile() function which + * performs the following: + * 1. Opens the file 'filename' + * 2. Reads the image data from it into a buffer allocated with malloc() + * 3. Fills in the image *width, *height and *components (number of bytes per pixel) + * 4. Closes the file + * 5. Returns the pointer to the image data + */ +extern uint8_t *jpegLoadFile(const char *fname, int *width, int *height, int *components); +#endif