aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJohn Hawthorn <jhawthor@uvic.ca>2008-05-15 01:07:11 -0700
committerJohn Hawthorn <jhawthor@uvic.ca>2008-05-15 01:07:11 -0700
commit74339219b352723980dcd4d87cafa166a8e27203 (patch)
treef7cf895e3949fba87b840550fa2a44076165abd8
parenta85e1645a3e44851251548d37c137ff4beadce3b (diff)
downloadmirror-meh-74339219b352723980dcd4d87cafa166a8e27203.tar.gz
mirror-meh-74339219b352723980dcd4d87cafa166a8e27203.tar.bz2
mirror-meh-74339219b352723980dcd4d87cafa166a8e27203.zip
various optimizations
-rw-r--r--src/jpeg.c23
-rw-r--r--src/main.c117
2 files changed, 81 insertions, 59 deletions
diff --git a/src/jpeg.c b/src/jpeg.c
index 6d3b40c..dde41ce 100644
--- a/src/jpeg.c
+++ b/src/jpeg.c
@@ -15,6 +15,7 @@ unsigned char *loadjpeg(char *filename, int *width, int *height){
JSAMPARRAY buffer;
int row_stride;
int i = 0;
+ int j;
int x, y;
unsigned char *retbuf;
@@ -27,23 +28,31 @@ unsigned char *loadjpeg(char *filename, int *width, int *height){
jpeg_create_decompress(&cinfo);
jpeg_stdio_src(&cinfo, infile);
jpeg_read_header(&cinfo, TRUE);
+ cinfo.do_fancy_upsampling = 0;
+ cinfo.do_block_smoothing = 0;
+ cinfo.quantize_colors = 0;
+ cinfo.dct_method = JDCT_IFAST;
jpeg_start_decompress(&cinfo);
*width = cinfo.output_width;
*height = cinfo.output_height;
- retbuf = malloc(cinfo.output_components * (cinfo.output_width * cinfo.output_height));
+ retbuf = malloc(4 * cinfo.output_components * (cinfo.output_width * cinfo.output_height));
if(cinfo.output_components != 3){
fprintf(stderr, "TODO: greyscale images are not supported\n");
exit(1);
}
row_stride = cinfo.output_width * cinfo.output_components;
- buffer = (*cinfo.mem->alloc_sarray)((j_common_ptr) &cinfo, JPOOL_IMAGE, row_stride, 1);
- for(y = 0; y < cinfo.output_height; y++){
- jpeg_read_scanlines(&cinfo, buffer, 1);
- for(x = 0; x < row_stride; x++){
- retbuf[i++] = buffer[0][x];
+ buffer = (*cinfo.mem->alloc_sarray)((j_common_ptr)&cinfo, JPOOL_IMAGE, row_stride, 16);
+ for(y = 0; y < cinfo.output_height; ){
+ int n = jpeg_read_scanlines(&cinfo, buffer, 16);
+ for(j = 0; j < n; j++){
+ for(x = 0; x < row_stride;){
+ retbuf[i++] = buffer[j][x++];
+ retbuf[i++] = buffer[j][x++];
+ retbuf[i++] = buffer[j][x++];
+ }
}
- assert(i % *width == 0);
+ y += n;
}
jpeg_finish_decompress(&cinfo);
jpeg_destroy_decompress(&cinfo);
diff --git a/src/main.c b/src/main.c
index 6250066..db89982 100644
--- a/src/main.c
+++ b/src/main.c
@@ -6,6 +6,8 @@
#include <X11/Xlib.h>
#include <X11/keysym.h>
+#include <sys/time.h>
+
#include "jpeg.h"
#include "util.h"
@@ -111,7 +113,6 @@ XImage *create_image_from_buffer(unsigned char *buf, int width, int height, int
return img;
}
-
void init(){
display = XOpenDisplay (NULL);
assert(display);
@@ -127,7 +128,7 @@ void init(){
void run(char *images[], int length){
int i = 0;
- int bufwidth, bufheight;
+ int bufwidth = 0, bufheight = 0;
int width = 0, height = 0;
XImage *img = NULL;
unsigned char *buf = NULL;
@@ -135,63 +136,75 @@ void run(char *images[], int length){
for(;;){
XEvent event;
- XNextEvent(display, &event);
- switch(event.type){
- case MapNotify:
- printf("MapNotify\n");
- break;
- case ConfigureNotify:
- printf("ConfigureNotify(%i, %i, %i, %i)\n", event.xconfigure.x, event.xconfigure.y, event.xconfigure.width, event.xconfigure.height);
- if(width != event.xconfigure.width || height != event.xconfigure.height){
- if(img)
- free(img);
- img = NULL;
- width = event.xconfigure.width;
- height = event.xconfigure.height;
- }
- break;
- case Expose:
- printf("Expose(%i)\n", event.xexpose.count);
- redraw = 1;
- break;
- case KeyPress:
- switch(XLookupKeysym(&event.xkey, 0)){
- case XK_Escape:
- exit(0);
- break;
- case XK_q:
- exit(0);
- break;
- case XK_t:
- i = (i + 1) % length;
- if(img)
- free(img);
- if(buf)
- free(buf);
- img = NULL;
- buf = NULL;
- redraw = 1;
- break;
- case XK_n:
- i = i ? i - 1 : length - 1;
+ while(XPending(display)){
+ XNextEvent(display, &event);
+ switch(event.type){
+ case MapNotify:
+ break;
+ case ConfigureNotify:
+ if(width != event.xconfigure.width || height != event.xconfigure.height){
if(img)
free(img);
- if(buf)
- free(buf);
img = NULL;
- buf = NULL;
- redraw = 1;
- break;
- }
- break;
+ width = event.xconfigure.width;
+ height = event.xconfigure.height;
+ }
+ break;
+ case Expose:
+ redraw = 1;
+ break;
+ case KeyPress:
+ switch(XLookupKeysym(&event.xkey, 0)){
+ case XK_Escape:
+ exit(0);
+ break;
+ case XK_q:
+ exit(0);
+ break;
+ case XK_t:
+ i = (i + 1) % length;
+ if(img)
+ free(img);
+ if(buf)
+ free(buf);
+ img = NULL;
+ buf = NULL;
+ redraw = 1;
+ break;
+ case XK_n:
+ i = i ? i - 1 : length - 1;
+ if(img)
+ free(img);
+ if(buf)
+ free(buf);
+ img = NULL;
+ buf = NULL;
+ redraw = 1;
+ break;
+ }
+ break;
+ }
}
if(redraw){
- if(!buf)
+ struct timeval tv0;
+ struct timeval tv1;
+ if(!buf){
+ printf("loading...");
+ gettimeofday(&tv0, NULL);
buf = loadjpeg(images[i], &bufwidth, &bufheight);
- assert(buf);
- if(!img)
+ assert(buf);
+ gettimeofday(&tv1, NULL);
+ printf(" %i milliseconds\n", (tv1.tv_sec - tv0.tv_sec) * 1000 + (tv1.tv_usec - tv0.tv_usec)/1000);
+ }
+ if(!img){
+ printf("scaling & converting...");
+ gettimeofday(&tv0, NULL);
img = create_image_from_buffer(buf, width, height, bufwidth, bufheight);
- assert(img);
+ assert(img);
+ gettimeofday(&tv1, NULL);
+ printf(" %i milliseconds\n", (tv1.tv_sec - tv0.tv_sec) * 1000 + (tv1.tv_usec - tv0.tv_usec)/1000);
+ }
+ printf("Displaying\n");
XPutImage(display, window, gc, img, 0, 0, 0, 0, width, height);
XFlush(display);
redraw = 0;