Go で作ったゲームを Android/iOS 対応させた話 (3) の続き。前の投稿から随分時間が空いてしまいました。今回から iOS 版の実装が始まります。 OpenGL の罠に次々とハマっていく様子が分かります。
日記
2016-06-07
黒い点滅の修正 (1, 2)
「なぜか glFlush
を呼ぶと直る」シリーズの一つ。コマンド実行後に明示的に glFlush
を呼ばないと、 Android 上で黒い点滅が出てしまうので、呼ぶように修正。前回 glFlush
をパフォーマンス向上のために削減したが、それの反動のような修正である。
2016-06-10
特筆することは特になく、リファクタリング的なことが多い。というか自分も何をやったのかだいぶ忘れている…。
2016-06-12
delayedImageTasks の撤廃
いままで delayedImageTasks という main が実行されるまでの描画コマンドタスクラインと、それとは別にアプリケーション実行中の描画コマンドタスクラインの 2 つが併存していた。 init 中に発行される描画コマンドは前者にためられる。 2 つは本質的に同じものなので、後者に統一した。
2016-06-14
画面ちらつきの修正
これは Ebiten のロジックバグのようなそうでないような何かだが、「何フレーム分更新した後に描画するか」の計算の際、 0 だった場合に何もしていなかったのが良くなかった。描画済みのフレームを再描画してあげることで修正。
2016-06-15
iOS 向け開発開始
Android 版がひとまず落ち着いたので、 iOS 版に向けた開発を開始した。
2016-06-17
ビルドタグ ios
を使用
ios
というビルドタグが使えるので利用する。なお iOS は基本的に darwin,arm
か darwin,arm64
だが、エミュレータも入れると darwin,amd64
もある。
glGetShaderPrecisionFormat
を使った highp 使用判定
glGetShaderPrecisionFormat
を使って highp の有無を調べるというもの。 OpenGL ES または WebGL のときに highp などを使い、そうでない OpenGL の場合は使わない (というか使えない) というのを判別する意図なのだが、この用途で glGetShaderPrecisionFormat
を使うのは良くなかった。単に GLSL 内で #ifdef GL_ES
を使えばいいことが随分後に判明する。
2016-06-18
iOS の描画先フレームバッファが 0 ではない問題の修正
デスクトップや Android の描画先フレームバッファは 0 (デフォルトフレームバッファ) であり、何も考えずにそこに描画していたのだが、 iOS は 0 は使えないことが判明。ロジックを変更する必要に迫られた。これに気づくまで画面真っ暗である。
フレームバッファの大きさを考慮にいれたスケールの計算 (後に撤廃)
iOS の描画先のフレームバッファのサイズは GL surface view の大きさとは一致せず、ちゃんと考慮してスケールを計算しないと駄目だった、と記憶している。後にちゃんとしたスケールを計算するように修正したので、この処理は不要になった。
glBindFramebuffer の度に glViewport を呼ぶ修正
Ebiten は glViewport
に指定する値が毎度同じなので最初の 1 回以外は全部すっ飛ばしていたのだが、どうも iOS の場合は glBindFramebuffer
の度に呼び出す必要が有ることが判明。 OpenGL は難しいですね…。
2016-06-19
iOS におけるスケールの取得
UIKit から画面のスケールを取得。 Objective-C を cgo 経由で呼び出した。
2016-06-21
iOS のタッチの実装
Ebiten は gomobile build
ではなく gomobile bind
で動的ライブラリを生成することでモバイルでの利用が可能になる。 gomobile bind
を使う以上 Ebiten 内部でタッチの状態の取得は不可能なので、 Objective-C 側からタッチの状態を渡してあげる必要がある。なお Android も同じである。
2016-06-22
iOS で glViewport
を毎フレーム呼ぶように修正
iOS は glViewport を毎フレーム呼ばなきゃいけないそうです。
glViewport
を呼ばなきゃいけない条件を緩和
実は「iOS ではフレームバッファが変わったら必ず glViewport
を呼ばなきゃいけない」というのは間違いで、大きさが変わったタイミングで呼べばいいことが判明 (どうして判明したかは忘れた)。無駄に glViewport
を呼ぶのはパフォーマンス上問題なので削除することに。
2016-06-23
GLSL で mat4
同士の ==
比較をしないように修正
いままで当たり前のように mat4
同士を ==
で比較していたのだが、実はこれは定義されていないことがわかり、削除。 iOS で発見されたが、なんで他のデバイスでこれが問題にならなかったんですかね…。
ここまでやってもまだ iOS での描画がおかしい。次回へ続く。
ライセンス
この記事のライセンスは CC BY 4.0 とします。