0

Background story: Right now I am working on an image encode and decode service. I will attach the service to a sensor (ex. camera) like to compress the image, send it over the network to receive it at the end with a client service, where the image is finaly decompressed and used. For this whole compression/decompression stuff I decided to use libJPEG Turbo, because it is the fastest library that I found.

Problem: In my mind a JPEG file is self describing and it should be possible to read it with every tool. But why I need for the compression and decompression with libJPEG Turbo additionally the pixel format (GRAY, RGB, BGR, RGBX, ...)? How can I extract/decompress the pixel format from the compressed JPEG (Byte Array)?

My code - compression (c++):

tjhandle _jpegCompressor = tjInitCompress();
tjCompress2(_jpegCompressor, buffer, width, 0, height, TJPF_RGB, &_compressedImage, &_jpegSize, TJSAMP_444, JPEG_QUALITY, TJFLAG_FASTDCT);
tjDestroy(_jpegCompressor);

My code - decompression (c++):

int width, height;
tjDecompressHeader(_jpegDecompressor, _compressedImage, _jpegSize, &width, &height);
size_t size = width*height*channels;
unsigned char* buffer = new unsigned char[size];
tjDecompress2(_jpegDecompressor, _compressedImage, _jpegSize, buffer, width, 0, height, TJPF_RGB, TJFLAG_FASTDCT);
tjDestroy(_jpegDecompressor);

Tests: I tested it out and the only importance is that I use for compression and decompression the same pixel format. If I use both times TJPF_BGR (or TJPF_RGB) it works, but if I use for decompression a different pixel format the channels are flipped.

Interestingly If I use the tjDecompress function (not tjDecompress2) I need to compress with TJ_RGB and can decompress with TJ_RGB or TJ_BGR to get a right result... If I start to compress with TJ_BGR the color is flipped at the end. What do I missunderstand?

tjDecompress(_jpegDecompressor, _compressedImage, _jpegSize, buffer, width, 0, height, 3, TJFLAG_FASTDCT);
Mozi
  • 1
  • 1
  • JPEG is normally stored in the YCbCr colorspace. If you're giving the compressor RGB and asking the decompressor for BGR, you'll get what you ask for, but the file itself doesn't tell you what color conversions happened to get it in YCbCr format. – BitBank Nov 30 '17 at 20:26
  • JPEG is normally stored in YCbCr colorspace, but could be in RGB or BGR pixel ordering. Right? how you load a JPEG correctly if you dont know (or can't extract) the pixel ordering (RGB/BGR). – Mozi Dec 01 '17 at 00:48
  • Or wait no.. compressed JPEG does not have anymore a specific pixel ordering - Right? That means for compression I just need to use the default behavior how images are loaded with libJPEG Turbo and for decompression I need to specify the output ordering - Right? – Mozi Dec 01 '17 at 00:59
  • 1
    Adobe created a strange option to store JPEGs in RGB colorspace, but then you can't do color subsampling. JPEGs can also be stored in CMYK colorspace, and again that doesn't allow for subsampling. Normal JPEGs use YCbCb. The RGB/BGR that you're referring to is done by color conversions in the encoder and decoder. If you ask the decoder to give you RGB it will; if you ask it for BGR, it can do that too. This logic is in the decoder because it's converting the colorspace from YCbCr to whatever you ask for. – BitBank Dec 01 '17 at 01:01
  • Alright thank you! But I am talking not about colorspace.. I would like to know what happens with the pixel format in each step! I am still not understanding why I get a flipped image if I first load it with OpenCV (BGR pixel ordering), compress it with libJPEG Turbo with the TJPF_BGR flag and decompress it later with TJ_RGB. I would expect a raw image in RGB pixel ordering as output. Is that true? – Mozi Dec 01 '17 at 20:35
  • I can't comment about those tools; you may have discovered a bug. I wrote my own JPEG codec, so I only can tell you about the standard and how I implemented it. – BitBank Dec 01 '17 at 22:50

0 Answers0