ゲームプログラミングの解説を続けていこう。前回は、描画フレームワークとしてOpenGLを使うということを解説した。今回は、OpenGLプログラミングの入り口となる箇所の説明をする。

OpenGLテンプレートの構成とOpenGL ESのバージョン

OpenGLプログラミングを行うために、Xcodeのプロジェクトテンプレートから「OpenGL ES Application」を選択するところまでが、前回の内容だった。まずは、このプロジェクトにどのようなクラスがあるか、説明しよう。

現在のテンプレートだと、含まれているクラスのうちOpenGLに関するものは、3つだ。EAGLViewクラスと、ES1Rendererクラス、ES2Rendererクラスだ。

EAGLViewクラスは、UIViewクラスを継承している。従って、通常のCocoaのビュー階層に、このクラスを追加することができる。このクラスの仕事は主に、OpenGLでのアニメーションを管理することにある。

実際にOpenGLの描画を行うのは、ES1RendererクラスとES2Rendererクラスになる。なぜ2つあるかというと、それぞれOpenGL ESの1.0と2.0に対応するからだ。OpenGL ES 2.0は、シェーダプログラミングが可能になるなど、1.0に比べて高い機能を持っている。だが、すべてのiPhoneで使える訳ではないので、注意が必要だ。以下の表を参考にしてほしい。

OpenGL ES 1.0 OpenGL ES 2.0
iPhone 3GS OK OK
iPhone 3G OK NG
iPhone OK NG
iPod touch 3rd OK OK
iPod touch 1st/2nd OK NG
iPhone Simulator OK OK

このように、iPhone 3GSとiPod touch 3rd generationでしか、OpenGL ES 2.0は使うことができない。2.0を使おうとすると、対象となるデバイスが限られてしまうので、よく検討してほしい。ここでは、1.0の機能だけを使って話を進めていくことにする。

さて、これからOpen GLプログラミングを進めていくのだが、そのソースコードはES1RendererまたはES2Rendererの中に書いていくことになる。だが、プロジェクトがデフォルトの状態だと、2.0が使用可能なデバイスではES2Rendererを使い、それ以外はES1Rendererを使うという、いささか面倒くさい事態が発生する。そこで、強制的にES1Rendererしか使わないように、ソースコードを変更しておこう。

EAGLViewクラスの、initWithCoder:メソッドを、以下のように変更しておく。

List 1.

// 常にES1Rendererを使用する
#if 1
        renderer = [[ES1Renderer alloc] init];
#else
        renderer = [[ES2Renderer alloc] init];
#endif

これで、どのデバイスであってもES1Rendererクラスを実装すれば良いということになる。こちらに絞って話を進めていこう。

OpenGL環境のセットアップ

ES1Rendererクラスを見てみよう。このクラスでは、OpenGLのセットアップおよび描画を行うための処理がいろいろと含まれている。

このクラスを使って描画を行うのだが、このとき我々が興味があるメソッドは、ただ1つである。renderメソッドだ。このメソッドが、描画を行うために用意されているものになる。UIViewで言うところの、drawRect:メソッドに相当するものだと考えていい。

このメソッドには、デフォルトの状態だと、デモとして四角形を描いて上下に動かすためのソースコードが書かれている。ここから四角形を書くためのソースコードを除去し、OpenGLのセットアップに必要なものだけを残すと、次のようになるだろう。

List 2.

- (void) render
{
    // EAGLコンテキストを設定する
    [EAGLContext setCurrentContext:context];

    // フレームバッファを設定する
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, defaultFramebuffer);

    // 視点の設定をする
    glViewport(0, 0, backingWidth, backingHeight);
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glOrthof(-1.0f, 1.0f, -1.5f, 1.5f, -1.0f, 1.0f);
    glMatrixMode(GL_MODELVIEW);

    // バッファをクリアする
    glClearColor(0.5f, 0.5f, 0.5f, 1.0f);
    glClear(GL_COLOR_BUFFER_BIT);

    // OpenGLの設定をする
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_COLOR_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);

    // 必要な描画を行う
    ...

    // バッファを表示する
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, colorRenderbuffer);
    [context presentRenderbuffer:GL_RENDERBUFFER_OES];
}

まず始めに、OpenGL環境のセットアップとして、EAGLコンテキストの設定や、フレームバッファの設定をする。

続いて、視点の設定をしている。ここが、2次元描画を行うための特別なものになっている。注意してほしいのが、glOrthofを読んでいるところである。これにより、正射影を設定している。2次元描画を行うには、正射影を設定して、z軸0上にポリゴンを並べてやればいいのだ。また、glOrhtofの引き数で、画面上の座標系も設定している。この設定により、画面上の中央が(0, 0)、画面横の長さが2.0、画面縦の長さが3.0という座標系ができあがっているのだ。

ここに、ポリゴンを配置して、絵を描いていくことになる。

次回は、実際に絵を描く手順を解説しよう。