PNMはPortable Any Mapの略で、以下の3つの画像フォーマットに対する総称のようです。
- PPM (Portable Pixmap Format) : RGBフルカラー - PGM (Portable Graymap Format) : グレイスケール - PBM (Portable Bitmap Format) : ビットマップ(白黒2値)
最初の2バイトがそれらを判別するマジックナンバーになっており、その下に縦横のピクセル数、そしてPPMであればRGBの最大値を書きます。
#
でコメントも書けるみたいですが、必須ではありません。
#include <iostream> int main() { int nx = 100; int ny = 100; int max = 255; std::cout << "P3\n" << nx << " " << ny << "\n" << max << "\n"; for (int x = 1; x <= nx; x++) { for (int y = 1; y <= ny; y++) { int r = max * int(x) / int(nx); int g = max * int(y) / int(ny); int b = 50; std::cout << r << " " << g << " " << b << "\n"; } } }
これをコンパイルして実行するとppmファイルを作れるはず…。
P3 100 100 255 0 2 2 0 2 5 ... ... ... 0 255 252 0 255 255
これをPhotoshopで開くと、以下のような画像ができます。Red / Greenでやったのでよく見るUVマップのグラデーションみたいになりました。
と、まあただそれだけなんですが、なぜか出力された画像をそのまま開こうとするとヘッダーが壊れている的なメッセージが出て開けません。
じゃあ、どうやって上の画像を出したかといえば、適当にネットから拾ってきたPPM画像の中身を差し替えただけです。一体何が違うのか。 改行やwhitespaceなどはだいぶ寛容なフォーマットのようだし…。
とまあ、謎が少し残ってしまいましたが、結果は出たので一応、満足です。
参考
http://tech.ckme.co.jp/pnm.shtml
https://www.mm2d.net/main/prog/c/image_io-01.html
http://paulbourke.net/dataformats/ppm
http://www.not-enough.org/abe/manual/command/netpbm/ppm.html