0

i resize a Bitmapfile using opencv (android-jni) and save the out bitmap to a file named /mnt/sdcard/org.jpg

then use

resultBitmap = BitmapFactory.decodeFile("/mnt/sdcard/org.jpg"); 

to get the bitmap and re-save this resultBitmap to the file /mnt/sdcard/result.jpg

then the org.jpg size is 100k and the result.jpg size is about 300k

why?

my resize method use opencv in jni like this:

int FUN_ENTRY JNICALL Java_com_funlib_imagefilter_ImageUtily_nativeResizeBitmap(    
                                                                                JNIEnv* env, jobject obj , jstring srcPath , jstring destPath,  int w , int h , int quality)
{
    char* srcPath1 = jstringTostring(env , srcPath);
    IplImage *src = cvLoadImage(srcPath1,CV_LOAD_IMAGE_ANYDEPTH | CV_LOAD_IMAGE_ANYCOLOR);
    if(srcPath1!=NULL)
    {
        free(srcPath1);
        srcPath1 = NULL;
    }
    if(src==NULL)
    {
        return -1;
    }

    CvSize sz;
    double rate1 = ((double) src->width) / (double) w + 0.1; 
    double rate2 = ((double) src->height) / (double) h + 0.1; 

    double rate = rate1 > rate2 ? rate1 : rate2; 
    sz.width = (int) (((double) src->width) / rate); 
    sz.height = (int) (((double) src->height) / rate); 
    IplImage *desc = cvCreateImage(sz,src->depth,src->nChannels);
    if(desc==NULL)
    {
        cvReleaseImage(&src);
        return -1;
    }
    cvResize(src,desc,CV_INTER_CUBIC);
    if(desc==NULL)
    {
        cvReleaseImage(&src);
        return -1;
    }
    char* destPath1 = jstringTostring(env , destPath);

    int p[3];
    p[0] = CV_IMWRITE_JPEG_QUALITY;
    p[1] = quality;
    p[2] = 0;

    cvSaveImage(destPath1 , desc , p);
    cvReleaseImage(&src);
    cvReleaseImage(&desc);
    if(destPath1!=NULL)
    {
        free(destPath1);
        destPath1 = NULL;
    }

    return 0;
}

and my main is

File f = new File(filePath);
    String tmpDestPath = f.getParent();
    if(!tmpDestPath.endsWith(File.separator))
        tmpDestPath += File.separator;
    tmpDestPath += "org.jpg";
    int ret = nativeResizeBitmap(filePath, tmpDestPath, width, height , quality);         //get the org.jpg file
    Bitmap bmp = null;
    if(ret == 0){
        bmp = BitmapFactory.decodeFile(tmpDestPath);
    }

    try {
        ImageUtily.saveBitmapToFile("result", bmp);  //get the result.jpg file
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

my saveBitmapToFile is

    public static void saveBitmapToFile(String fileName, Bitmap bmp) throws IOException
{
    File f = new File("/sdcard/DCIM/TEMP/" + fileName + ".jpg");
    f.createNewFile();
    FileOutputStream fOut = null;
    try {
        fOut = new FileOutputStream(f);
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    }

    bmp.compress(Bitmap.CompressFormat.JPEG, 100, fOut);
    try {
        fOut.flush();
    } catch (IOException e) {
        e.printStackTrace();
    }
    try {
        fOut.close();
    } catch (IOException e) {
        e.printStackTrace();
    }
}
Ray
  • 468
  • 4
  • 17
  • 3
    try dialing down your `quality` parameter in `bmp.compress(Bitmap.CompressFormat.JPEG, 100, fOut);` from `100` to something lower. 100 = max quality which isn't going to give you small JPEG images. – Jens May 11 '12 at 07:08

1 Answers1

0

I don't know OpenCV / Android-JNI, so I can just try to give you a hint.

I suppose the function saveBitmapToFile does what it says on the tin: save a bitmap (as in BMP file format) as it is. You would need to compress your bmp first, maybe this could point you in the right direction.

As to why the new file is bigger: if you really want to know (and are not just interested in how to fix it), fire up a Hex editor of your choice and take a look at the file header. Bitmap uses various bit depths and compressions which may have been changed during the process.

Community
  • 1
  • 1
Daerst
  • 954
  • 7
  • 24
  • You may save a ARGB_8888 Bitmap, which is default and at least recommended I think (check Bitmap.Config). If your origin bmp is an RGB_565, it is half size because ARGB_8888 = 32 bit, RGB_565 = 16 bit. – sschrass May 11 '12 at 06:27