代码之家  ›  专栏  ›  技术社区  ›  Peter

是否正确更换Sun internal com.Sun.image.codec.jpeg软件包?

  •  4
  • Peter  · 技术社区  · 16 年前

    我们有一些代码使用这个旧的内部Sun包来处理图像,基本上是在从输入流读入/解码后将JPEG编码为特定大小和质量。下面是代码示例。我希望您能提供一个使用适当java.*或javax.*API的最佳实践替换示例。

    private void encodeJPEG(BufferedImage bi, BufferedOutputStream out, float quality) throws
      ImageFormatException, IOException {
     JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
     JPEGEncodeParam param = encoder.getDefaultJPEGEncodeParam(bi);
     param.setQuality(quality, false);
     param.setDensityUnit(DENSITY_UNIT);
     param.setXDensity(DENSITY);
     param.setYDensity(DENSITY);
     encoder.setJPEGEncodeParam(param);
     encoder.encode(bi);
    }
    
    
    private void initJPEG(File jpegFile) throws FileNotFoundException, IOException,
      IOException {
    FileInputStream inputStream = new FileInputStream(jpegFile);
    try {
      JPEGImageDecoder decoder = JPEGCodec.createJPEGDecoder(inputStream);
      buffImage = decoder.decodeAsBufferedImage();
    }
    .....error handling.....
    

    }

    2 回复  |  直到 16 年前
        1
  •  2
  •   Vineet Reynolds    16 年前

    我还没有尝试过这种方法,但是你可以看看 Java Image I/O API . 这个 JPEGImageWriteParam class

        2
  •  1
  •   sja    10 年前

    我也有同样的问题,我做了一些测试,用JPEG编解码器、ImageIO(不带参数)、ImageIO(带参数)来测量编码和写入文件的差异。

        int numTest = 200;
        Robot robot = new Robot();
        BufferedImage image = robot.createScreenCapture(new Rectangle(Toolkit.getDefaultToolkit().getScreenSize()));
    
        //JPEGCODEC
        long t1 = System.currentTimeMillis();
        ByteArrayOutputStream ba = new ByteArrayOutputStream();
        JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(ba);
        JPEGEncodeParam param = encoder.getDefaultJPEGEncodeParam(image);
        param.setQuality(0.75f, false);
        encoder.setJPEGEncodeParam(param);
    
        File f = new File("TestJPEGCODEC");
        f.mkdir();
        for (int i = 0; i < numTest; i++) {
            encoder.encode(image);
            f = new File("TestJPEGCODEC\\test" + i + ".jpg");
            FileOutputStream fo = new FileOutputStream(f);
            fo.write(ba.toByteArray());
            fo.flush();
            ba.reset();
    
        }
        long t2 = System.currentTimeMillis();
        System.out.println("JPEGCODEC");
        System.out.println("Total time:: " + (t2 - t1) + " average time:: " + (t2 - t1) / numTest);
    
        //NORMAL IMAGEIO
        t1 = System.currentTimeMillis();
        f = new File("TestImageIO");
        f.mkdir();
        for (int i = 0; i < numTest; i++) {
            f = new File("TestImageIO\\test" + i + ".jpg");
            ImageIO.write(image, "jpg", f);
        }
        t2 = System.currentTimeMillis();
        System.out.println("ImageIO");
        System.out.println("Total time:: " + (t2 - t1) + " average time:: " + (t2 - t1) / numTest);
    
        Iterator<ImageWriter> it = ImageIO.getImageWritersByFormatName("jpg");
        ImageWriter writer = null;
        while (it.hasNext()) {
            writer = it.next();
        }
        //IMAGEIO EXPLICIT MODE
        t1 = System.currentTimeMillis();
        ImageWriteParam par = writer.getDefaultWriteParam();
        par.setCompressionMode(ImageWriteParam.MODE_EXPLICIT);
        par.setCompressionQuality(0.75f);
    
        f = new File("TestImageIOExplicity");
        f.mkdir();
        for (int i = 0; i < numTest; i++) {
            f = new File("TestImageIOExplicity\\test" + i + ".jpg");
            FileImageOutputStream output = new FileImageOutputStream(f);
            writer.setOutput(output);
            IIOImage img = new IIOImage(image, null, null);
            writer.write(null, img, par);
            output.close();
        }
    
        t2 = System.currentTimeMillis();
        writer.dispose();
        System.out.println("IMAGEIOPAR");
        System.out.println("Total time:: " + (t2 - t1) + " average time:: " + (t2 - t1) / numTest);
    

    对于上面的代码,我的测试结果如下(毫秒)。

    JPEGCODEC 
    Total time:: 13750 average time:: 68
    ImageIO
    Total time:: 38906 average time:: 194
    IMAGEIOPAR
    Total time:: 43078 average time:: 215
    

    我知道我不应该使用com.sun.image.codec.jpeg.jpeg编解码器,但是由于这种结果,它使得使用ImageIO编码/写入jpg变得难以忍受。在我当前的项目中,平均编码和写入的差异非常大,我必须使用jpeg编解码器,或者使用另一个外部库来达到同样的效果。