bit-shashank
bit-shashank

Reputation: 921

Saving a buffered image with lose less compression

I have a java program which capture screen shots at a regular interval using java Robot class.But since it takes screen shots very often(~5 sec) it could fill my hard disk very soon. Is there any way through which i could decrease the size of image before saving, but could regenerate the original image without losing the quality.

import java.io.*;
import java.util.*;
import java.awt.*;
import java.io.*;
import java.awt.image.BufferedImage;
import java.awt.*;
import com.mysql.jdbc.exceptions.jdbc4.CommunicationsException;
import java.sql.*;  
import java.util.*;
import javax.imageio.ImageIO;
class wtd
{
public static BufferedImage getImage()throws Exception
       {
            Dimension screenDim = Toolkit.getDefaultToolkit().getScreenSize();
              Robot robot = new Robot();


               BufferedImage image = robot.createScreenCapture(new Rectangle(0, 0, (int) screenDim.getWidth(),(int) screenDim.getHeight()));
               return image;



    }
      public static void main(String args[])throws Exception
    { 
                 long id=0;
                       try{
                           while(true)
                           {
                       BufferedImage originalImage=getImage();

                          ImageIO.write(originalImage, "jpg", new File("D:/"+id+".jpg"));
                                         id++;


                                 }
                   }

               catch(Exception e){}

            }
        }

Upvotes: 1

Views: 503

Answers (2)

davidxxx
davidxxx

Reputation: 131346

If your images are already compressed, using another compression processing will not be very helpful : you will spare space but not necessarily a lot of.

If your images are not or few compressed, you could use classic compression tools as zip that allows lossless data compression.
You have multiple level of compression but more the level of compression is high, more the processing time is long.
So according to the cpu power, the available cpu thread number and the size of your images, you should use a level more or less important of compression.

For example the java.util.zip.ZipOutputStream class allows to create a zip with a specific level of compression by invoking the setLevel(int level) method.
Then you could use the java.util.zip.ZipInputStream class to extract the archive.


Edit for a code example :

Here is a not tested example by using the javax.imageio.ImageIO.write() JDK 8 specific method that allows to write a java.awt.image.BufferedImage into an java.io.OutputStream object:

  // Here is the capture bufferedImage from your application
  BufferedImage screenShot = ...;

  // You create the zip file and you add entry that will store the image
  FileOutputStream fileOut = new FileOutputStream("yourZipFile.zip");
  ZipOutputStream zipOut = new ZipOutputStream(fileOut);
  zipOut.setLevel(9); // 9 is the max level      
  ZipEntry zipEntry = new ZipEntry("screenshot-2017-03-24_12-03-30.jpg");
  zipOut.putNextEntry(zipEntry);

  // you get the bytes from the image 
  ByteArrayOutputStream out = new ByteArrayOutputStream();
  javax.imageio.ImageIO.write(screenShot, "jpg", out);
  byte[] bytes = out.toByteArray();

  // you write the bytes in the zipOutputStream
  zipOut.write(bytes, 0, bytes.length);
  zipOut.close();

Upvotes: 1

acm
acm

Reputation: 2120

If you are looking for lossless compression you can give a try to Lepton which achieves:

a 22% savings reduction for existing JPEG images, by predicting coefficients in JPEG blocks and feeding those predictions as context into an arithmetic coder. Lepton preserves the original file bit-for-bit perfectly. It compresses JPEG files at a rate of 5 megabytes per second and decodes them back to the original bits at 15 megabytes per second, securely, deterministically, and in under 24 megabytes of memory.

Upvotes: 0

Related Questions