monolithic kernel

プラグイン無しでOpenGLを用いた描画を行う

HSPからOpenGLを使う方法のメモ。プラグインは使わないのでコンテストのHSPTV部門でも利用可能です。

文章では説明しづらいので以下サンプルのソースコード。HSPTV部門での利用を想定して定数の演算を最適化しています。pfd_nの値は一部0になるので更なる最適化も可能だとは思いますが、そこは本質ではないので割愛。

#uselib “gdi32”#func SwapBuffers “SwapBuffers” int#cfunc ChoosePixelFormat “ChoosePixelFormat” int, var#func SetPixelFormat “SetPixelFormat” int, int, var#uselib “opengl32”#cfunc wglCreateContext “wglCreateContext” int#func wglMakeCurrent “wglMakeCurrent” int, int#func wglDeleteContext “wglDeleteContext” int#cfunc wglGetCurrentDC “wglGetCurrentDC”#func glClear “glClear” int#func glFinish “glFinish”#func glBegin “glBegin” int#func glEnd “glEnd”#func glVertex2d “glVertex2d” double, double#func glColor3d “glColor3d” double, double, double#uselib “user32”#cfunc GetDC “GetDC” int#func ReleaseDC “ReleaseDC” int, int#define GL_TRIANGLES 0x0004#define GL_COLOR_BUFFER_BIT 0x00004000#define PFD_DOUBLEBUFFER 0x00000001#define PFD_DRAW_TO_WINDOW 0x00000004#define PFD_SUPPORT_OPENGL 0x00000020#define PFD_TYPE_RGBA 0#define PFD_MAIN_PLANE 0// screen 0のDCを取得する。// システム変数hdcの値は内部バッファのDCなので利用できない。hdc_ = GetDC(hwnd)// PIXELFORMATDESCRIPTOR構造体の値を定義する。#const pfd_nSize 40#const pfd_nVersion 1#const pfd_dwFlags (PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER)#const pfd_iPixelType PFD_TYPE_RGBA #const pfd_cColorBits 24#const pfd_cRedBits 0#const pfd_cRedShift 0#const pfd_cGreenBits 0#const pfd_cGreenShift 0#const pfd_cBlueBits 0#const pfd_cBlueShift 0#const pfd_cAlphaBits 0#const pfd_cAlphaShift 0#const pfd_cAccumBits 0#const pfd_cAccumRedBits 0#const pfd_cAccumGreenBits 0#const pfd_cAccumBlueBits 0#const pfd_cAccumAlphaBits 0#const pfd_cDepthBits 0#const pfd_cStencliBits 0#const pfd_cAuxBuffers 16#const pfd_iLayerType PFD_MAIN_PLANE#const pfd_bReserved 0#const pfd_dwLayerMask 0#const pfd_dwVisibleMask 0#const pfd_dwDamageMask 0// PIXELFORMATDESCRIPTOR構造体を初期化する。#const pfd_0 ((pfd_nVersion << 16) | pfd_nSize)#const pfd_1 (pfd_dwFlags)#const pfd_2 ((pfd_cRedShift << 24) | (pfd_cRedBits << 16) | (pfd_cColorBits << 8) | pfd_iPixelType)#const pfd_3 ((pfd_cBlueShift << 24) | (pfd_cBlueBits << 16) | (pfd_cGreenShift << 8) | pfd_cGreenBits)#const pfd_4 ((pfd_cAccumRedBits << 24) | (pfd_cAccumBits << 16) | (pfd_cAlphaShift << 8) | pfd_cAlphaBits)#const pfd_5 ((pfd_cDepthBits << 24) | (pfd_cAccumAlphaBits << 16) | (pfd_cAccumBlueBits << 8) | pfd_cAccumGreenBits)#const pfd_6 ((pfd_bReserved << 24) | (pfd_iLayerType << 16) | (pfd_cAuxBuffers << 8) | pfd_cStencliBits)#const pfd_7 (pfd_dwLayerMask)#const pfd_8 (pfd_dwVisibleMask)#const pfd_9 (pfd_dwDamageMask)pfd = pfd_0, pfd_1, pfd_2, pfd_3, pfd_4, pfd_5, pfd_6, pfd_7, pfd_8, pfd_9#undef pfd_0#undef pfd_1#undef pfd_2#undef pfd_3#undef pfd_4#undef pfd_5#undef pfd_6#undef pfd_7#undef pfd_8#undef pfd_9// ピクセルフォーマットを設定する。SetPixelFormat hdc_, ChoosePixelFormat(hdc_, pfd), pfd// コンテキストを生成し、設定する。hrc = wglCreateContext(hdc_)wglMakeCurrent hdc_, hrconexit closemain // バッファをクリアする。 glClear GL_COLOR_BUFFER_BIT // 描画を行う。 glBegin GL_TRIANGLES glColor3d 1 glVertex2d , 1 glColor3d , 1 glVertex2d -1, -1 glColor3d , , 1 glVertex2d 1, -1 glEnd // 描画を終了する。 glFinish SwapBuffers wglGetCurrentDC() await 30 goto mainclose // コンテキストを元に戻し、破棄する。 wglMakeCurrent hdc_ wglDeleteContext hrc ReleaseDC hwnd, hdc_ end

このコードは最小限なので本格的に開発する場合にはgl.hあたりから定義をとってくる必要があります。

実際にプログラムに利用した例としては、2007年のコンテストに応募したameのソースコードが参考になるかもしれません。

追記

  • 2010/12/10
    • デバイスコンテキストのリークを修正