diff options
author | Tor Andersson <tor@ghostscript.com> | 2010-07-11 17:07:43 +0200 |
---|---|---|
committer | Tor Andersson <tor@ghostscript.com> | 2010-07-11 17:07:43 +0200 |
commit | 58288d41515ec9d7101de1c5949127b528a4d220 (patch) | |
tree | d795db976b729a3ad237cc7ec970c18f6cb1e399 | |
parent | 4946c50148e8c196198f50410acb444b0aa0f31d (diff) | |
download | mupdf-58288d41515ec9d7101de1c5949127b528a4d220.tar.xz |
Reinsert Robin Watts' specialized pixel unpacking loops.
-rw-r--r-- | draw/imageunpack.c | 149 | ||||
-rw-r--r-- | fitz/fitz.h | 4 | ||||
-rw-r--r-- | mupdf/pdf_image.c | 19 |
3 files changed, 142 insertions, 30 deletions
diff --git a/draw/imageunpack.c b/draw/imageunpack.c index b899a8ad..577eac21 100644 --- a/draw/imageunpack.c +++ b/draw/imageunpack.c @@ -10,38 +10,151 @@ #define get8(buf,x) (buf[x]) #define get16(buf,x) (buf[x << 1]) +static unsigned char get1tab1[256][8]; +static unsigned char get1tab1p[256][16]; +static unsigned char get1tab255[256][8]; +static unsigned char get1tab255p[256][16]; + +static void +initget1tables(void) +{ + static int once = 0; + unsigned char bits[1]; + int i, k, x; + + /* TODO: mutex lock here */ + + if (once) + return; + + for (i = 0; i < 256; i++) + { + bits[0] = i; + for (k = 0; k < 8; k++) + { + x = get1(bits, k); + + get1tab1[i][k] = x; + get1tab1p[i][k * 2] = x; + get1tab1p[i][k * 2 + 1] = 1; + + get1tab255[i][k] = x * 255; + get1tab255p[i][k * 2] = x * 255; + get1tab255p[i][k * 2 + 1] = 255; + } + } + + once = 1; +} + void -fz_unpacktile(fz_pixmap *dst, unsigned char * restrict src, int n, int depth, int stride) +fz_unpacktile(fz_pixmap *dst, unsigned char * restrict src, int n, int depth, int stride, int scale) { int pad, x, y, k; + int w = dst->w; pad = 0; if (dst->n > n) - pad = (1 << depth) - 1; + pad = ((1 << depth) - 1) * scale; - /* TODO: reinsert Robin Watts' specialized loops here */ + initget1tables(); for (y = 0; y < dst->h; y++) { unsigned char *sp = src + y * stride; unsigned char *dp = dst->samples + y * (dst->w * dst->n); - int b = 0; - for (x = 0; x < dst->w; x++) + + /* Specialized loops */ + + if (n == 1 && depth == 1 && scale == 1 && !pad) + { + int w3 = w >> 3; + for (x = 0; x < w3; x++) + { + memcpy(dp, get1tab1[*sp++], 8); + dp += 8; + } + x = x << 3; + if (x < w) + memcpy(dp, get1tab1[*sp], w - x); + } + + else if (n == 1 && depth == 1 && scale == 255 && !pad) + { + int w3 = w >> 3; + for (x = 0; x < w3; x++) + { + memcpy(dp, get1tab255[*sp++], 8); + dp += 8; + } + x = x << 3; + if (x < w) + memcpy(dp, get1tab255[*sp], w - x); + } + + else if (n == 1 && depth == 1 && scale == 1 && pad == 1) + { + int w3 = w >> 3; + for (x = 0; x < w3; x++) + { + memcpy(dp, get1tab1p[*sp++], 16); + dp += 16; + } + x = x << 3; + if (x < w) + memcpy(dp, get1tab1p[*sp], (w - x) << 1); + } + + else if (n == 1 && depth == 1 && scale == 255 && pad == 255) + { + int w3 = w >> 3; + for (x = 0; x < w3; x++) + { + memcpy(dp, get1tab255p[*sp++], 16); + dp += 16; + } + x = x << 3; + if (x < w) + memcpy(dp, get1tab255p[*sp], (w - x) << 1); + } + + else if (depth == 8 && !pad) + { + int len = w * n; + while (len--) + *dp++ = *sp++; + } + + else if (depth == 8 && pad == 255) + { + for (x = 0; x < w; x++) + { + for (k = 0; k < n; k++) + *dp++ = *sp++; + *dp++ = 255; + } + } + + else { - for (k = 0; k < n; k++) + int b = 0; + for (x = 0; x < w; x++) { - switch (depth) + for (k = 0; k < n; k++) { - case 1: *dp++ = get1(sp, b); break; - case 2: *dp++ = get2(sp, b); break; - case 4: *dp++ = get4(sp, b); break; - case 8: *dp++ = get8(sp, b); break; - case 16: *dp++ = get16(sp, b); break; + switch (depth) + { + case 1: *dp++ = get1(sp, b) * scale; break; + case 2: *dp++ = get2(sp, b) * scale; break; + case 4: *dp++ = get4(sp, b) * scale; break; + case 8: *dp++ = get8(sp, b); break; + case 16: *dp++ = get16(sp, b); break; + } + b++; } - b++; + if (pad) + *dp++ = pad; } - if (pad) - *dp++ = pad; } } } @@ -51,7 +164,7 @@ fz_unpacktile(fz_pixmap *dst, unsigned char * restrict src, int n, int depth, in */ void -fz_decodetile(fz_pixmap *pix, float *decode, int scale) +fz_decodetile(fz_pixmap *pix, float *decode) { int min[FZ_MAXCOLORS + 2]; int max[FZ_MAXCOLORS + 2]; @@ -62,7 +175,7 @@ fz_decodetile(fz_pixmap *pix, float *decode, int scale) int needed; int k; - needed = scale != 1; + needed = 0; for (k = 0; k < n; k++) { min[k] = decode[k * 2] * 255; @@ -77,7 +190,7 @@ fz_decodetile(fz_pixmap *pix, float *decode, int scale) while (len--) { for (k = 0; k < n; k++) - p[k] = min[k] + fz_mul255(sub[k], p[k] * scale); + p[k] = min[k] + fz_mul255(sub[k], p[k]); p += n; } } diff --git a/fitz/fitz.h b/fitz/fitz.h index 517e001e..9dbbafdc 100644 --- a/fitz/fitz.h +++ b/fitz/fitz.h @@ -1112,8 +1112,8 @@ void fz_executedisplaylist(fz_displaylist *list, fz_device *dev, fz_matrix ctm); extern void fz_accelerate(void); extern void fz_acceleratearch(void); -extern void fz_decodetile(fz_pixmap *pix, float *decode, int scale); -extern void fz_unpacktile(fz_pixmap *dst, unsigned char * restrict src, int n, int depth, int stride); +extern void fz_decodetile(fz_pixmap *pix, float *decode); +extern void fz_unpacktile(fz_pixmap *dst, unsigned char * restrict src, int n, int depth, int stride, int scale); extern void (*fz_duff_ni1on)(unsigned char*restrict,int,int,unsigned char*restrict,int,unsigned char*restrict,int,int,int); extern void (*fz_duff_1i1o1)(unsigned char*restrict,int,unsigned char*restrict,int,unsigned char*restrict,int,int,int); diff --git a/mupdf/pdf_image.c b/mupdf/pdf_image.c index 221dd507..9724b1ef 100644 --- a/mupdf/pdf_image.c +++ b/mupdf/pdf_image.c @@ -249,7 +249,7 @@ pdf_loadimage(pdf_image **imgp, pdf_xref *xref, fz_obj *rdb, fz_obj *dict) } static void -pdf_maskcolorkey(fz_pixmap *pix, int n, int *colorkey) +pdf_maskcolorkey(fz_pixmap *pix, int n, int *colorkey, int scale) { unsigned char *p = pix->samples; int len = pix->w * pix->h; @@ -258,7 +258,7 @@ pdf_maskcolorkey(fz_pixmap *pix, int n, int *colorkey) { t = 1; for (k = 0; k < n; k++) - if (p[k] < colorkey[k * 2] || p[k] > colorkey[k * 2 + 1]) + if (p[k] < colorkey[k * 2] * scale || p[k] > colorkey[k * 2 + 1] * scale) t = 0; if (t) for (k = 0; k < pix->n; k++) @@ -283,15 +283,10 @@ pdf_loadtile(pdf_image *img /* ...bbox/y+h should go here... */) case 4: scale = 17; break; } - fz_unpacktile(tile, img->samples->bp, img->n, img->bpc, img->stride); + fz_unpacktile(tile, img->samples->bp, img->n, img->bpc, img->stride, scale); if (img->usecolorkey) - pdf_maskcolorkey(tile, img->n, img->colorkey); - - if (!img->indexed) - { - fz_decodetile(tile, img->decode, scale); - } + pdf_maskcolorkey(tile, img->n, img->colorkey, scale); if (img->indexed) { @@ -303,12 +298,16 @@ pdf_loadtile(pdf_image *img /* ...bbox/y+h should go here... */) decode[2] = img->decode[2]; decode[3] = img->decode[3]; - fz_decodetile(tile, decode, scale); + fz_decodetile(tile, decode); conv = pdf_expandindexedpixmap(tile); fz_droppixmap(tile); tile = conv; } + else + { + fz_decodetile(tile, img->decode); + } return tile; } |