言語:C/C++
ライブラリ:Magick++ (ImageMagick)
Magick++とC++を使うことで、画像のピクセル列にアクセスして値を参照したり書き換えたりできます。他の言語のImageMagickインターフェースでできるかはわかりませんが、ピクセル列の値を書き換えるとかっていかにもC++で画像処理しているっていう感覚で楽しいですし、既存のクラスやメソッドに無い処理を実装する場合には便利ですね。
100×100の青い画像を作成して、画像の左上(全体の1/4)をグラデーションにするプログラムを書いてみました。
#include <Magick++.h>
using namespace std;
using namespace Magick;
int main(int argc,char **argv)
{
const int width = 100;
const int height = 100;
Image image(Geometry(width, height), ColorRGB(0, 0, 1));
image.type(TrueColorType);
image.modifyImage();
Pixels view(image);
PixelPacket* pixels = view.get(0, 0, width / 2, height / 2);
for (int i = 0; i < height / 2; i++) {
for (int j = 0; j < width / 2; j++) {
pixels[i*(width / 2)+j] = ColorRGB(1, 0, (double)j / (double)(width / 2));
}
}
view.sync();
image.write("sample.png");
return 0;
}
using namespace std;
using namespace Magick;
int main(int argc,char **argv)
{
const int width = 100;
const int height = 100;
Image image(Geometry(width, height), ColorRGB(0, 0, 1));
image.type(TrueColorType);
image.modifyImage();
Pixels view(image);
PixelPacket* pixels = view.get(0, 0, width / 2, height / 2);
for (int i = 0; i < height / 2; i++) {
for (int j = 0; j < width / 2; j++) {
pixels[i*(width / 2)+j] = ColorRGB(1, 0, (double)j / (double)(width / 2));
}
}
view.sync();
image.write("sample.png");
return 0;
}
作成した画像からピクセル列を生成するにはMagick::Viewクラスを使います。コンストラクタにMagick::Imageクラスのインスタンスを渡すことで、その画像のピクセル列の領域がメモリに確保されます。
生成したピクセル列からポインタを取得するには、Magick::Viewクラスのget関数を使います。
PixelPacket* Magick::View::get(
const ssize_t x_,
const ssize_t y_,
const ssize_t columns_,
const size_t rows_
)
const ssize_t x_,
const ssize_t y_,
const ssize_t columns_,
const size_t rows_
)
画像中の位置をx_とy_に指定して、x_とy_からの領域の大きさをcolumns_とrows_に指定します。この例では、画像の左上から縦横それぞれ50ピクセル分のピクセル列のポインタを取得しています。
元の画像(Magick::Imageクラスのインスタンス)にピクセル列の内容を反映させたい場合は、Magick::Viewクラスのsync関数を使います。この関数は呼ぶだけです。
最後にMagick::Imageクラスのwrite関数で画像ファイルとして出力しています。以下のような画像になります。