AGALで環境マッピング | Photoshop CC Tutorials
今回は六面中、一面だけ反射する環境マッピングのプログラムを作成してみました。

が、しかしすべてアセンブラで書いたので一面だけ反射させるだけでも
プログラムが膨大なものとなってしまい可読性が物凄く悪くなってきました。(;^_^ A

何か便利なツールはないものかと”ClockMakerさん”のはてなブックマークを拝見していたところ
”akihiro kamijoさん”の「Pixel Bender 3D」の記事を発見しました。
そして「Pixel Bender 3D」で書かれた高級言語を拝見してみましたが
高級言語の有難さに涙がでてきそうでした。(;^_^ A

■ ClockMakerさんのはてなブックマーク
http://b.hatena.ne.jp/yasu-log/PixelBender3D/

■ akihiro kamijoさんの「Pixel Bender 3D」に関する記事
Pixel Bender 3D プレビュー 3 公開
http://cuaoar.jp/2011/11/pixel-bender-3d-3.html
Pixel Bender 3D カーネルの書き方
http://cuaoar.jp/2011/12/pixel-bender-3d.html
Pixel Bender 3D カーネルの書き方の続き
http://cuaoar.jp/2011/12/pixel-bender-3d-1.html
Pixel Bender 3D とテクスチャマッピング
http://cuaoar.jp/2011/12/pixel-bender-3d-2.html

今回作成したプログラムです。
床井さんのレイキャスティングのサイトを参考にして作成しました。
//////////////////
// R = I-2(N・I)N
//////////////////
// ベクトルIを求める
"sub ft0, v0, fc18\n" + // fc18 == eye(0,0,-1)
// (N・I)を求める
"dp3 ft6, v1, ft0\n" +
// (N・I)・Nを求める
"mul ft6, ft6, v1\n" +
// -2(N・I)・Nを求める
"add ft6, ft6, ft6\n" +
"neg ft6, ft6\n" +
// R = I-2(N・I)・Nを求める
"add ft0, ft0, ft6\n" +
"nrm ft0.xyz, ft0.xyz\n" + // ft0 == 反射視線R

//////////////////
// uv値を求める
//////////////////
// vec q = cross(dir, e2)
"crs ft6.xyz, ft0.xyz, fc17.xyz\n" +
// float s = dot(q, e1)
"dp3 ft2.xyz, ft6.xyz, fc16.xyz\n" + // ft2 == s

// vec3 e = org - po
"sub ft3, v0, fc15\n" + // ft3 == e
// vec3 r = cross(e, e1)
"crs ft4.xyz, ft3.xyz, fc16.xyz\n" + // ft4 == r
// u = dot(q, e)/s
"dp3 ft6.x, ft6.xyz, ft3.xyz\n" +
"div ft7.x, ft6.x, ft2.x\n" +
// v = dot(r, dir)/s
"dp3 ft3.xyz, ft4.xyz, ft0.xyz\n" +
"div ft7.y, ft3.xyz, ft2.x\n" +
"mov ft4.xy, ft7.xy\n" +
// ft4.xy == uv

// if(s!=0.0)
"sne ft6.x, ft2.x, fc19.x\n" +
"seq ft7.x, ft2.x, fc19.x\n" +
"mul ft6.xy, ft4.xy, ft6.xx\n" +
"mul ft7.xy, fc20.xy, ft7.xx\n" + // fc20 == 100
"add ft4.xy, ft6.xy, ft7.xy\n" +

//////////////////////////////////
// if(u >= 0 && v >= 0 && w >= 0)
//////////////////////////////////
// if(u >= 0
"sge ft6.x, ft4.x, fc19.x\n" + // ft4 == u >= fc19.x == 0.0
"slt ft7.x, ft4.x, fc19.x\n" + // ft4 == u < fc19.x == 0.0
"mul ft6.x, ft4.x, ft6.x\n" +
"mul ft7.x, fc20.x, ft7.x\n" + // fc19 == 0.0
"add ft4.x, ft6.x, ft7.x\n" + // ft4.xにuの値が格納される

"mov ft5.xy, fc19.xy\n" + // ft5 == 0 (初期化)
"mov ft1, fc19\n" + // ft1 == 0 (初期化)

// && v >= 0
"sge ft6.x, ft4.y, fc19.x\n" + // ft4 == v >= fc19.x == 0.0
"slt ft7.x, ft4.y, fc19.x\n" + // ft4 == v < fc19.x == 0.0
"mul ft6.xy, ft4.xy, ft6.xx\n" +
"mul ft7.xy, fc20.xy, ft7.xx\n" + // fc20 == 100.0
"add ft4.xy, ft6.xy, ft7.xy\n" +

// w = 2 - u - tを求める
"sub ft4.z, fc21.x, ft4.x\n" + // 2 - u
"sub ft4.z, ft4.z, ft4.y\n" + // 2 - u

//&& w >= 0)
"sge ft6.x, ft4.z, fc19.x\n" + // ft4.z == w >= fc19.x == 0.0
"slt ft7.x, ft4.z, fc19.x\n" + // ft4.z == w < fc19.x == 0.0
"mul ft6.xyz, ft4.xyz, ft6.xxx\n" +
"mul ft7.xyz, fc19.xyz, ft7.xxx\n" + // fc19 == 0.0
"add ft4.xyz, ft6.xyz, ft7.xyz\n" +

"add ft5.xy, ft5.xy, ft4.xy\n" + // ft5 == uv値

"tex ft7, ft4.xy, fs0 <2d,repeat,linear,nomip>\n" +

"sne ft6.x, ft4.x, fc20.x\n" + // fc20 == 100
"mul ft7, ft7, ft6.xxxx.\n" + // ft7 == RGBA
"add ft1, ft1, ft7\n" +

"mov oc, ft1"


■ 床井さんのサイト
http://marina.sys.wakayama-u.ac.jp/~tokoi/?date=20100113


できあがりの画像です。
$ピック社長のブログ