OpenGLを使ってみる。その1 -初期化編-

OpenGLのレンダーターゲット周りを触ってみたくなったので、しばらくOpenGLを使っていきます。久しぶりのC++です。

開発環境

ウィンドウを作る

面倒なのでWin32アプリケーションウィザードで作ります。

OpenGLの初期化

  • gl/gl.h、opengl32.lib
  • PIXELFORMATDESCRIPTORでフォーマットを指定
  • ChoosePixelFormatで適切なピクセルフォーマットを選択(1から始まるインデックスを取得)
  • SetPixelFormatでピクセルフォーマットを指定
  • wglCreateContextでレンダリングコンテキストを作成
#include <gl/gl.h>
#pragma comment( lib, "opengl32.lib" )
HGLRC glrc;
初期化関数
bool Init( HWND hwnd )
{
    HDC dc = GetDC( hwnd );
    try
    {
        //
        //ピクセルフォーマットの設定
        //
        PIXELFORMATDESCRIPTOR pfd =
        { 
            sizeof(PIXELFORMATDESCRIPTOR),   // size of this pfd 
            1,                     // version number 
            PFD_DRAW_TO_WINDOW |   // support window 
            PFD_SUPPORT_OPENGL |   // support OpenGL 
            PFD_DOUBLEBUFFER,      // double buffered 
            PFD_TYPE_RGBA,         // RGBA type 
            24,                    // 24-bit color depth 
            0, 0, 0, 0, 0, 0,      // color bits ignored 
            0,                     // no alpha buffer 
            0,                     // shift bit ignored 
            0,                     // no accumulation buffer 
            0, 0, 0, 0,            // accum bits ignored 
            32,                    // 32-bit z-buffer 
            0,                     // no stencil buffer 
            0,                     // no auxiliary buffer 
            PFD_MAIN_PLANE,        // main layer 
            0,                     // reserved 
            0, 0, 0                // layer masks ignored 
        };
        int format = ChoosePixelFormat( dc, &pfd );
        if( format == 0 )
            throw "";

        if( !SetPixelFormat( dc, format, &pfd ) )
            throw "";

        //
        //レンダリングコンテキスト作成
        //
        glrc = wglCreateContext( dc );
        if( !glrc )
            throw "";
    }
    catch( ... )
    {
        ReleaseDC( hwnd, dc );
        return false;
    }

    wglMakeCurrent( dc, glrc );
    //OpenGLの初期設定
    ;
    wglMakeCurrent( dc, 0 );
    ReleaseDC( hwnd, dc );
    SendMessage( hwnd, WM_PAINT, 0, 0 );
    return true;
}

OpenGLの破棄

解放関数
void Release()
{
    //
    //レンダリングコンテキスト破棄
    //
    wglDeleteContext( glrc );
}

バックバッファのクリア

  • glClearColorでクリアカラーの設定
  • glClearDepthでクリア時の深度値を設定
  • glClearでクリア
    • GL_COLOR_BUFFER_BIT:バックバッファ
    • GL_DEPTH_BUFFER_BIT:Zバッファ
  • SwapBuffersで画面の更新
描画関数
void Render( HDC dc )
{
    glClearColor( 0.1f, 0.1f, 0.1f, 1.0f );
    glClearDepth( 1.0f );
    glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );

    SwapBuffers( dc );
}

バイスコンテキストとレンダリングコンテキストの関連付け

  • wglMakeCurrentで関連付け
    • 利用可能なレンダリングコンテキストは1つのスレッドで1つだけ
ウィンドウプロシージャ
    case WM_PAINT:
        hdc = BeginPaint(hWnd, &ps);
        // TODO: 描画コードをここに追加してください...
        wglMakeCurrent( hdc, glrc );
        Render( hdc );
        wglMakeCurrent( hdc, 0 );
        EndPaint(hWnd, &ps);
        break;

実行結果


サンプル