c++ - How to Decode JPEG Using Win32? -




i have chunk of memory containing raw bytes of jpeg , convert 24-bit rgb can render using stretchdibits. i've looked around msdn jeez... don't want use third party libraries or c++ if don't have to. suggestions? wish there function decodejpeg() or something...

i came solution uses wic, doesn't seem use c++, wasn't able following code compile c, not sure. took lot of time put pieces together, here is!

#include <wincodec.h> #include <stdio.h>  #pragma comment(lib, "ole32.lib") #pragma comment(lib, "windowscodecs.lib")  #define min(a, b) (a < b ? : b)  void win32decodejpeg(unsigned int imagedatasize, void *imagedata,                  unsigned int destsize, void *dest) {     static iwicimagingfactory *iwicfactory;     if(iwicfactory == null)     {         coinitializeex(null, coinit_multithreaded);         cocreateinstance(clsid_wicimagingfactory, nullptr, clsctx_inproc_server, iid_ppv_args(&iwicfactory));     }      iwicstream *stream;     iwicfactory->createstream(&stream);     stream->initializefrommemory((unsigned char *)imagedata, imagedatasize);      iwicbitmapdecoder *bitmapdecoder;     iwicfactory->createdecoderfromstream(stream, null, wicdecodemetadatacacheondemand, &bitmapdecoder);      iwicbitmapframedecode *framedecode;     bitmapdecoder->getframe(0, &framedecode);      iwicformatconverter *formatconverter;     iwicfactory->createformatconverter(&formatconverter);      formatconverter->initialize(framedecode,                                 guid_wicpixelformat24bppbgr,                                 wicbitmapdithertypenone,                                 nullptr,                                 0.0f,                                 wicbitmappalettetypecustom);      iwicbitmap *bitmap;     iwicfactory->createbitmapfromsource(formatconverter, wicbitmapcacheondemand, &bitmap);      unsigned int width, height;     bitmap->getsize(&width, &height);     wicrect rect = {0, 0, (int)width, (int)height};      iwicbitmaplock *lock;     bitmap->lock(&rect, wicbitmaplockread, &lock);      unsigned int pixeldatasize = 0;     unsigned char *pixeldata;     lock->getdatapointer(&pixeldatasize, &pixeldata);      memcpy(dest, pixeldata, min(destsize, pixeldatasize));      stream->release();     bitmapdecoder->release();     framedecode->release();     formatconverter->release();     bitmap->release();     lock->release(); }  int main() {     int imagewidth = 640;     int imageheight = 480;      int decodedbuffersize = imagewidth * imageheight * 3;     void *decodedbuffer = malloc(decodedbuffersize);      file *imagefile = fopen("test.jpg", "rb");      fseek(imagefile, 0, seek_end);     int imagesize = ftell(imagefile);     rewind(imagefile);      void *imagedata = malloc(imagesize);     fread(imagedata, 1, imagesize, imagefile);      fclose(imagefile);      win32decodejpeg(imagesize, imagedata, decodedbuffersize, decodedbuffer); } 

edit: popular demand, here's version basic error checking , rudimentary explanations:

#include <wincodec.h> #include <stdio.h>  #pragma comment(lib, "ole32.lib") #pragma comment(lib, "windowscodecs.lib")  void win32decodejpeg(unsigned int imagedatasize, void *imagedata,                  unsigned int destsize, void *dest) {     // iwicimagingfactory structure containing function pointers of wic api     static iwicimagingfactory *iwicfactory;     if(iwicfactory == null)     {         if(coinitializeex(null, coinit_multithreaded) != s_ok)         {             printf("failed initialize com library\n");             return;         }          if(cocreateinstance(clsid_wicimagingfactory, nullptr, clsctx_inproc_server, iid_ppv_args(&iwicfactory)) != s_ok)         {             printf("failed create instance of wic\n");             return;         }     }      iwicstream *stream;     if(iwicfactory->createstream(&stream) != s_ok)     {         printf("failed create stream\n");         return;     }      if(stream->initializefrommemory((unsigned char *)imagedata, imagedatasize) != s_ok)     {         printf("failed initialize stream memory\n");         return;     }      iwicbitmapdecoder *bitmapdecoder;     if(iwicfactory->createdecoderfromstream(stream, null, wicdecodemetadatacacheondemand, &bitmapdecoder) != s_ok)     {         printf("failed create bitmap decoder stream\n");         return;     }      iwicbitmapframedecode *framedecode;     // frames apply gifs , other animated media. jpegs have single frame.     if(bitmapdecoder->getframe(0, &framedecode) != s_ok)     {         printf("failed 0th frame frame decoder\n");         return;     }      iwicformatconverter *formatconverter;     if(iwicfactory->createformatconverter(&formatconverter) != s_ok)     {         printf("failed create format converter\n");         return;     }      // function not actual decoding     if(formatconverter->initialize(framedecode,                                    guid_wicpixelformat24bppbgr,                                    wicbitmapdithertypenone,                                    nullptr,                                    0.0f,                                    wicbitmappalettetypecustom) != s_ok)     {         printf("failed initialize format converter\n");         return;     }      iwicbitmap *bitmap;     if(iwicfactory->createbitmapfromsource(formatconverter, wicbitmapcacheondemand, &bitmap) != s_ok)     {         printf("failed create bitmap format converter\n");         return;     }      unsigned int width, height;     if(bitmap->getsize(&width, &height) != s_ok)     {         printf("failed size of bitmap\n");         return;     }     wicrect rect = {0, 0, (int)width, (int)height};      iwicbitmaplock *lock;     // function actual decoding. seems defer decoding until it's needed     if(bitmap->lock(&rect, wicbitmaplockread, &lock) != s_ok)     {         printf("failed lock bitmap\n");         return;     }      unsigned int pixeldatasize = 0;     unsigned char *pixeldata;     if(lock->getdatapointer(&pixeldatasize, &pixeldata) != s_ok)     {         printf("failed data pointer\n");         return;     }      memcpy(dest, pixeldata, destsize < pixeldatasize ? destsize : pixeldatasize);      stream->release();     bitmapdecoder->release();     framedecode->release();     formatconverter->release();     bitmap->release();     lock->release(); }  int main() {     int imagewidth = 640;     int imageheight = 480;      int decodedbuffersize = imagewidth * imageheight * 3;     void *decodedbuffer = malloc(decodedbuffersize);      file *imagefile = fopen("test.jpg", "rb");      fseek(imagefile, 0, seek_end);     int imagesize = ftell(imagefile);     rewind(imagefile);      void *imagedata = malloc(imagesize);     fread(imagedata, 1, imagesize, imagefile);      fclose(imagefile);      win32decodejpeg(imagesize, imagedata, decodedbuffersize, decodedbuffer); } 




wiki

Comments

Popular posts from this blog

elasticsearch - what is the equivalent data type for geo_point in hibernate search? -

Jenkins: find build number for git commit -

firebase - How to wait value in Ionic 2 -