#include <gl/glew.h>
#include <gl/wglew.h>
//祖传设置像素格式函数
bool set_pixel_format(HDC hdc)
{
PIXELFORMATDESCRIPTOR pfd = { 0 };
pfd.nSize = sizeof(pfd);
pfd.nVersion = 1;
pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
pfd.iPixelType = PFD_TYPE_RGBA;
pfd.cColorBits = 32;
pfd.cRedBits = 8;
//pfd.cRedShift = 16;
pfd.cGreenBits = 8;
//pfd.cGreenShift = 8;
pfd.cBlueBits = 8;
//pfd.cBlueShift = 0;
pfd.cAlphaBits = 8;
//pfd.cAlphaShift = 0;
//pfd.cAccumBits = 64;
//pfd.cAccumRedBits = 16;
//pfd.cAccumGreenBits = 16;
//pfd.cAccumBlueBits = 16;
//pfd.cAccumAlphaBits = 0;
pfd.cDepthBits = 24;
pfd.cStencilBits = 8;
pfd.cAuxBuffers = 0;
pfd.iLayerType = PFD_MAIN_PLANE;
pfd.bReserved = 0;
pfd.dwLayerMask = 0;
pfd.dwVisibleMask = 0;
pfd.dwDamageMask = 0;
int pixel_id = ChoosePixelFormat(hdc, &pfd);
if (!pixel_id) {
//Let's choose a default index.
pixel_id = 1;
if (FALSE == DescribePixelFormat(hdc, pixel_id, sizeof(PIXELFORMATDESCRIPTOR), &pfd)) {
MessageBox(WindowFromDC(hdc), TEXT("DescribePixelFormat error."), TEXT("OpenGL"), MB_OK);
return -1;
}
}
if (FALSE == SetPixelFormat(hdc, pixel_id, &pfd))
{
MessageBox(WindowFromDC(hdc), TEXT("SetPixelFormat error."), TEXT("OpenGL"), MB_OK);
return -2;
}
}
//初始化1.1版本的OpenGL
HGLRC init_context(HDC hdc)
{
if(set_pixel_format(hdc) == false){
return NULL;
}
HGLRC hRC = wglCreateContext(hdc);
if (!hRC) {
MessageBox(WindowFromDC(hdc), TEXT("wglCreateContext error."), TEXT("OpenGL"), MB_OK);
}
if (FALSE == wglMakeCurrent(hdc, hRC)) {
MessageBox(WindowFromDC(hdc), TEXT("wglMakeCurrent error."), TEXT("OpenGL"), MB_OK);
}
return hRC;
}
void set_attribute(int* attrib, int name, int value)
{
while(*attrib){
if(*attrib == name){
*++attrib = value;
break;
}
attrib += 2;
}
}
//使用wglCreateContextAttribsARB初始化OpenGL
//HGLRC init_context_ext(hDC, 主版本, 次版本)
HGLRC init_context_ext(HDC hDC, int major, int minor)
{
HGLRC hRC = init_context(hDC);
if(hRC == NULL){
return NULL;
}
//init glew
int err = glewInit();
if (GLEW_OK != err){
MessageBox(WindowFromDC(hDC), TEXT("glewInit() error."), TEXT("OpenGL"), 0);
return false;
}
//init wglew
err = wglewInit();
if (GLEW_OK != err){
MessageBox(WindowFromDC(hDC), TEXT("wglewInit() error."), TEXT("OpenGL"), 0);
return false;
}
//删除当前OpenGL环境
wglMakeCurrent(NULL, NULL);
wglDeleteContext(hRC);
int nPixelFormat=-1;
int nPixCount = 0;
float fPixAttribs[]= {
0,0
};
int pixel_attrib[] =
{
WGL_SUPPORT_OPENGL_ARB, GL_TRUE, // Must support OGL rendering
WGL_DRAW_TO_WINDOW_ARB, GL_TRUE, // pf that can run a window
WGL_ACCELERATION_ARB, WGL_FULL_ACCELERATION_ARB, // must be HW accelerated
WGL_DOUBLE_BUFFER_ARB, GL_TRUE, // Double buffered context
WGL_PIXEL_TYPE_ARB, WGL_TYPE_RGBA_ARB,
WGL_COLOR_BITS_ARB, 32, // 8 bits of each R, G and B
WGL_DEPTH_BITS_ARB, 24, // 24 bits of depth precision for window
WGL_STENCIL_BITS_ARB, 8, // 开启模板缓冲区,模板缓冲区位数=8
WGL_SAMPLE_BUFFERS_ARB, GL_TRUE, // MSAA on,开启多重采样
WGL_SAMPLES_ARB, 4, // 4x MSAA ,多重采样样本数量为4
0, 0
};
//这些没有测试
//WGL_CONTEXT_CORE_PROFILE_BIT_ARB 只包含核心环境
//WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB 创建一个能够兼容所有OpenGL老版本的环境。
//WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB
//WGL_CONTEXT_FLAGS_ARB, WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB,
wglChoosePixelFormatARB(hDC, pixel_attrib, fPixAttribs, 1, &nPixelFormat, (UINT*)&nPixCount);
if (nPixelFormat==-1) {
// Try again without MSAA
set_attribute(pixel_attrib, WGL_SAMPLE_BUFFERS_ARB, GL_FALSE);
wglChoosePixelFormatARB(hDC, pixel_attrib, fPixAttribs, 1, &nPixelFormat, (UINT*)&nPixCount);
}
GLint attribs[] = {
//WGL_CONTEXT_MAJOR_VERSION_ARB, 3,//主版本3
//WGL_CONTEXT_MINOR_VERSION_ARB, 3,//次版本号3
WGL_CONTEXT_MAJOR_VERSION_ARB, major, //主版本
WGL_CONTEXT_MINOR_VERSION_ARB, minor, //次版本号
WGL_CONTEXT_PROFILE_MASK_ARB,WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB,
//要求返回兼容模式环境,如果不指定或指定为WGL_CONTEXT_CORE_PROFILE_BIT_ARB会返回只包含核心功能的环境
0, 0
};
/*
hRC = wglCreateContextAttribsARB(hDC, 0, attribs);
if (hRC == NULL) {
MessageBox(WindowFromDC(hDC), TEXT("Could not create an OpenGL 3.3 context."), TEXT("OpenGL"), 0);
attribs[3] = 2;
hRC = wglCreateContextAttribsARB(hDC,0, attribs);
if (hRC == NULL) {
MessageBox(WindowFromDC(hDC), TEXT("Could not create an OpenGL 3.2 context."), TEXT("OpenGL"), 0);
//要求opengl3.2以上环境
return NULL;
}
}
*/
hRC = wglCreateContextAttribsARB(hDC, 0, attribs);
if (hRC == NULL) {
MessageBox(WindowFromDC(hDC), TEXT("Could not create an OpenGL context."), TEXT("OpenGL"), 0);
return NULL;
}
if (FALSE == wglMakeCurrent(hDC, hRC)) {
wglDeleteContext(hRC);
MessageBox(WindowFromDC(hDC), TEXT("wglMakeCurrent error."), TEXT("OpenGL"), MB_OK);
return NULL;
}
return hRC;
}