Schritt 1: Eigenschaften des Anwendungsfensters festlegen.
Schritt 2: Anwendungsfenster registrieren lassen.
Schritt 3: Falls die Anwendung im Vollbildmodus laufen soll, dann dessen Eigenschaften festlegen und die Anzeige-Einstellungen dementsprechend ändern.
Schritt 4: Anwendungsfenster erzeugen.
Schritt 5: Gewünschtes Pixelformat festlegen.
Schritt 6: Gerätekontext anfordern.
Schritt 7: Überprüfen, ob das gewünschte Pixelformat vom Gerätekontext unterstützt wird.
Schritt 8: Temporären OpenGL-Compatibility-Profile-Renderkontext erstellen, den wir jedoch nicht zum Rendern verwenden werden. Bei Verwendung von älteren Catalyst-Treibern (vor der offiziellen Unterstützung von OpenGL 3.3 und 4.0 seitens ATI) wurde an dieser Stelle ein OpenGL-2.x-Renderkontext erzeugt. Den temporären Renderkontext benötigen wir für die Erstellung eines Forward-Compatible-Renderkontext, den wir im weiteren Verlauf zum Rendern nutzen.
Hinweis:
Im Gegensatz zu einem Forward-Compatible-Renderkontext soll ein Compatibility-Profile-Renderkontext die Abwärtskompatibilität mit älteren OpenGL-Versionen gewährleisten.
Schritt 9: GLEW-Library initialisieren.
Schritt 10: Attribute für den OpenGL-Renderkontext festlegen. Wir verwenden aus Performancegründen einen Forward-Compatible-Renderkontext, der jedoch keine Abwärtskompatibilität mehr gewährleistet.
Schritt 11: Überprüfen, ob der gewünschte Renderkontext erstellt werden kann.
Schritt 12: Den Compatibility-Profile-Renderkontext löschen und den Forward-Compatible-Renderkontext zum neuen Renderkontext der Anwendung machen.
Hier nun der zugehörige Source Code:
BOOL CreateOpenGLWindow(LPCWSTR title)
{
// Struktur zum Speichern der Fenstereigenschaften
WNDCLASS wc;
DWORD dwExStyle; // Aussehen des Fensters (Erweiterungen)
DWORD dwStyle; // Aussehen des Fensters
RECT WindowRect; // Fenstergröße
// Fenstergröße festlegen:
WindowRect.left = 0;
WindowRect.right = g_screenwidth_Loaded;
WindowRect.top = 0;
WindowRect.bottom = g_screenheight_Loaded;
// Instanz der Windows Anwenung holen:
g_ApplicationInstanceHandle = GetModuleHandle(NULL);
// Fenstereigenschaften festlegen:
// Aussehen des Fensters festlegen:
wc.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;
// Callback Funktion für die Nachrichtenverarbeitung:
wc.lpfnWndProc = (WNDPROC) WndProc;
// weitere Eigenschaften:
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = g_ApplicationInstanceHandle;
wc.hIcon = LoadIcon(NULL, IDI_WINLOGO);
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = NULL;
wc.lpszMenuName = NULL;
wc.lpszClassName = L"OpenGL";
// Fenster registrieren lassen:
if(!RegisterClass(&wc))
{
Add_To_Log("Failed To Register The Window Class.");
return FALSE;
}
// Einstellugen für den Vollbildmodus festlegen:
if(g_FullScreen)
{
DEVMODE dmScreenSettings;
// Speicherbereich leeren:
memset(&dmScreenSettings,0,sizeof(dmScreenSettings));
// benötigten Speicherplatz ermitteln:
dmScreenSettings.dmSize = sizeof(dmScreenSettings);
// Bildschirmbreite festlegen:
dmScreenSettings.dmPelsWidth = g_screenwidth_Loaded;
// Bildschirmhöhe festlegen:
dmScreenSettings.dmPelsHeight = g_screenheight_Loaded;
// Farbtiefe festlegen:
dmScreenSettings.dmBitsPerPel = g_ColorDepth;
dmScreenSettings.dmFields = DM_BITSPERPEL|DM_PELSWIDTH|DM_PELSHEIGHT;
// Anzeigeeinstellungen für den Vollbildmodus ändern:
if(ChangeDisplaySettings(&dmScreenSettings,CDS_FULLSCREEN)!=
DISP_CHANGE_SUCCESSFUL)
{
g_FullScreen = FALSE;
}
}
// Der Wechsel in den Vollbildmodus war erfolgreich:
if(g_FullScreen)
{
dwExStyle=WS_EX_APPWINDOW; // Fenster wird in der Task-Leiste Angezeigt
dwStyle=WS_POPUP; // Fenster ohne Rahmen verwenden
ShowCursor(FALSE); // Mauszeiger nicht anzeigen
}
else
{
// Fenster wird in der Task-Leiste Angezeigt,Fenster,
// mit gehobener Kante:
dwExStyle=WS_EX_APPWINDOW | WS_EX_WINDOWEDGE;
// Fenster-Buttons für Minimieren, Maximieren und Schließen anzeigen:
dwStyle=WS_OVERLAPPEDWINDOW;
}
// Fenster justieren:
AdjustWindowRectEx(&WindowRect, dwStyle, FALSE, dwExStyle);
// Anwendungsfenster erzeugen:
if(!(g_MainWindowHandle = CreateWindowEx(dwExStyle, L"OpenGL", title,
dwStyle | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
0, 0, WindowRect.right-WindowRect.left,
WindowRect.bottom-WindowRect.top, NULL,
NULL, g_ApplicationInstanceHandle, NULL)))
{
KillOpenGLWindow();
Add_To_Log("Window Creation Error!");
return FALSE;
}
// unser gewünschtes Pixelformat festlegen:
static PIXELFORMATDESCRIPTOR pfd =
{
sizeof(PIXELFORMATDESCRIPTOR), 1,
PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER,
PFD_TYPE_RGBA, g_ColorDepth, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
g_ZBufferDepth, 0, 0, PFD_MAIN_PLANE, 0, 0, 0, 0
};
// Device (Geräte) Context (DC) holen:
if(!(g_DeviceContextHandle = GetDC(g_MainWindowHandle)))
{
KillOpenGLWindow();
Add_To_Log("Can't Create A GL Device Context!");
return FALSE;
}
// Zwischenspeichern des beim Rendern zu verwendenden Pixelformats
// Farbtiefe, Genauigkeit des Tiefenpuffers, etc.
GLuint PixelFormat;
// Überprüfen, ob das gewünschte Pixelformat unterstützt wird:
if(!(PixelFormat=ChoosePixelFormat(g_DeviceContextHandle, &pfd)))
{
KillOpenGLWindow();
Add_To_Log("Can't Find A Suitable PixelFormat!");
return FALSE;
}
// Pixelformat festlegen:
if(!SetPixelFormat(g_DeviceContextHandle,PixelFormat,&pfd))
{
KillOpenGLWindow();
Add_To_Log("Can't Set The PixelFormat!");
return FALSE;
}
// zunächst einen temporären Compatibility-Profile-Renderkontext erstellen,
// den wir jedoch nicht zum Rendern verwenden werden:
HGLRC tempContext = wglCreateContext(g_DeviceContextHandle);
wglMakeCurrent(g_DeviceContextHandle, tempContext);
// GLEW-Library initialisieren
glewInit();
Add_To_Log((char*)glGetString(GL_VERSION));
// Attribute für den OpenGL 3.3 Render-Context festlegen:
int attribList[] =
{
WGL_CONTEXT_MAJOR_VERSION_ARB, 3,
WGL_CONTEXT_MINOR_VERSION_ARB, 3,
WGL_CONTEXT_FLAGS_ARB, WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB, 0
};
// Überprüfen, ob ein OpenGL 3.3 Render-Context erstellt werden kann:
if(wglewIsSupported("WGL_ARB_create_context") == 1)
{
// OpenGL 3.3 Render-Context erstellen:
// Hierfür wird die wglCreateContextAttribsARB()-Methode benötigt, die
// ihrerseits den Compatibility-Profile-Context benötigt:
g_OpenGLRenderContextHandle = wglCreateContextAttribsARB(
g_DeviceContextHandle,0, attribList);
// temporären Compatibility-Profile-Context löschen:
wglMakeCurrent(NULL,NULL);
wglDeleteContext(tempContext);
// OpenGL 3.3 Render-Context zum Rendern verwenden:
wglMakeCurrent(g_DeviceContextHandle,g_OpenGLRenderContextHandle);
Add_To_Log( (char*)glGetString(GL_VERSION) );
}
ShowWindow(g_MainWindowHandle, SW_SHOW); // Fenser anzeigen
SetForegroundWindow(g_MainWindowHandle); // im Vordergrund
// Tastatureingaben sollen von unserer Anwendung verarbeitet werden:
SetFocus(g_MainWindowHandle);
// Größe des Betrachtungsfensters (Viewport) festlegen
// und Projektionsmatrizen berechnen:
ReSizeOpenGLScene(g_screenwidth, g_screenheight);
if(!Set_Initial_OpenGL_RenderParameter(&g_BackgroundScreenColor))
{
KillOpenGLWindow();
Add_To_Log("Can't Activate The GL Rendering Context.");
return FALSE;
}
return TRUE;
}
{
// Struktur zum Speichern der Fenstereigenschaften
WNDCLASS wc;
DWORD dwExStyle; // Aussehen des Fensters (Erweiterungen)
DWORD dwStyle; // Aussehen des Fensters
RECT WindowRect; // Fenstergröße
// Fenstergröße festlegen:
WindowRect.left = 0;
WindowRect.right = g_screenwidth_Loaded;
WindowRect.top = 0;
WindowRect.bottom = g_screenheight_Loaded;
// Instanz der Windows Anwenung holen:
g_ApplicationInstanceHandle = GetModuleHandle(NULL);
// Fenstereigenschaften festlegen:
// Aussehen des Fensters festlegen:
wc.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;
// Callback Funktion für die Nachrichtenverarbeitung:
wc.lpfnWndProc = (WNDPROC) WndProc;
// weitere Eigenschaften:
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = g_ApplicationInstanceHandle;
wc.hIcon = LoadIcon(NULL, IDI_WINLOGO);
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = NULL;
wc.lpszMenuName = NULL;
wc.lpszClassName = L"OpenGL";
// Fenster registrieren lassen:
if(!RegisterClass(&wc))
{
Add_To_Log("Failed To Register The Window Class.");
return FALSE;
}
// Einstellugen für den Vollbildmodus festlegen:
if(g_FullScreen)
{
DEVMODE dmScreenSettings;
// Speicherbereich leeren:
memset(&dmScreenSettings,0,sizeof(dmScreenSettings));
// benötigten Speicherplatz ermitteln:
dmScreenSettings.dmSize = sizeof(dmScreenSettings);
// Bildschirmbreite festlegen:
dmScreenSettings.dmPelsWidth = g_screenwidth_Loaded;
// Bildschirmhöhe festlegen:
dmScreenSettings.dmPelsHeight = g_screenheight_Loaded;
// Farbtiefe festlegen:
dmScreenSettings.dmBitsPerPel = g_ColorDepth;
dmScreenSettings.dmFields = DM_BITSPERPEL|DM_PELSWIDTH|DM_PELSHEIGHT;
// Anzeigeeinstellungen für den Vollbildmodus ändern:
if(ChangeDisplaySettings(&dmScreenSettings,CDS_FULLSCREEN)!=
DISP_CHANGE_SUCCESSFUL)
{
g_FullScreen = FALSE;
}
}
// Der Wechsel in den Vollbildmodus war erfolgreich:
if(g_FullScreen)
{
dwExStyle=WS_EX_APPWINDOW; // Fenster wird in der Task-Leiste Angezeigt
dwStyle=WS_POPUP; // Fenster ohne Rahmen verwenden
ShowCursor(FALSE); // Mauszeiger nicht anzeigen
}
else
{
// Fenster wird in der Task-Leiste Angezeigt,Fenster,
// mit gehobener Kante:
dwExStyle=WS_EX_APPWINDOW | WS_EX_WINDOWEDGE;
// Fenster-Buttons für Minimieren, Maximieren und Schließen anzeigen:
dwStyle=WS_OVERLAPPEDWINDOW;
}
// Fenster justieren:
AdjustWindowRectEx(&WindowRect, dwStyle, FALSE, dwExStyle);
// Anwendungsfenster erzeugen:
if(!(g_MainWindowHandle = CreateWindowEx(dwExStyle, L"OpenGL", title,
dwStyle | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
0, 0, WindowRect.right-WindowRect.left,
WindowRect.bottom-WindowRect.top, NULL,
NULL, g_ApplicationInstanceHandle, NULL)))
{
KillOpenGLWindow();
Add_To_Log("Window Creation Error!");
return FALSE;
}
// unser gewünschtes Pixelformat festlegen:
static PIXELFORMATDESCRIPTOR pfd =
{
sizeof(PIXELFORMATDESCRIPTOR), 1,
PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER,
PFD_TYPE_RGBA, g_ColorDepth, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
g_ZBufferDepth, 0, 0, PFD_MAIN_PLANE, 0, 0, 0, 0
};
// Device (Geräte) Context (DC) holen:
if(!(g_DeviceContextHandle = GetDC(g_MainWindowHandle)))
{
KillOpenGLWindow();
Add_To_Log("Can't Create A GL Device Context!");
return FALSE;
}
// Zwischenspeichern des beim Rendern zu verwendenden Pixelformats
// Farbtiefe, Genauigkeit des Tiefenpuffers, etc.
GLuint PixelFormat;
// Überprüfen, ob das gewünschte Pixelformat unterstützt wird:
if(!(PixelFormat=ChoosePixelFormat(g_DeviceContextHandle, &pfd)))
{
KillOpenGLWindow();
Add_To_Log("Can't Find A Suitable PixelFormat!");
return FALSE;
}
// Pixelformat festlegen:
if(!SetPixelFormat(g_DeviceContextHandle,PixelFormat,&pfd))
{
KillOpenGLWindow();
Add_To_Log("Can't Set The PixelFormat!");
return FALSE;
}
// zunächst einen temporären Compatibility-Profile-Renderkontext erstellen,
// den wir jedoch nicht zum Rendern verwenden werden:
HGLRC tempContext = wglCreateContext(g_DeviceContextHandle);
wglMakeCurrent(g_DeviceContextHandle, tempContext);
// GLEW-Library initialisieren
glewInit();
Add_To_Log((char*)glGetString(GL_VERSION));
// Attribute für den OpenGL 3.3 Render-Context festlegen:
int attribList[] =
{
WGL_CONTEXT_MAJOR_VERSION_ARB, 3,
WGL_CONTEXT_MINOR_VERSION_ARB, 3,
WGL_CONTEXT_FLAGS_ARB, WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB, 0
};
// Überprüfen, ob ein OpenGL 3.3 Render-Context erstellt werden kann:
if(wglewIsSupported("WGL_ARB_create_context") == 1)
{
// OpenGL 3.3 Render-Context erstellen:
// Hierfür wird die wglCreateContextAttribsARB()-Methode benötigt, die
// ihrerseits den Compatibility-Profile-Context benötigt:
g_OpenGLRenderContextHandle = wglCreateContextAttribsARB(
g_DeviceContextHandle,0, attribList);
// temporären Compatibility-Profile-Context löschen:
wglMakeCurrent(NULL,NULL);
wglDeleteContext(tempContext);
// OpenGL 3.3 Render-Context zum Rendern verwenden:
wglMakeCurrent(g_DeviceContextHandle,g_OpenGLRenderContextHandle);
Add_To_Log( (char*)glGetString(GL_VERSION) );
}
ShowWindow(g_MainWindowHandle, SW_SHOW); // Fenser anzeigen
SetForegroundWindow(g_MainWindowHandle); // im Vordergrund
// Tastatureingaben sollen von unserer Anwendung verarbeitet werden:
SetFocus(g_MainWindowHandle);
// Größe des Betrachtungsfensters (Viewport) festlegen
// und Projektionsmatrizen berechnen:
ReSizeOpenGLScene(g_screenwidth, g_screenheight);
if(!Set_Initial_OpenGL_RenderParameter(&g_BackgroundScreenColor))
{
KillOpenGLWindow();
Add_To_Log("Can't Activate The GL Rendering Context.");
return FALSE;
}
return TRUE;
}