3 Replies Latest reply on Nov 28, 2011 4:43 PM by Maxideon

    int array to byte array conversion


      My problem is very similar to the below post.

      CMYK to RGB conversion with icc profile. Output is too dark

      The only difference is i try to get the pixels of a normal jpeg or bitmap file (using PixelGrabber which returns an int array), and then am trying to send the pixels over a network as byte array (after conversion of int array to byte array using Integer.valueof(intvalue).byteValue() for each integer pixel data).

      I use TYPE_INT_RGB color coding for all the image operations, and i intend to have 8-bit RGB color coding on the other side of the network.

      Then i try to read the same image as binary data from network and am using MemoryImageSource to reconstruct the image (again in default RGB color coding), which i could do it successfully, but the resultant image is blurd similar to the lines of the above thread link, although in my case its not black.

      I suppose the blurdness is because, when i convert the integer array to byte array, i lose the 3 byte data in MSB of integer and only one LSB byte data is used for transmission. Am i correct? If it is, how do i achieve the conversion? Or is there any way to get the pixel data as byte array directly instead of using PixelGrabber? Kindly do also note that i had to display the image from the image pixel byte array data received.

      Any help is appreciated.

        • 1. Re: int array to byte array conversion
          There are several things you seem to be doing wrong.

          The PixelGrabber class is used to retrieve pixel information from Toolkit images, since the Image class doesn't have any convenient way to obtain rgb information. A BufferedImage, on the other hand, has about 4 ways you can retrieve pixel information depending on how low level you want to go. One of those ways is to simply call BufferedImage#getRGB. No PixelGrabber needed.

          The second thing you're doing wrong is turning an int[] array into a byte[] array by casting the ints into bytes. Each byte in the int represents a color - alpha, red, green, or blue. By casting you loose all the but the blue component. What you need to do is make the byte[] array 3 or 4 times the size of the int[] array. Then store the lowest 3 bytes or all 4 bytes of each int into the byte array using whatever endian you want. I'm sure if you poke around the java api, you can find classes that do exactly this for you. In fact, if you wrap your network stream using DataOutpustStream and DataInputStream then...

          The third thing you seem to be doing wrong is trying to send raw images over a network. Images can very quickly get to be 100's of KB to MB in size. Compare your current method to compressing the image first (ImageIO#write + ByteArrayOutputStream), sending the compressed data, and then turning it back into a java Image (ImageIO#read + ByteArrayInputStream or Toolkit). You spend time compressing/decompressing the image, but you'll probably spend a lot less time sending much less data over the network.
          1 person found this helpful
          • 2. Re: int array to byte array conversion
            Thanks for your reply.

            There are a couple of things that i missed or misquoted in my question.

            First, I shouldn't have said network, as am accessing a custom made hardware device using USB protocol. Second, as my hardware device has very stringent memory requirements, I thought the conversion of individual elements in integer array to byte value would help me. And third, as the destination is a hardware device, am not sure whether decompression will be supported by the hardware, and for the purpose of making the number of bytes to be transferred, a constant, i chose to send the pixel data, instead of the byte data i get from

            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            ImageIO.write(image, format, baos);

            I were sure I were losing information by converting integer to byte, but weren't sure what information i were losing. Will try sending all the pixel information, so as to make the number of bytes to be transferred a constant, or if its too huge, will try to send the byte array constructed from the above code snippet itself.

            Anyways, thanks for your reply.

            • 3. Re: int array to byte array conversion
              I hear there's a complicated way you can get the JPEGImageWriter that comes with java to essentially 'set' the file size of the output. So you can take any java image you want and turn it into a jpg file of exactly the size you specify. Of course, the lower the file size the more information you loose.

              However, if compressing/decompressing using the png or jpg format is out of the question (since it's not constant and the other side may not have a means to decode it), but you still need some sort of byte reduction, then consider drawing the image on a TYPE_USHORT_565_RGB BufferedImage. Then send the resulting short[] array
              short[] toSend = ((DataBufferUShort) bufferedImage.getRaster().getDataBuffer()).getData();
              The 565 image uses 5 bits for the red, 6 bits for the green, and 5 bits for the blue. That is, you're turning your image into a 16 bit color image. The change is visually negligible and the number of bytes to be transferred will still be constant. This is the most compression you're going to get without using ImageIO or writing your own stuff on the other end.