2011年7月28日木曜日

OpenGL ES2.0 シェーダの行列計算

Adreno 200・Tegra 250と、PowerVR SGX540で
行列計算の結果が異なる。
確認したのは4次元の場合。
mat4 m;
vec4 p;
p = p*m;

詳しく調査していないけれど、PowerVRで表示の奥行きが崩れているので、
列か行どちらか4番目の扱い方が違うっぽい。

列ベクトルで、変換は左から行列を掛けるように行列を作っていると、
mat4 m;
vec4 p;
p = p*m;
でよいはず。実際、Adreno 200・Tegra 250では問題ない。
(column majorだから逆から掛けている)
これだとPowerVRで崩れるので、シェーダに渡す前に行列を転置、
p = m*p;
とすると3つのGPUで上手くいく。なんだこれは。

ES2.0で、glUniformMatrix のtranspose引数はG_FALSEじゃないといけないの、
すぐに忘れるな。

2011年7月27日水曜日

PerfHUD ES

NVidia社のPerfHUD ESは、
Tegra2ベースの”開発機”で動作する。
私も最初わからなかったが、ドキュメントや各種プレゼンテーションでも、
profiling and debugging tool for Tegra-based development kits
とある。

フォーラム
http://developer.nvidia.com/tegra/forum/connecting-perfhud-es-motorola-xoom

そして、こんなものが
http://www.enovapp.com/tips/how-to-enable-perfhud-es-on-all-android-tegra-devices/

rootとる必要があるのか、嫌だな。

2011年6月20日月曜日

DoxyComment

DoxyCommentで訪れる方が多いため、
ごめんなさいしないといけません。
大した情報がないです。
さらに、VisualStudio2008に移行した時に動作しなくなり、
それ以来使っていないです。
今は、下のような粗雑なマクロしか使っていなかったりします。

Dim author = "hoge"

Sub PutFileHeader()
 Dim str As String
 Dim today As Date = Date.Now.Date()

 str = DTE.ActiveDocument.Name().ToUpper()
 str = str.Replace(".", "_")
 str = "INC_" + str + "__"

 DTE.ActiveDocument.Selection.Text = "#ifndef " + str
 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "#define " + str
 DTE.ActiveDocument.Selection.NewLine()

 Dim name As String
 name = DTE.ActiveDocument.Name()
 DTE.ActiveDocument.Selection.Text = "/**"
 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "@file " + name
 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "@author " + author

 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "@date " + today + " create"
 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "*/"

 DTE.ActiveDocument.Selection.NewLine()
 DTE.ActiveDocument.Selection.Text = "#endif //" + str
 DTE.ActiveDocument.Selection.NewLine()
End Sub


ここから、DoxyCommentとは関係なし。
自戒をこめて。
ドキュメントやサンプルを読まない人がいる。
誰も触れたことのない新技術のライブラリなら、
しっかりと読むべきだろうと。
趣味ならいくらでも自分で悩めばいいが。

2011年5月23日月曜日

ETC1圧縮方法その2

アルゴリズムでどうにかする方法が思い浮かばないので、
小手先でなんとかしてみる。

とりあえず、テーブルのインデックス計算で
RGB各値で別に誤差計算するのではなく、
あらかじめ計算した輝度値だけで行う。
元々のフォーマットが輝度値の誤差をベースカラーに
載せる形式だから、それほど悪くない解だと思う。

浮動小数点数を固定小数点数に直す。
小手先の極みである、計算時間はどうやっても線形にしか減らない。
浮動小数点なら、汚いが見れる範囲だなと思うアルゴリズムでも、
かなり汚くなる。そこまで汚くなるほど精度が足りていないとは思えないので
どこか間違っている。

もう少し思考錯誤の必要がある。
満足いく速度と品質は得られそうにないので、
ユーザが設定するオプションという扱いになりそうだ。
それはプログラマの敗北宣言。

2011年5月20日金曜日

Ericsson Texture Compressionへの圧縮方法

ETC1のフォーマット概要と圧縮法について。

問題は、ETC1へ圧縮するにあたり計算時間が許容できないので、
速い計算方法はないものかというもの。

詳細は、Open GL ES の拡張OES_compressed_ETC1_RGB8_textureの仕様に説明されている。
RGB 24bitの4x4ピクセルを、64ビットに圧縮する。
4x4を、2x4又は4x2のサブブロックに分割し、
サブブロック2つ分のベースカラーにRGB 8bit、
サブブロックそれぞれに差分テーブルのインデックス 3bit、
16ピクセルそれぞれに2bitの、差分テーブルの要素を示すビット 2bit、
残りは、サブブロックの割り方に1bit、ベースカラーの表現方法に1bit、
となる。
base color = 8x3 = 24bit
color table = 3bit x 2 = 6bit
bits for color table = 2bit x 16 = 32 bit
mode flags = 2bit

解凍する場合、計算イメージとしては以下のようになる。
ピクセルの色 = ベースカラー + 差分テーブル[ 2ビットインデックス ]

どう圧縮するかが悩むところ。
差分テーブルは以下左から、テーブル番号、2bit値で11、10、00、01、
0 -8 -2 2 8
1 -17 -5 5 17
2 -29 -9 9 29
3 -42 -13 13 42
4 -60 -18 18 60
5 -80 -24 24 80
6 -106 -33 33 106
7 -183 -47 47 183

テーブル値をどう算出したか妄想すると、統計ではないかと。
計算すべきものは以下の3つ。
・各サブブロックのベースカラーの計算
・ベースカラーに対して、テーブルの決定
・テーブルとベースカラーに対して、2ビットインデックスの計算

発見的手法しかないのかこれは。

2011年5月9日月曜日

VBOの修正と頂点の転送

毎フレーム頂点を書き換える必要があるとして、
Vertex Buffer Object(VBO)の書き換えと、
毎フレーム頂点バッファを転送して描画するのはどちらが速いか。
データによりけりではある。

ここからは妄想。
----
VBOの書き換えを行った場合、
描画前にglFlushで書き換えを反映する必要があるGPUと、
そうでないGPUがある。Windows上のエミュレータは後者。
前者は描画時にバッファの書き込みを待たず、
後者は終わるまで待つ。

glFlushを呼ばない場合、
表示からするとバッファが壊れている。
このことから、VBOの書き換え時に
別のバッファを用意している。
仕様上はglFinishでなければ解決できない。
glFlushで上手くいっているように見えるのは、
単にglFlushに時間がかかって転送が完了しているだけなのか。
----
ここまで妄想。

glFlushを毎フレーム呼べば解決する。
しかし、重量級のglFlushは使いたくない、VBOの書き換えもしたい。
VBOのダブルバッファリングを行い、glFlushを呼ばない実装を試してみたところ、
一見上手く動作しているように見える。
swapBuffers等どこかのタイミングで、
そのフレームのコマンドが全て終了するのを待っている(glFinish)
と考えてよいものか。そうであるはずなのだが、自信を持てない。

Adreno SDKとAdreno Profiler

Radeon HD 5770 Windows XP上で、
PowerVR SDKのOpengl ES2エミュレータが動かなくなった。
Windows 7では元から動かない。
というのが以前の話。

代わりにAdreno SDKとProfilerを導入。
Adrenoでの開発はこちらの方がよいか、快適である。
AdrenoがATI Z430だっただけあり、Radeonとの相性がよいらしい。
ドキュメントもRadeon対応状況の記載に比べて、
Geforceは2,3個動作するのは確認したという感じになっている。

次はTegra2かと思うが、Radeonと相性悪そうだな。動くのかな。
Tegra2の性能が頭ひとつ出ているのだから早急にすることでもない。