Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members | Related Pages

Representations/Perception/JPEGImage.cpp

Go to the documentation of this file.
00001 /**
00002  * @file JPEGImage.cpp
00003  * 
00004  * Implementation of class JPEGImage
00005  */ 
00006 
00007 #include "Platform/GTAssert.h"
00008 #include "JPEGImage.h"
00009 
00010 JPEGImage::JPEGImage(const Image& image)
00011 {
00012   *this = image;
00013 }
00014 
00015 JPEGImage& JPEGImage::operator=(const Image& src)
00016 {
00017   cameraInfo = src.cameraInfo;
00018   frameNumber = src.frameNumber;
00019 
00020   jpeg_compress_struct cInfo;
00021   jpeg_error_mgr jem;
00022   cInfo.err = jpeg_std_error(&jem);
00023   jpeg_create_compress(&cInfo);
00024 
00025   if(!cInfo.dest)
00026     cInfo.dest = (jpeg_destination_mgr*)
00027       (*cInfo.mem->alloc_small) ((j_common_ptr) &cInfo,JPOOL_PERMANENT,
00028                                  sizeof(DestDescriptor));
00029   cInfo.dest->init_destination = onDestInit;
00030   cInfo.dest->empty_output_buffer = onDestEmpty;
00031   cInfo.dest->term_destination = onDestTerm;
00032   ((DestDescriptor*) cInfo.dest)->theObject = this;
00033 
00034   cInfo.image_width = cameraInfo.resolutionWidth;
00035   cInfo.image_height = cameraInfo.resolutionHeight * 3;
00036   cInfo.input_components = 1;
00037   cInfo.in_color_space = JCS_GRAYSCALE;
00038   jpeg_set_defaults(&cInfo);
00039   cInfo.dct_method = JDCT_FASTEST;
00040   jpeg_set_quality(&cInfo,75,true);
00041 
00042   jpeg_start_compress(&cInfo,true);
00043 
00044   while(cInfo.next_scanline < cInfo.image_height) 
00045   {
00046     JSAMPROW rowPointer = const_cast<JSAMPROW>(&src.image[cInfo.next_scanline % src.cameraInfo.resolutionHeight]
00047                                                          [cInfo.next_scanline / src.cameraInfo.resolutionHeight][0]);
00048     jpeg_write_scanlines(&cInfo,&rowPointer,1);
00049   }
00050 
00051   jpeg_finish_compress(&cInfo);
00052   jpeg_destroy_compress(&cInfo);
00053   return *this;
00054 }
00055 
00056 void JPEGImage::toImage(Image& dest) const
00057 {
00058   dest.cameraInfo = cameraInfo;
00059   dest.frameNumber = frameNumber;
00060 
00061   jpeg_decompress_struct cInfo;
00062   jpeg_error_mgr jem;
00063   cInfo.err = jpeg_std_error(&jem);
00064 
00065   jpeg_create_decompress(&cInfo);
00066 
00067   if(!cInfo.src)
00068     cInfo.src = (jpeg_source_mgr *)
00069       (*cInfo.mem->alloc_small)((j_common_ptr) &cInfo,JPOOL_PERMANENT,
00070                                  sizeof(jpeg_source_mgr));
00071   cInfo.src->init_source       = onSrcIgnore;
00072   cInfo.src->fill_input_buffer = onSrcEmpty;
00073   cInfo.src->skip_input_data   = onSrcSkip;
00074   cInfo.src->resync_to_restart = jpeg_resync_to_restart;
00075   cInfo.src->term_source       = onSrcIgnore;
00076   cInfo.src->bytes_in_buffer = size;
00077   cInfo.src->next_input_byte = (const JOCTET*) image;
00078 
00079   jpeg_read_header(&cInfo,true);
00080   jpeg_start_decompress(&cInfo);
00081 
00082   // setup rows
00083   while (cInfo.output_scanline < cInfo.output_height) 
00084   {
00085     JSAMPROW rowPointer = (unsigned char*) (cInfo.output_height == (unsigned) cameraResolutionHeight_ERS210
00086                           ? &dest.image[cInfo.output_scanline][0][0]
00087                           : &dest.image[cInfo.output_scanline % dest.cameraInfo.resolutionHeight]
00088                                        [cInfo.output_scanline / dest.cameraInfo.resolutionHeight][0]);
00089     (void) jpeg_read_scanlines(&cInfo,&rowPointer,1);
00090   }
00091 
00092   // decompress
00093   jpeg_finish_decompress(&cInfo);
00094   jpeg_destroy_decompress(&cInfo);
00095 
00096   // compatibility with old format: move to correct positions
00097   if(cInfo.output_height == (unsigned) cameraResolutionHeight_ERS210)
00098     for(unsigned i = 0; i < cInfo.output_height; ++i)
00099       for(unsigned c = 2; c > 0; --c)
00100         memmove(&dest.image[i][c][0], 
00101                 &dest.image[i][0][c * cameraResolutionWidth_ERS210], 
00102                 cameraResolutionWidth_ERS210);
00103 
00104   // clear high resolution y channels
00105   for(int y = 0; y < dest.cameraInfo.resolutionHeight; ++y)
00106     for(int c = 3; c < 6; ++c)
00107       memset(&dest.image[y][c][0], 128, dest.cameraInfo.resolutionWidth);
00108 }
00109 
00110 void JPEGImage::onDestInit(j_compress_ptr cInfo)
00111 {
00112   JPEGImage& image = *((DestDescriptor*) cInfo->dest)->theObject;
00113   cInfo->dest->next_output_byte = (JOCTET*) image.image;
00114   cInfo->dest->free_in_buffer = image.cameraInfo.resolutionWidth * image.cameraInfo.resolutionHeight * 3;
00115 }
00116 
00117 int JPEGImage::onDestEmpty(j_compress_ptr)
00118 {
00119   ASSERT(false);
00120   return false;
00121 }
00122 
00123 void JPEGImage::onDestTerm(j_compress_ptr cInfo)
00124 {
00125   JPEGImage& image = *((DestDescriptor*) cInfo->dest)->theObject;
00126   image.size = (char*) cInfo->dest->next_output_byte - (char*) image.image;
00127 }
00128 
00129 void JPEGImage::onSrcSkip(j_decompress_ptr,long)
00130 {
00131 }
00132 
00133 int JPEGImage::onSrcEmpty(j_decompress_ptr)
00134 {
00135   ASSERT(false);
00136   return false;
00137 }
00138 
00139 void JPEGImage::onSrcIgnore(j_decompress_ptr)
00140 {
00141 }
00142 
00143 Out& operator<<(Out& stream,const JPEGImage& image)
00144 {
00145   ASSERT(image.size);
00146   stream << image.cameraInfo.resolutionWidth << image.cameraInfo.resolutionHeight << image.frameNumber << image.size;
00147   stream.write(&image.image,image.size);
00148   return stream;
00149 }
00150 
00151 In& operator>>(In& stream,JPEGImage& image)
00152 {
00153   stream >> image.cameraInfo.resolutionWidth >> image.cameraInfo.resolutionHeight >> image.frameNumber >> image.size;
00154   image.setCameraInfo();
00155   stream.read(&image.image,image.size);
00156   return stream;
00157 }

Generated on Mon Mar 20 22:00:03 2006 for GT2005 by doxygen 1.3.6