SetTimer를 사용하여 게임에 타이머를 넣었습니다. 잠시 후 타이머가 1000ms마다 트리거되고 타이머의 시간 간격을 변경하려고하므로 SetTimer를 다시 호출합니다. 동일한 timerId (MSDN에 따르면 이것은 이전 타이머를 새로운 시간 초과로 바꿉니다)이지만 타이머가 작동하지 않는 것 같습니다.SetTimer가 시간 간격을 변경하지 않음
여기가 내 코드입니다. 일반적인 게임 루프입니다.
INT WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR szCmdLine, int iCmdShow)
{
WNDCLASSEX winClass ;
winClass.lpszClassName = L"RotationBySetTimer";
winClass.cbSize = sizeof(WNDCLASSEX);
winClass.style = CS_HREDRAW | CS_VREDRAW;
winClass.lpfnWndProc = MsgProc;
winClass.hInstance = hInstance;
winClass.hIcon = NULL ;
winClass.hIconSm = NULL ;
winClass.hCursor = LoadCursor(NULL, IDC_ARROW) ;
winClass.hbrBackground = NULL ;
winClass.lpszMenuName = NULL ;
winClass.cbClsExtra = 0;
winClass.cbWndExtra = 0;
RegisterClassEx (&winClass) ;
HWND hWnd = CreateWindowEx(NULL,
winClass.lpszClassName, // window class name
L"RotationBySetTimer", // window caption
WS_OVERLAPPEDWINDOW, // window style
32, // initial x position
32, // initial y position
600, // initial window width
600, // initial window height
NULL, // parent window handle
NULL, // window menu handle
hInstance, // program instance handle
NULL) ; // creation parameters
**SetTimer(hWnd, 1, 1000, NULL);**
// Initialize Direct3D
if(SUCCEEDED(InitD3D(hWnd)))
{
// Show the window
ShowWindow(hWnd, SW_SHOWDEFAULT);
UpdateWindow(hWnd);
MSG msg ;
ZeroMemory(&msg, sizeof(msg));
PeekMessage(&msg, NULL, 0U, 0U, PM_NOREMOVE);
// Get last time
static DWORD lastTime = timeGetTime();
while (msg.message != WM_QUIT)
{
if(PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE) != 0)
{
TranslateMessage (&msg) ;
DispatchMessage (&msg) ;
}
else // Render the game if there is no message to process
{
// Get current time
DWORD currTime = timeGetTime();
// Calculate time elapsed
float timeDelta = (currTime - lastTime) * 0.001f;
// Render
Render(hWnd, timeDelta) ;
// Update last time to current
lastTime = currTime;
}
}
}
UnregisterClass(winClass.lpszClassName, hInstance) ;
return 0;
}
그리고 이따금 씩 렌더링 기능에서 SetTimer를 호출하여 시간 간격을 변경합니다.
void Render(HWND hWnd, float timeDelta)
{
**SetTimer(hWnd, 1, 2000, NULL);**
if (!g_bActive)
{
Sleep(50) ;
}
SetupMatrix() ;
// Clear the back-buffer to a RED color
g_pd3dDevice->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,0), 1.0f, 0);
// Begin the scene
if(SUCCEEDED(g_pd3dDevice->BeginScene()))
{
// Draw teapot
g_pTeapotMesh->DrawSubset(0) ;
// End the scene
g_pd3dDevice->EndScene();
}
// Present the back-buffer contents to the display
g_pd3dDevice->Present(NULL, NULL, NULL, NULL);
}
코드는 렌더링 기능에서 SetTimer를 다시 호출하기 전에 작동하지만이 줄을 추가 한 후 작동을 멈추는 이유는 무엇입니까?
'WM_TIMER' 메시지를 받으려면 코드가 메시지 루프를 펌핑해야합니다. 메시지 루프를 펌핑하기 위해 주기적으로 멈추지 않는 계산 집약적 인 렌더링에 걸린다면, 타이머의 간격에 관계없이'WM_TIMER' 메시지를받지 못할 것입니다. 'SetTimer'에 대한 두 번째 호출을 주석 처리한다면 실제로 WM_TIMER 메시지가 매 1000ms마다 수신됩니까? –
예, SetTimer에 대한 두 번째 호출을 주석 처리 할 때 작동합니다. – zdd