Win32: Fix event time wrapping

Related to #1012.
This commit is contained in:
Camilla Löwy 2017-09-14 03:34:04 +02:00
parent c577ae4b0e
commit 138b10eb28
2 changed files with 19 additions and 8 deletions

View File

@ -259,8 +259,9 @@ typedef struct _GLFWlibraryWin32
RAWINPUT* rawInput; RAWINPUT* rawInput;
int rawInputSize; int rawInputSize;
// The time of the last event // State for accumulating a non-wrapping event time
LONG lastEventTime; uint32_t lastTimestamp;
uint64_t eventTime;
struct { struct {
HINSTANCE instance; HINSTANCE instance;

View File

@ -347,6 +347,14 @@ static int getKeyMods(void)
return mods; return mods;
} }
// Updates the event time with the specified timestamp
//
static void updateEventTime(LONG timestamp)
{
_glfw.win32.eventTime += (uint32_t) timestamp - _glfw.win32.lastTimestamp;
_glfw.win32.lastTimestamp = timestamp;
}
// Retrieves and translates modifier keys // Retrieves and translates modifier keys
// //
static int getAsyncKeyMods(void) static int getAsyncKeyMods(void)
@ -595,7 +603,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
case WM_UNICHAR: case WM_UNICHAR:
{ {
const GLFWbool plain = (uMsg != WM_SYSCHAR); const GLFWbool plain = (uMsg != WM_SYSCHAR);
_glfw.win32.lastEventTime = GetMessageTime(); updateEventTime(GetMessageTime());
if (uMsg == WM_UNICHAR && wParam == UNICODE_NOCHAR) if (uMsg == WM_UNICHAR && wParam == UNICODE_NOCHAR)
{ {
@ -618,7 +626,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
const int scancode = (lParam >> 16) & 0x1ff; const int scancode = (lParam >> 16) & 0x1ff;
const int action = ((lParam >> 31) & 1) ? GLFW_RELEASE : GLFW_PRESS; const int action = ((lParam >> 31) & 1) ? GLFW_RELEASE : GLFW_PRESS;
const int mods = getKeyMods(); const int mods = getKeyMods();
_glfw.win32.lastEventTime = GetMessageTime(); updateEventTime(GetMessageTime());
if (key == _GLFW_KEY_INVALID) if (key == _GLFW_KEY_INVALID)
break; break;
@ -653,7 +661,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
case WM_XBUTTONUP: case WM_XBUTTONUP:
{ {
int i, button, action; int i, button, action;
_glfw.win32.lastEventTime = GetMessageTime(); updateEventTime(GetMessageTime());
if (uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONUP) if (uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONUP)
button = GLFW_MOUSE_BUTTON_LEFT; button = GLFW_MOUSE_BUTTON_LEFT;
@ -704,7 +712,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
{ {
const int x = GET_X_LPARAM(lParam); const int x = GET_X_LPARAM(lParam);
const int y = GET_Y_LPARAM(lParam); const int y = GET_Y_LPARAM(lParam);
_glfw.win32.lastEventTime = GetMessageTime(); updateEventTime(GetMessageTime());
// Disabled cursor motion input is provided by WM_INPUT // Disabled cursor motion input is provided by WM_INPUT
if (window->cursorMode == GLFW_CURSOR_DISABLED) if (window->cursorMode == GLFW_CURSOR_DISABLED)
@ -783,6 +791,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
case WM_MOUSELEAVE: case WM_MOUSELEAVE:
{ {
updateEventTime(GetMessageTime());
window->win32.cursorTracked = GLFW_FALSE; window->win32.cursorTracked = GLFW_FALSE;
_glfwInputCursorEnter(window, GLFW_FALSE); _glfwInputCursorEnter(window, GLFW_FALSE);
return 0; return 0;
@ -790,6 +799,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
case WM_MOUSEWHEEL: case WM_MOUSEWHEEL:
{ {
updateEventTime(GetMessageTime());
_glfwInputScroll(window, 0.0, (SHORT) HIWORD(wParam) / (double) WHEEL_DELTA); _glfwInputScroll(window, 0.0, (SHORT) HIWORD(wParam) / (double) WHEEL_DELTA);
return 0; return 0;
} }
@ -797,6 +807,7 @@ static LRESULT CALLBACK windowProc(HWND hWnd, UINT uMsg,
case WM_MOUSEHWHEEL: case WM_MOUSEHWHEEL:
{ {
// This message is only sent on Windows Vista and later // This message is only sent on Windows Vista and later
updateEventTime(GetMessageTime());
// NOTE: The X-axis is inverted for consistency with macOS and X11 // NOTE: The X-axis is inverted for consistency with macOS and X11
_glfwInputScroll(window, -((SHORT) HIWORD(wParam) / (double) WHEEL_DELTA), 0.0); _glfwInputScroll(window, -((SHORT) HIWORD(wParam) / (double) WHEEL_DELTA), 0.0);
return 0; return 0;
@ -1504,8 +1515,7 @@ void _glfwPlatformSetWindowFloating(_GLFWwindow* window, GLFWbool enabled)
double _glfwPlatformGetEventTime(void) double _glfwPlatformGetEventTime(void)
{ {
/* Windows events are stored in milliseconds */ return (double) _glfw.win32.eventTime / 1000.0;
return (double) _glfw.win32.lastEventTime / 1000.0;
} }
void _glfwPlatformPollEvents(void) void _glfwPlatformPollEvents(void)