C++プログラミングで、画像処理をする時に使う、GDI+。
きっと今ではもっといい方法、あるのかもしれないけれど、昔ながらのプログラミングでやっていると、これしかない。
// PNG 形式のイメージ (BPP = 32ビット) を構築 //
Gdiplus::Bitmap sImagePNG(width , height , PixelFormat32bppARGB) ;
ファイルを保存する時に、
" image/png"
みたいな、固有の文字列を使用しなければならない。
これ、調べて直接指定してもいいけれど、それはアマチュアレベル。
仕様が変更されてもいいように、システムから取り出す方がいい。
MSDNでサンプルがある。
その改良版。
// GDI+ で対応可能な拡張子の情報を検索 //
// ※ pResultFormat : CLSID用フォーマット文字列 "image/***" //
// ※ pResultClsid : CLSID //
// ※ pResultDescription : "JPEG" , "BMP" などの表題 //
BOOL FindEncoderClsidByExt(const CString& strEXT , CString* pResultFormat , CLSID* pResultClsid , CString* pResultDescription)
{
/************************************************************************
CodecName , FilenameExtension , FormatDescription , MimeType
[0]. Built-in BMP Codec , *.BMP;*.DIB;*.RLE , BMP , image/bmp
[1]. Built-in JPEG Codec , *.JPG;*.JPEG;*.JPE;*.JFIF , JPEG , image/jpeg
[2]. Built-in GIF Codec , *.GIF , GIF , image/gif
[3]. Built-in TIFF Codec , *.TIF;*.TIFF , TIFF , image/tiff
[4]. Built-in PNG Codec , *.PNG , PNG , image/png
**********************************************************************/
UINT num ; // number of image encoders
UINT size ; // size, in bytes, of the image encoder array
// 1. 初期設定 //
BOOL bFound = FALSE ;
// 2. 定数情報を読み取り //
// (1). 読み取る情報のサイズを取得 //
// How many encoders are there?
// How big (in bytes) is the array of all ImageCodecInfo objects?
GetImageEncodersSize(&num , &size) ;
// (2). サイズ確保 //
// Create a buffer large enough to hold the array of ImageCodecInfo
// objects that will be returned by GetImageEncoders.
ImageCodecInfo* pImageCodecInfo = (ImageCodecInfo*)(malloc(size)) ;
// (3). 実際に読み取り //
// GetImageEncoders creates an array of ImageCodecInfo objects
// and copies that array into a previously allocated buffer.
// The third argument, imageCodecInfo, is a pointer to that buffer.
GetImageEncoders(num , size , pImageCodecInfo) ;
// 3. 拡張子による検索 //
// Display the graphics file format (MimeType)
// for each ImageCodecInfo object.
for(UINT j = 0 ; j < num ; ++j)
{
// (1). 拡張子の連結を取得 : "*.BMP;*.DIB;*.RLE" //
LPCTSTR lpszEnumEXT = pImageCodecInfo[j].FilenameExtension ;
// (2). 拡張子の連結 "*.BMP;*.DIB;*.RLE" に指定された拡張子が含まれるか //
BOOL bResult = CheckEnumEXT(strEXT , lpszEnumEXT) ;
// (3). 存在しなかった場合 //
if ( ! bResult ) continue ;
// (4). 結果 //
// ※ pResultFormat : CLSID用フォーマット文字列 "image/***" //
if (pResultFormat) pResultFormat->Format(_T("%s") , pImageCodecInfo[j].MimeType) ;
// ※ pResultClsid : CLSID //
if (pResultClsid) *pResultClsid = pImageCodecInfo[j].Clsid ;
// ※ pResultDescription : "JPEG" , "BMP" などの表題 //
if (pResultDescription) pResultDescription->Format(_T("%s") , pImageCodecInfo[j].FormatDescription) ;
// (5). 終了 //
bFound = TRUE ;
break ;
}
// 3. メモリ解放 //
::free(pImageCodecInfo) ;
return bFound ;
}
/////////////////////////////////////////////////////////////////////
// 拡張子の連結 "*.BMP;*.DIB;*.RLE" に指定された拡張子が含まれるか //
BOOL CheckEnumEXT(const CString& strEXT , LPCTSTR lpszEnumEXT)
{
CString strFind ;
// 1. CString 型 //
// (1). 拡張子の連結を取得 : "*.BMP;*.DIB;*.RLE" //
CString strEnumExt(lpszEnumEXT);
// (2). 最後に ";" を追加 //
strEnumExt += _T(";") ;
// (3). 検索する文字列 //
strFind.Format(_T("*.%s;") , strEXT) ;
strFind.MakeUpper() ;
// 2. 検索 //
int nPos = strEnumExt.Find(strFind , 0) ;
// 3. 結果 //
// (1). 存在しなかった場合 //
if (nPos < 0) return FALSE ;
return TRUE ;
}
こんな感じで、拡張子を大文字で指定するだけで、固有のフォーマットなどを取り出すようにしている。
MSDNでも、検索すると、出てくる。


