2016-04-22 16 views
1

Ich versuche ein Farbbild in ein Graustufenbild zu konvertieren und es als BYTE-Werte in einem 2D-Array zu speichern und später muss ich etwas an diesem 2D-Array machen. Obwohl die Werte meines Arrays alle Bytes sind, wird mein Ausgabebild blau statt grau. Kann mir bitte jemand helfen? Hier ist mein Code:Wie konvertiert man Int RGB in BYTE 2D-Array Graues Bild

public class HW { 

public static void main(String[] args) { 
    int[][] savedImage = readimage(new File("C:\\Images\\input.jpg")); 

    BufferedImage grayImage = new BufferedImage(savedImage.length, savedImage[0].length, BufferedImage.TYPE_INT_RGB); 

    for (int i =0 ; i<savedImage.length ; i ++){ 
     for (int j=0 ; j<savedImage[0].length ; j++){ 
      grayImage.setRGB(i, j, savedImage[i][j]); 
      System.out.print(savedImage[i][j] + ","); 
     } 
     System.out.println(); 
    } 

    try { 
     File outputfile = new File ("C:\\Images\\garyoutput.jpg"); 
     ImageIO.write(grayImage, "jpg", outputfile); 
    } 
    catch(IOException e) { 
     e.printStackTrace(); 
    } 
} 

public static int[][] readimage(File filename) throws IOException { 
    // Grayscale Image output 
    BufferedImage img = ImageIO.read(filename); 

    int width = img.getWidth(); 
    int height = img.getHeight(); 
    int [][] readimageVal = new int [width][height]; 

    for (int i = 0; i<height ; i++) { 
     for (int j =0 ; j<width ; j++) { 
      int p = img.getRGB(j,i); 

      int r = (p>>16)&0xff; 
      int g = (p>>8)&0xff; 
      int b = p&0xff; 

      int avg = ((r+b+g)/3); 

      readimageVal[j][i] = avg; 
     } 
    } 
    return readimageVal; 
} 

}

+0

Sie haben den falschen Pixel/Byte-Typ eingestellt. Verwenden Sie 'new BufferedImage (savedImage.length, savedImage [0] .length, BufferedImage.TYPE_USHORT_GRAY);' – JayC667

Antwort

2

Das Problem ist in den Haupt verschachtelten Schleifen im main Methode:

for (int i =0 ; i<savedImage.length ; i ++){ 
    for (int j=0 ; j<savedImage[0].length ; j++){ 
      grayImage.setRGB(i, j, savedImage[i][j]);//← Here 
     System.out.print(savedImage[i][j] + ","); 
    } 
} 

int[][] savedImage enthält einen Byte den Grauwert darstellt, aber grayImage ist noch Typ BufferedImage.TYPE_INT_RGB. Also, wenn Sie nur grayImage.setRGB(i, j, savedImage[i][j]) nennen, nur der blaue Teil des int wird gesetzt:

RRRRRRRR GGGGGGGG BBBBBBBB 
00000000 00000000 xxxxxxxx 

So müssen Sie dies stattdessen nennen:

int rgb = savedImage[i][j]; 
rgb = (rgb<<16)|(rgb<<8)|(rgb); 
grayImage.setRGB(i, j, rgb); 
+0

Es funktioniert jetzt einwandfrei. Ich danke dir sehr. – Nazi

1

Sie haben verschiedene Möglichkeiten, es zu tun, aber erste, hier ist ein einfacher Weg, um die Pixel zuzugreifen:

public static int[][] readimage(File filename) throws IOException { 
    BufferedImage img = ImageIO.read(filename) ;// Grayscale Image output 
    final int width = img.getWidth() ; 
    final int height = img.getHeight() ; 
    int[][] graylevelarray = new int[height][width] ; 

    for (int y=0 ; y < height ; y++) 
     for (int x=0 ; x < width ; x++) { 
      int r = img.getRaster().getSample(x, y, 0) ; 
      int g = img.getRaster().getSample(x, y, 1) ; 
      int b = img.getRaster().getSample(x, y, 2) ; 
      graylevelarray[y][x] = ??? ; 
      } 

    return graylevelarray ; 
    } 

Wie gesagt, für die Umwandlung, haben Sie viele verschiedene Möglichkeiten:

  • Ein Durchschnitt wie Sie, aber es wird selten verwendet.
  • CIE 601 (0,299 * R + 0,587 * G + 0,114 * B) oder CIE 709 (0,2125 * R + 0,7154 * G + 0,0721 * B) empfohlen, am häufigsten verwendet.
  • Billig/schnell grün (R + 2 * G + B)/4, das ist schneller, zum Beispiel in der Bibliothek Zxing verwendet.