24 ビットカラー全パターンの画像を作成するコード

OpenCV に BGR2YIQ が用意されていなくて,手書きしようと思った.MATLAB の rgb2ntsc と一致するかを見るため,全色を 1 ピクセル含む画像が欲しかった.なんとなく見つからなかったから,作ってみた.

  • 0 - 256^3 を 下位から 8 ビットずつ画素値として設定する
  • コマンドラインパラメータには 1 より大きい 256^3 の約数を入れる
    • 256 か 65536 を入れるときれいに見える
  • 出力ファイル名は a.png に固定
  • ファイルサイズは PNG にしているから 8 MB ほどになる
    • BMP にすると 48 MB になる

出力例

フォトライフ上限になった.掲載を凍結する.

3 種類掲載する.いずれも IrfanView で開き,PNGOUT プラグインを使用しての保存によりファイルサイズを圧縮した.

  • 全体俯瞰用.正方形
    • パラメータに 4096 を与えて生成した 4096x4096x3
  • キレーに見える横長
    • パラメータに 256 を与えて生成した 256x65536x3
  • キレーに見える縦長
    • パラメータに 65536 を与えて生成した 65536x256x3

createSampleImage.cpp

#include <stdio.h>
#include <opencv/cv.h>
#include <opencv/highgui.h>

#ifdef _DEBUG
#pragma comment( lib, "cv200d.lib" )
#pragma comment( lib, "cxcore200d.lib" )
#pragma comment( lib, "highgui200d.lib" )
#else
#pragma comment( lib, "cv200.lib" )
#pragma comment( lib, "cxcore200.lib" )
#pragma comment( lib, "highgui200.lib" )
#endif

#define PX(im,x,y,c) im.data[ 3 * x + im.step * y + c]
#define RGBMaskB 0x00ff0000
#define RGBMaskG 0x0000ff00
#define RGBMaskR 0x000000ff

// argv[1] に 256^3 の約数を入れる
// ただし 1 はだめ
int main ( int argc, char *argv[] )
{
	// argv[1] チェック
	if ( argc < 2 )
	{
		// パラメータがないとき終了
		return 0;
	}
	int outrow = atoi(argv[1]);
	int numofColorPattern = 256*256*256;
	if ( outrow < 2 )
	{
		// パラメータが負の数のとき,0 のとき,1 のとき終了
		return 0;
	}
	if ( numofColorPattern%outrow != 0 )
	{
		// パラメータが 256^3 の約数でないとき終了
		return 0;
	}

	// バッファ
	cv::Mat work( 1, 256*256*256, CV_8UC3 );
	
	// 画像作成
	int b, g, r;
	for ( int bgr = 0; bgr < work.cols; bgr++ )
	{
		b = ( bgr & RGBMaskB ) >> 16;
		g = ( bgr & RGBMaskG ) >>  8;
		r = ( bgr & RGBMaskR )      ;
		PX( work, bgr, 0, 0) = cv::saturate_cast<uchar>(b);
		PX( work, bgr, 0, 1) = cv::saturate_cast<uchar>(g);
		PX( work, bgr, 0, 2) = cv::saturate_cast<uchar>(r);
	}

	// 出力用画像作成
	cv::Mat still;
	still = work.reshape( 0, outrow );
	cv::imwrite( "a.png", still );

	return 0;
}