0

I have an grayscale image with dimension 256*256.I am trying to downscale it to 128*128. I am taking an average of two pixel and writing it to the ouput file.

class Start {

 public static void main (String [] args) throws IOException {

 File input= new File("E:\\input.raw");

 File output= new  File("E:\\output.raw");
 new Start().resizeImage(input,output,2);

 }



 public  void resizeImage(File input, File output, int downScaleFactor) throws IOException {
          byte[] fileContent= Files.readAllBytes(input.toPath());
          FileOutputStream  stream= new FileOutputStream(output);
          int i=0;
          int j=1;
          int result=0;
          for(;i<fileContent.length;i++)
          {
                if(j>1){
                    // skip the records.
                    j--;
                    continue;
                }
                else { 
                    result = fileContent[i];
                    for (; j < downScaleFactor; j++) {
                        result =  ((result + fileContent[i + j]) / 2);
                    }
                    j++;
                    stream.write( fileContent[i]);
                }
          }
        stream.close();
      }

}

Above code run successfully , I can see the size of output file size is decreased but when I try to convert output file (raw file) to jpg online (https://www.iloveimg.com/convert-to-jpg/raw-to-jpg) it is giving me an error saying that file is corrupt. I have converted input file from same online tool it is working perfectly. Something is wrong with my code which is creating corrupt file. How can I correct it ?

P.S I can not use any library which directly downscale an image .

sar
  • 1,277
  • 3
  • 21
  • 48
  • 1
    I would recommend having a look at [this question](https://stackoverflow.com/questions/14115950/quality-of-image-after-resize-very-low-java) for a discussion on down scaling images and maintaining quality. Because the accept answer uses a third party library, I'd also recommend having a look at [this answer](https://stackoverflow.com/questions/11959758/java-maintaining-aspect-ratio-of-jpanel-background-image/11959928#11959928) which discusses using a divide and conquer approach to scaling images using the library functionality found in Java itself – MadProgrammer Sep 29 '17 at 01:01
  • The online tool you are linking converts ["Camera RAW"](https://en.wikipedia.org/wiki/Raw_image_format) files to JPEG. These kinds of files are not "raw" pixel data, they conform to a file format (typically TIFF/Exif based), contain multiple images in different compression/resolutions, thumbnails etc. along with the "raw" sensor data (which is typically JPEG lossless compressed). Your code assumes the file contains raw pixel data, and corrupts the camera RAW files in the process. See [this answer](https://stackoverflow.com/q/1222324/1428606) for some input on how to read them... – Harald K Oct 11 '17 at 10:03

1 Answers1

0

Your code is not handling image resizing.

See how-to-resize-images-in-java.

Which, i am copying a simple version here:

import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;

public class ImageResizer {

    public static void resize(String inputImagePath,
            String outputImagePath, int scaledWidth, int scaledHeight)
            throws IOException {
        // reads input image
        File inputFile = new File(inputImagePath);
        BufferedImage inputImage = ImageIO.read(inputFile);

        // creates output image
        BufferedImage outputImage = new BufferedImage(scaledWidth,
                scaledHeight, inputImage.getType());

        // scales the input image to the output image
        Graphics2D g2d = outputImage.createGraphics();
        g2d.drawImage(inputImage, 0, 0, scaledWidth, scaledHeight, null);
        g2d.dispose();

        // extracts extension of output file
        String formatName = outputImagePath.substring(outputImagePath
                .lastIndexOf(".") + 1);

        // writes to output file
        ImageIO.write(outputImage, formatName, new File(outputImagePath));
    }

    public static void resize(String inputImagePath,
            String outputImagePath, double percent) throws IOException {
        File inputFile = new File(inputImagePath);
        BufferedImage inputImage = ImageIO.read(inputFile);
        int scaledWidth = (int) (inputImage.getWidth() * percent);
        int scaledHeight = (int) (inputImage.getHeight() * percent);
        resize(inputImagePath, outputImagePath, scaledWidth, scaledHeight);
    }

    public static void main(String[] args) {
        String inputImagePath = "resources/snoopy.jpg";
        String outputImagePath1 = "target/Puppy_Fixed.jpg";
        String outputImagePath2 = "target/Puppy_Smaller.jpg";
        String outputImagePath3 = "target/Puppy_Bigger.jpg";

        try {
            // resize to a fixed width (not proportional)
            int scaledWidth = 1024;
            int scaledHeight = 768;
            ImageResizer.resize(inputImagePath, outputImagePath1, scaledWidth, scaledHeight);

            // resize smaller by 50%
            double percent = 0.5;
            ImageResizer.resize(inputImagePath, outputImagePath2, percent);

            // resize bigger by 50%
            percent = 1.5;
            ImageResizer.resize(inputImagePath, outputImagePath3, percent);

        } catch (IOException ex) {
            System.out.println("Error resizing the image.");
            ex.printStackTrace();
        }
    }

}
Nicolas Modrzyk
  • 13,961
  • 2
  • 36
  • 40
  • 1
    Java's scaling is notoriously low quality, which be improved by using a divide and conquer approach, demonstrated [here](https://stackoverflow.com/questions/11959758/java-maintaining-aspect-ratio-of-jpanel-background-image/11959928#11959928) – MadProgrammer Sep 29 '17 at 00:59