From: DRC Date: Wed, 23 Feb 2011 12:09:56 +0000 (+0000) Subject: Support for compressing from/decompressing to a BufferedImage in the Java wrapper X-Git-Tag: 1.1.90~214 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=84a1bcca6fd0f21091a84f04b820b29012c60857;p=libjpeg-turbo Support for compressing from/decompressing to a BufferedImage in the Java wrapper git-svn-id: svn+ssh://svn.code.sf.net/p/libjpeg-turbo/code/trunk@432 632fc199-4ca6-4c93-a231-07263d6284db --- diff --git a/java/TJUnitTest.java b/java/TJUnitTest.java index e52b1f8..227729a 100644 --- a/java/TJUnitTest.java +++ b/java/TJUnitTest.java @@ -32,6 +32,8 @@ import java.io.*; import java.util.*; +import java.awt.image.*; +import javax.imageio.*; import org.libjpegturbo.turbojpeg.*; public class TJUnitTest { @@ -42,6 +44,7 @@ public class TJUnitTest { System.out.println("\nUSAGE: java "+classname+" [options]\n"); System.out.println("Options:\n"); System.out.println("-yuv = test YUV encoding/decoding support\n"); + System.out.println("-bi = test BufferedImage support\n"); System.exit(1); } @@ -60,11 +63,18 @@ public class TJUnitTest { {1, 1, 1, 1, 2, 2, 0}; private final static int _boffset[]= {2, 0, 2, 0, 1, 3, 0}; + private final static int biType[]= + {0, BufferedImage.TYPE_3BYTE_BGR, BufferedImage.TYPE_INT_BGR, + BufferedImage.TYPE_INT_RGB, 0, 0, BufferedImage.TYPE_BYTE_GRAY}; private final static int _3byteFormats[]= {TJ.PF_RGB, TJ.PF_BGR}; + private final static int _3byteFormatsBI[]= + {TJ.PF_BGR}; private final static int _4byteFormats[]= {TJ.PF_RGBX, TJ.PF_BGRX, TJ.PF_XBGR, TJ.PF_XRGB}; + private final static int _4byteFormatsBI[]= + {TJ.PF_RGBX, TJ.PF_BGRX}; private final static int _onlyGray[]= {TJ.PF_GRAY}; private final static int _onlyRGB[]= @@ -72,6 +82,7 @@ public class TJUnitTest { private final static int YUVENCODE=1, YUVDECODE=2; private static int yuv=0; + private static boolean bi=false; private static int exitstatus=0; @@ -149,6 +160,56 @@ public class TJUnitTest { } } + private static void initimg(BufferedImage img, int pf, int flags) + { + int i, _i, j, w=img.getWidth(), h=img.getHeight(), pixel; + + if(pf==TJ.PF_GRAY) + { + for(_i=0; _i<16; _i++) + { + if((flags&TJ.BOTTOMUP)!=0) i=h-_i-1; else i=_i; + for(j=0; jcvi+1) + v=(v<0)? v+256:v; + if(vcv+1) { - throw new Exception("\nComp. "+vname+" at "+i+","+j+" should be "+cvi + throw new Exception("\nComp. "+vname+" at "+i+","+j+" should be "+cv +", not "+v+"\n"); } } - private static void checkval0(int i, int j, byte v, String vname) + private static void checkval0(int i, int j, int v, String vname) throws Exception { - int vi=(v<0)? v+256:v; - if(vi>1) + v=(v<0)? v+256:v; + if(v>1) { throw new Exception("\nComp. "+vname+" at "+i+","+j+" should be 0, not " +v+"\n"); } } - private static void checkval255(int i, int j, byte v, String vname) + private static void checkval255(int i, int j, int v, String vname) throws Exception { - int vi=(v<0)? v+256:v; - if(vi<254 && !(vi==217 && i==0 && j==21)) + v=(v<0)? v+256:v; + if(v<254 && !(v==217 && i==0 && j==21)) { throw new Exception("\nComp. "+vname+" at "+i+","+j+" should be 255, not " +v+"\n"); @@ -309,6 +370,115 @@ public class TJUnitTest { return retval; } + private static int checkimg(BufferedImage img, int pf, + int subsamp, int scalefactor, int flags) throws Exception + { + int i, _i, j, retval=1, w=img.getWidth(), h=img.getHeight(); + int halfway=16/scalefactor, blocksize=8/scalefactor; + + try + { + if(subsamp==TJ.SAMP_GRAY) + { + for(_i=0; _i>16) & 0xFF; + int g=(img.getRGB(j, i)>>8) & 0xFF; + int b=img.getRGB(j, i) & 0xFF; + if(((_i/blocksize)+(j/blocksize))%2==0) + { + checkval255(_i, j, r, "R"); + checkval255(_i, j, g, "G"); + checkval255(_i, j, b, "B"); + } + else + { + checkval(_i, j, r, "R", 76); + checkval(_i, j, g, "G", 76); + checkval(_i, j, b, "B", 76); + } + } + } + for(_i=halfway; _i>16) & 0xFF; + int g=(img.getRGB(j, i)>>8) & 0xFF; + int b=img.getRGB(j, i) & 0xFF; + if(((_i/blocksize)+(j/blocksize))%2==0) + { + checkval0(_i, j, r, "R"); + checkval0(_i, j, g, "G"); + checkval0(_i, j, b, "B"); + } + else + { + checkval(_i, j, r, "R", 226); + checkval(_i, j, g, "G", 226); + checkval(_i, j, b, "B", 226); + } + } + } + } + else + { + for(_i=0; _i>16) & 0xFF; + int g=(img.getRGB(j, i)>>8) & 0xFF; + int b=img.getRGB(j, i) & 0xFF; + checkval255(_i, j, r, "R"); + if(((_i/blocksize)+(j/blocksize))%2==0) + { + checkval255(_i, j, g, "G"); + checkval255(_i, j, b, "B"); + } + else + { + checkval0(_i, j, g, "G"); + checkval0(_i, j, b, "B"); + } + } + } + for(_i=halfway; _i>16) & 0xFF; + int g=(img.getRGB(j, i)>>8) & 0xFF; + int b=img.getRGB(j, i) & 0xFF; + checkval0(_i, j, b, "B"); + if(((_i/blocksize)+(j/blocksize))%2==0) + { + checkval0(_i, j, r, "R"); + checkval0(_i, j, g, "G"); + } + else + { + checkval255(_i, j, r, "R"); + checkval255(_i, j, g, "G"); + } + } + } + } + } + catch(Exception e) + { + System.out.println(e); + retval=0; + } + return retval; + } + private static int PAD(int v, int p) { return ((v+(p)-1)&(~((p)-1))); @@ -444,9 +614,9 @@ public class TJUnitTest { int h, int pf, String basefilename, int subsamp, int qual, int flags) throws Exception { - String tempstr; byte [] bmpbuf; + String tempstr; byte [] bmpbuf=null; BufferedImage img=null; String pixformat; double t; - int size=0; + int size=0, ps=TJ.pixelSize[pf]; if(yuv==YUVENCODE) flags|=TJ.YUV; @@ -459,13 +629,31 @@ public class TJUnitTest { if(yuv==YUVENCODE) System.out.print("YUV ... "); else System.out.print("Q"+qual+" ... "); - bmpbuf=new byte[w*h*TJ.pixelSize[pf]+1]; - initbuf(bmpbuf, w, h, pf, flags); + if(bi) + { + img=new BufferedImage(w, h, biType[pf]); + initimg(img, pf, flags); + tempstr=basefilename+"_enc_"+pixformat+"_" + +(((flags&TJ.BOTTOMUP)!=0)? "BU":"TD")+"_"+_subnames[subsamp] + +"_Q"+qual+".png"; + File file=new File(tempstr); + ImageIO.write(img, "png", file); + } + else + { + bmpbuf=new byte[w*h*ps+1]; + initbuf(bmpbuf, w, h, pf, flags); + } Arrays.fill(jpegbuf, (byte)0); t=gettime(); - tjc.setBitmapBuffer(bmpbuf, w, 0, h, pf); - size=tjc.compress(jpegbuf, subsamp, qual, flags); + if(bi) + size=tjc.compress(img, jpegbuf, subsamp, qual, flags); + else + { + tjc.setBitmapBuffer(bmpbuf, w, 0, h, pf); + size=tjc.compress(jpegbuf, subsamp, qual, flags); + } t=gettime()-t; if(yuv==YUVENCODE) @@ -476,6 +664,7 @@ public class TJUnitTest { +(((flags&TJ.BOTTOMUP)!=0)? "BU":"TD")+"_"+_subnames[subsamp] +"_Q"+qual+".jpg"; writejpeg(jpegbuf, size, tempstr); + if(yuv==YUVENCODE) { if(checkbufyuv(jpegbuf, size, w, h, subsamp)==1) @@ -493,10 +682,12 @@ public class TJUnitTest { int jpegsize, int w, int h, int pf, String basefilename, int subsamp, int flags, int scalefactor) throws Exception { - String pixformat; int _hdrw=0, _hdrh=0, _hdrsubsamp=-1; double t; + String pixformat, tempstr; int _hdrw=0, _hdrh=0, _hdrsubsamp=-1; + double t; int scaledw=(w+scalefactor-1)/scalefactor; int scaledh=(h+scalefactor-1)/scalefactor; int temp1, temp2; + BufferedImage img=null; byte [] bmpbuf=null; if(yuv==YUVDECODE) flags|=TJ.YUV; else if(yuv==YUVENCODE) return; @@ -525,9 +716,24 @@ public class TJUnitTest { if(temp1!=scaledw || temp2!=scaledh) throw new Exception("Scaled size mismatch"); - byte [] bmpbuf=tjd.decompress(scaledw, 0, scaledh, pf, flags); + if(bi) + { + img=new BufferedImage(scaledw, scaledh, biType[pf]); + tjd.decompress(img, flags); + } + else + bmpbuf=tjd.decompress(scaledw, 0, scaledh, pf, flags); t=gettime()-t; + if(bi) + { + tempstr=basefilename+"_dec_"+pixformat+"_" + +(((flags&TJ.BOTTOMUP)!=0)? "BU":"TD")+"_"+_subnames[subsamp] + +"_"+scalefactor+"x"+".png"; + File file=new File(tempstr); + ImageIO.write(img, "png", file); + } + if(yuv==YUVDECODE) { if(checkbufyuv(bmpbuf, bmpbuf.length, w, h, subsamp)==1) @@ -536,13 +742,15 @@ public class TJUnitTest { } else { - if(checkbuf(bmpbuf, scaledw, scaledh, pf, subsamp, scalefactor, flags) - ==1) + if((bi && checkimg(img, pf, subsamp, scalefactor, flags)==1) + || (!bi && checkbuf(bmpbuf, scaledw, scaledh, pf, subsamp, scalefactor, + flags)==1)) System.out.print("Passed."); else { System.out.print("FAILED!"); exitstatus=-1; - dumpbuf(bmpbuf, scaledw, scaledh, pf, scalefactor, flags); + if(bmpbuf!=null) + dumpbuf(bmpbuf, scaledw, scaledh, pf, scalefactor, flags); } } System.out.format(" %.6f ms\n", t*1000.); @@ -669,10 +877,13 @@ public class TJUnitTest { if(argv[i].substring(0, 1).equalsIgnoreCase("-h") || argv[i].equalsIgnoreCase("-?")) usage(); + if(argv[i].equalsIgnoreCase("-bi")) bi=true; } + if(bi && doyuv) + throw new Exception("-bi and -yuv cannot be used together."); if(doyuv) yuv=YUVENCODE; - dotest(35, 39, _3byteFormats, TJ.SAMP_444, "test"); - dotest(39, 41, _4byteFormats, TJ.SAMP_444, "test"); + dotest(35, 39, bi? _3byteFormatsBI:_3byteFormats, TJ.SAMP_444, "test"); + dotest(39, 41, bi? _4byteFormatsBI:_4byteFormats, TJ.SAMP_444, "test"); if(doyuv) { dotest(41, 35, _3byteFormats, TJ.SAMP_422, "test"); @@ -681,9 +892,9 @@ public class TJUnitTest { dotest(41, 35, _4byteFormats, TJ.SAMP_420, "test"); } dotest(35, 39, _onlyGray, TJ.SAMP_GRAY, "test"); - dotest(39, 41, _3byteFormats, TJ.SAMP_GRAY, "test"); - dotest(41, 35, _4byteFormats, TJ.SAMP_GRAY, "test"); - if(!doyuv) dotest1(); + dotest(39, 41, bi? _3byteFormatsBI:_3byteFormats, TJ.SAMP_GRAY, "test"); + dotest(41, 35, bi? _4byteFormatsBI:_4byteFormats, TJ.SAMP_GRAY, "test"); + if(!doyuv && !bi) dotest1(); if(doyuv) { yuv=YUVDECODE; @@ -700,6 +911,7 @@ public class TJUnitTest { catch(Exception e) { System.out.println(e); + exitstatus=-1; } System.exit(exitstatus); } diff --git a/java/org/libjpegturbo/turbojpeg/TJCompressor.java b/java/org/libjpegturbo/turbojpeg/TJCompressor.java index 8833570..0fcffac 100644 --- a/java/org/libjpegturbo/turbojpeg/TJCompressor.java +++ b/java/org/libjpegturbo/turbojpeg/TJCompressor.java @@ -28,6 +28,8 @@ package org.libjpegturbo.turbojpeg; +import java.awt.image.*; + public class TJCompressor { public TJCompressor() throws Exception { @@ -60,6 +62,50 @@ public class TJCompressor { flags | TJ.getFlags(bitmapPixelFormat)); } + public int compress(BufferedImage srcImage, byte [] dstBuf, int jpegSubsamp, + int jpegQual, int flags) throws Exception { + if(srcImage == null || flags < 0) + throw new Exception("Invalid argument in decompress()"); + flags &= ~(TJ.YUV); + int width = srcImage.getWidth(); + int height = srcImage.getHeight(); + int pixelFormat; boolean intPixels=false; + switch(srcImage.getType()) { + case BufferedImage.TYPE_3BYTE_BGR: + pixelFormat=TJ.PF_BGR; break; + case BufferedImage.TYPE_BYTE_GRAY: + pixelFormat=TJ.PF_GRAY; break; + case BufferedImage.TYPE_INT_BGR: + pixelFormat=TJ.PF_RGBX; intPixels=true; break; + case BufferedImage.TYPE_INT_RGB: + pixelFormat=TJ.PF_BGRX; intPixels=true; break; + default: + throw new Exception("Unsupported BufferedImage format"); + } + WritableRaster wr = srcImage.getRaster(); + if(intPixels) { + SinglePixelPackedSampleModel sm = + (SinglePixelPackedSampleModel)srcImage.getSampleModel(); + int pitch = sm.getScanlineStride(); + DataBufferInt db = (DataBufferInt)wr.getDataBuffer(); + int [] buf = db.getData(); + return compress(buf, width, pitch, height, dstBuf, jpegSubsamp, jpegQual, + flags | TJ.getFlags(pixelFormat)); + } + else { + ComponentSampleModel sm = + (ComponentSampleModel)srcImage.getSampleModel(); + int pixelSize = sm.getPixelStride(); + if(pixelSize != TJ.pixelSize[pixelFormat]) + throw new Exception("Inconsistency between pixel format and pixel size in BufferedImage"); + int pitch = sm.getScanlineStride(); + DataBufferByte db = (DataBufferByte)wr.getDataBuffer(); + byte [] buf = db.getData(); + return compress(buf, width, pitch, height, TJ.getPixelSize(pixelFormat), + dstBuf, jpegSubsamp, jpegQual, flags | TJ.getFlags(pixelFormat)); + } + } + public void close() throws Exception { destroy(); } @@ -83,6 +129,10 @@ public class TJCompressor { int height, int pixelSize, byte [] dstbuf, int jpegSubsamp, int jpegQual, int flags) throws Exception; + private native int compress(int [] srcBuf, int width, int pitch, + int height, byte [] dstbuf, int jpegSubsamp, int jpegQual, int flags) + throws Exception; + static { System.loadLibrary("turbojpeg"); } diff --git a/java/org/libjpegturbo/turbojpeg/TJDecompressor.java b/java/org/libjpegturbo/turbojpeg/TJDecompressor.java index 01d5e9c..08d0bbd 100644 --- a/java/org/libjpegturbo/turbojpeg/TJDecompressor.java +++ b/java/org/libjpegturbo/turbojpeg/TJDecompressor.java @@ -28,6 +28,8 @@ package org.libjpegturbo.turbojpeg; +import java.awt.image.*; + public class TJDecompressor { public TJDecompressor() throws Exception { @@ -66,49 +68,96 @@ public class TJDecompressor { return jpegSubsamp; } - public int getScaledWidth(int desired_width, int desired_height) + public int getScaledWidth(int desiredWidth, int desiredHeight) throws Exception { if(jpegWidth < 1 || jpegHeight < 1) throw new Exception("JPEG buffer not initialized"); - return getScaledWidth(jpegWidth, jpegHeight, desired_width, - desired_height); + return getScaledWidth(jpegWidth, jpegHeight, desiredWidth, + desiredHeight); } - public int getScaledHeight(int output_width, int output_height) + public int getScaledHeight(int desiredWidth, int desiredHeight) throws Exception { if(jpegWidth < 1 || jpegHeight < 1) throw new Exception("JPEG buffer not initialized"); - return getScaledHeight(jpegWidth, jpegHeight, output_width, - output_height); + return getScaledHeight(jpegWidth, jpegHeight, desiredWidth, + desiredHeight); } - public void decompress(byte [] dstBuf, int width, int pitch, - int height, int pixelFormat, int flags) throws Exception { + public void decompress(byte [] dstBuf, int desiredWidth, int pitch, + int desiredHeight, int pixelFormat, int flags) throws Exception { if(jpegBuf == null) throw new Exception("JPEG buffer not initialized"); - decompress(jpegBuf, jpegBufSize, dstBuf, width, pitch, height, - TJ.getPixelSize(pixelFormat), flags | TJ.getFlags(pixelFormat)); + decompress(jpegBuf, jpegBufSize, dstBuf, desiredWidth, pitch, + desiredHeight, TJ.getPixelSize(pixelFormat), + flags | TJ.getFlags(pixelFormat)); } - public byte [] decompress(int width, int pitch, int height, + public byte [] decompress(int desiredWidth, int pitch, int desiredHeight, int pixelFormat, int flags) throws Exception { - if(width < 0 || height < 0 || pitch < 0 || pixelFormat < 0 - || pixelFormat >= TJ.NUMPFOPT) + if(desiredWidth < 0 || desiredHeight < 0 || pitch < 0 || pixelFormat < 0 + || pixelFormat >= TJ.NUMPFOPT || flags < 0) throw new Exception("Invalid argument in decompress()"); int pixelSize = TJ.getPixelSize(pixelFormat); - int scaledWidth = getScaledWidth(width, height); - int scaledHeight = getScaledHeight(width, height); + int scaledWidth = getScaledWidth(desiredWidth, desiredHeight); + int scaledHeight = getScaledHeight(desiredWidth, desiredHeight); if(pitch == 0) pitch = scaledWidth * pixelSize; int bufSize; if((flags&TJ.YUV)!=0) - bufSize = TJ.bufSizeYUV(width, height, jpegSubsamp); + bufSize = TJ.bufSizeYUV(jpegWidth, jpegHeight, jpegSubsamp); else bufSize = pitch * scaledHeight; byte [] buf = new byte[bufSize]; if(jpegBuf == null) throw new Exception("JPEG buffer not initialized"); - decompress(jpegBuf, jpegBufSize, buf, width, pitch, height, + decompress(jpegBuf, jpegBufSize, buf, desiredWidth, pitch, desiredHeight, TJ.getPixelSize(pixelFormat), flags | TJ.getFlags(pixelFormat)); return buf; } + public void decompress(BufferedImage dstImage, int flags) throws Exception { + if(dstImage == null || flags < 0) + throw new Exception("Invalid argument in decompress()"); + flags &= ~(TJ.YUV); + int desiredWidth = dstImage.getWidth(); + int desiredHeight = dstImage.getHeight(); + int scaledWidth = getScaledWidth(desiredWidth, desiredHeight); + int scaledHeight = getScaledHeight(desiredWidth, desiredHeight); + if(scaledWidth != desiredWidth || scaledHeight != desiredHeight) + throw new Exception("BufferedImage dimensions do not match a scaled image size that TurboJPEG is capable of generating."); + int pixelFormat; boolean intPixels=false; + switch(dstImage.getType()) { + case BufferedImage.TYPE_3BYTE_BGR: + pixelFormat=TJ.PF_BGR; break; + case BufferedImage.TYPE_BYTE_GRAY: + pixelFormat=TJ.PF_GRAY; break; + case BufferedImage.TYPE_INT_BGR: + pixelFormat=TJ.PF_RGBX; intPixels=true; break; + case BufferedImage.TYPE_INT_RGB: + pixelFormat=TJ.PF_BGRX; intPixels=true; break; + default: + throw new Exception("Unsupported BufferedImage format"); + } + WritableRaster wr = dstImage.getRaster(); + if(intPixels) { + SinglePixelPackedSampleModel sm = + (SinglePixelPackedSampleModel)dstImage.getSampleModel(); + int pitch = sm.getScanlineStride(); + DataBufferInt db = (DataBufferInt)wr.getDataBuffer(); + int [] buf = db.getData(); + decompress(jpegBuf, jpegBufSize, buf, scaledWidth, pitch, scaledHeight, + flags | TJ.getFlags(pixelFormat)); + } + else { + ComponentSampleModel sm = + (ComponentSampleModel)dstImage.getSampleModel(); + int pixelSize = sm.getPixelStride(); + if(pixelSize != TJ.pixelSize[pixelFormat]) + throw new Exception("Inconsistency between pixel format and pixel size in BufferedImage"); + int pitch = sm.getScanlineStride(); + DataBufferByte db = (DataBufferByte)wr.getDataBuffer(); + byte [] buf = db.getData(); + decompress(buf, scaledWidth, pitch, scaledHeight, pixelFormat, flags); + } + } + public void close() throws Exception { destroy(); } @@ -131,14 +180,18 @@ public class TJDecompressor { throws Exception; private native void decompress(byte [] srcBuf, int size, byte [] dstBuf, - int width, int pitch, int height, int pixelSize, int flags) + int desiredWidth, int pitch, int desiredHeight, int pixelSize, int flags) + throws Exception; + + private native void decompress(byte [] srcBuf, int size, int [] dstBuf, + int desiredWidth, int pitch, int desiredHeight, int flags) throws Exception; - private native int getScaledWidth(int input_width, int input_height, - int output_width, int output_height) throws Exception; + private native int getScaledWidth(int jpegWidth, int jpegHeight, + int desiredWidth, int desiredHeight) throws Exception; - private native int getScaledHeight(int input_width, int input_height, - int output_width, int output_height) throws Exception; + private native int getScaledHeight(int jpegWidth, int jpegHeight, + int desiredWidth, int desiredHeight) throws Exception; static { System.loadLibrary("turbojpeg"); diff --git a/java/org_libjpegturbo_turbojpeg_TJCompressor.h b/java/org_libjpegturbo_turbojpeg_TJCompressor.h index 3148fb6..e7129af 100644 --- a/java/org_libjpegturbo_turbojpeg_TJCompressor.h +++ b/java/org_libjpegturbo_turbojpeg_TJCompressor.h @@ -28,9 +28,17 @@ JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_destroy * Method: compress * Signature: ([BIIII[BIII)I */ -JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress +JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3BIIII_3BIII (JNIEnv *, jobject, jbyteArray, jint, jint, jint, jint, jbyteArray, jint, jint, jint); +/* + * Class: org_libjpegturbo_turbojpeg_TJCompressor + * Method: compress + * Signature: ([IIII[BIII)I + */ +JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3IIII_3BIII + (JNIEnv *, jobject, jintArray, jint, jint, jint, jbyteArray, jint, jint, jint); + #ifdef __cplusplus } #endif diff --git a/java/org_libjpegturbo_turbojpeg_TJDecompressor.h b/java/org_libjpegturbo_turbojpeg_TJDecompressor.h index 16c3923..8f65388 100644 --- a/java/org_libjpegturbo_turbojpeg_TJDecompressor.h +++ b/java/org_libjpegturbo_turbojpeg_TJDecompressor.h @@ -36,9 +36,17 @@ JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress * Method: decompress * Signature: ([BI[BIIIII)V */ -JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress +JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3BIIIII (JNIEnv *, jobject, jbyteArray, jint, jbyteArray, jint, jint, jint, jint, jint); +/* + * Class: org_libjpegturbo_turbojpeg_TJDecompressor + * Method: decompress + * Signature: ([BI[IIIII)V + */ +JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3IIIII + (JNIEnv *, jobject, jbyteArray, jint, jintArray, jint, jint, jint, jint); + /* * Class: org_libjpegturbo_turbojpeg_TJDecompressor * Method: getScaledWidth diff --git a/turbojpeg-jni.c b/turbojpeg-jni.c index f2f34ee..b9bd429 100644 --- a/turbojpeg-jni.c +++ b/turbojpeg-jni.c @@ -86,7 +86,7 @@ JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_init return; } -JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress +JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3BIIII_3BIII (JNIEnv *env, jobject obj, jbyteArray src, jint width, jint pitch, jint height, jint pixelsize, jbyteArray dst, jint jpegsubsamp, jint jpegqual, jint flags) @@ -114,6 +114,33 @@ JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress return (jint)size; } +JNIEXPORT jint JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3IIII_3BIII + (JNIEnv *env, jobject obj, jintArray src, jint width, jint pitch, + jint height, jbyteArray dst, jint jpegsubsamp, jint jpegqual, jint flags) +{ + tjhandle handle=0; + unsigned long size=0; + unsigned char *srcbuf=NULL, *dstbuf=NULL; + + gethandle(); + + bailif0(srcbuf=(*env)->GetPrimitiveArrayCritical(env, src, 0)); + bailif0(dstbuf=(*env)->GetPrimitiveArrayCritical(env, dst, 0)); + + if(tjCompress(handle, srcbuf, width, pitch*sizeof(jint), height, + sizeof(jint), dstbuf, &size, jpegsubsamp, jpegqual, flags)==-1) + { + (*env)->ReleasePrimitiveArrayCritical(env, dst, dstbuf, 0); + (*env)->ReleasePrimitiveArrayCritical(env, src, srcbuf, 0); + _throw(tjGetErrorStr()); + } + + bailout: + if(dstbuf) (*env)->ReleasePrimitiveArrayCritical(env, dst, dstbuf, 0); + if(srcbuf) (*env)->ReleasePrimitiveArrayCritical(env, src, srcbuf, 0); + return (jint)size; +} + JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJCompressor_destroy (JNIEnv *env, jobject obj) { @@ -199,7 +226,7 @@ JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress return; } -JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress +JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3BIIIII (JNIEnv *env, jobject obj, jbyteArray src, jint size, jbyteArray dst, jint width, jint pitch, jint height, jint pixelsize, jint flags) { @@ -225,6 +252,33 @@ JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress return; } +JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3IIIII + (JNIEnv *env, jobject obj, jbyteArray src, jint size, jintArray dst, + jint width, jint pitch, jint height, jint flags) +{ + tjhandle handle=0; + unsigned char *srcbuf=NULL, *dstbuf=NULL; + + gethandle(); + + bailif0(srcbuf=(*env)->GetPrimitiveArrayCritical(env, src, 0)); + bailif0(dstbuf=(*env)->GetPrimitiveArrayCritical(env, dst, 0)); + + if(tjDecompress(handle, srcbuf, (unsigned long)size, dstbuf, width, + pitch*sizeof(jint), height, sizeof(jint), flags)==-1) + { + (*env)->ReleasePrimitiveArrayCritical(env, dst, dstbuf, 0); + (*env)->ReleasePrimitiveArrayCritical(env, src, srcbuf, 0); + _throw(tjGetErrorStr()); + } + + bailout: + if(dstbuf) (*env)->ReleasePrimitiveArrayCritical(env, dst, dstbuf, 0); + if(srcbuf) (*env)->ReleasePrimitiveArrayCritical(env, src, srcbuf, 0); + return; + +} + JNIEXPORT void JNICALL Java_org_libjpegturbo_turbojpeg_TJDecompressor_destroy (JNIEnv *env, jobject obj) { diff --git a/turbojpeg-mapfile.jni b/turbojpeg-mapfile.jni index bf2ce4b..7c930b8 100755 --- a/turbojpeg-mapfile.jni +++ b/turbojpeg-mapfile.jni @@ -14,11 +14,13 @@ Java_org_libjpegturbo_turbojpeg_TJ_bufSize; Java_org_libjpegturbo_turbojpeg_TJ_bufSizeYUV; Java_org_libjpegturbo_turbojpeg_TJCompressor_init; - Java_org_libjpegturbo_turbojpeg_TJCompressor_compress; + Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3BIIII_3BIII; + Java_org_libjpegturbo_turbojpeg_TJCompressor_compress___3IIII_3BIII; Java_org_libjpegturbo_turbojpeg_TJCompressor_destroy; Java_org_libjpegturbo_turbojpeg_TJDecompressor_init; Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompressHeader; - Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress; + Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3BIIIII; + Java_org_libjpegturbo_turbojpeg_TJDecompressor_decompress___3BI_3IIIII; Java_org_libjpegturbo_turbojpeg_TJDecompressor_destroy; Java_org_libjpegturbo_turbojpeg_TJDecompressor_getScaledHeight; Java_org_libjpegturbo_turbojpeg_TJDecompressor_getScaledWidth;