I have a full-screen OpenGL application which uses standard Win32 TrackPopupMenu function. The first call to this function works fine but after that things go awry: usually the popup menu stops showing up (the code still executes). But on some hardware (notably MacBook running Windows 7) there is some odd flickering when redrawing the window.
I think this is a new problem on Windows 7 (haven’t tried on Windows Vista) because it definitely was working on Windows XP.
Has anyone seen this? I am attaching a simple program that reproduces this behavior. Notice that if you change the width or height of the window by one pixel the problem goes away.
Any help or advice will be appreciated.
#include <windows.h>
#include <windowsx.h>
#include <GL\gl.h>
HMENU hPopupMenu;
void CreateGL(HWND);
void Redraw();
HDC hdc;
HGLRC hrc;
int width;
int height;
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_CREATE:
CreateGL(hWnd);
return 0;
case WM_PAINT:
ValidateRect(hWnd, NULL);
Redraw();
return 0;
case WM_CONTEXTMENU:
TrackPopupMenu(hPopupMenu, 0, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam), 0, hWnd, NULL);
Redraw();
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hWnd, msg, wParam, lParam);
}
int WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int)
{
WNDCLASS wc;
memset(&wc, 0, sizeof(wc));
wc.lpfnWndProc = WndProc;
wc.hInstance = hInstance;
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.lpszClassName = “OpenGLTest”;
wc.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH);
RegisterClass(&wc);
hPopupMenu = CreatePopupMenu();
AppendMenu(hPopupMenu, 0, 101, "Item 1");
AppendMenu(hPopupMenu, 0, 102, "Item 2");
width = GetSystemMetrics(SM_CXSCREEN);
// Uncommenting following line will fix the problem
//--width;
height = GetSystemMetrics(SM_CYSCREEN);
HWND hWnd = CreateWindow("OpenGLTest", "Test",
WS_POPUP, 0, 0, width, height,
NULL, NULL, hInstance, NULL);
ShowWindow(hWnd, SW_SHOW);
UpdateWindow(hWnd);
MSG msg;
while(GetMessage(&msg, 0, NULL, NULL))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return 0;
}
void CreateGL(HWND hWnd)
{
PIXELFORMATDESCRIPTOR pfd;
memset(&pfd, 0, sizeof(pfd));
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 = 24;
pfd.cAlphaBits = 16;
pfd.cDepthBits = 16;
pfd.iLayerType = 0;
hdc = GetDC(hWnd);
int nPF = ChoosePixelFormat(hdc, &pfd);
SetPixelFormat(hdc, nPF, &pfd);
hrc = wglCreateContext(hdc);
wglMakeCurrent(hdc, hrc);
}
void Redraw()
{
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(-1.0f, 1.0f, -1.0f, 1.0f, -1.0f, 1.0f);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glViewport(0, 0, width, height);
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT);
glColor3f(1.0f, 1.0f, 1.0f);
glBegin(GL_LINES);
glVertex2f(-0.9f, -0.9f);
glVertex2f(0.9f, 0.9f);
glEnd();
glFlush();
SwapBuffers(hdc);
}