diff --git a/windows/init.cpp b/windows/init.cpp index 2fb52c0f..6b6752da 100644 --- a/windows/init.cpp +++ b/windows/init.cpp @@ -140,6 +140,7 @@ const char *uiInit(uiInitOptions *o) void uiUninit(void) { + uiprivUninitTimers(); uiprivUninitImage(); uninitMenus(); unregisterD2DScratchClass(); diff --git a/windows/main.cpp b/windows/main.cpp index d171e339..485ef570 100644 --- a/windows/main.cpp +++ b/windows/main.cpp @@ -129,6 +129,8 @@ void uiQueueMain(void (*f)(void *data), void *data) logLastError(L"error queueing function to run on main thread"); } +static std::map timers; + void uiTimer(int milliseconds, int (*f)(void *data), void *data) { uiprivTimer *timer; @@ -139,4 +141,19 @@ void uiTimer(int milliseconds, int (*f)(void *data), void *data) // note that timer IDs are pointer sized precisely so we can use them as timer IDs; see https://blogs.msdn.microsoft.com/oldnewthing/20150924-00/?p=91521 if (SetTimer(utilWindow, (UINT_PTR) timer, milliseconds, NULL) == 0) logLastError(L"error calling SetTimer() in uiTimer()"); + timers[timer] = true; +} + +void uiprivFreeTimer(uiprivTimer *t) +{ + timers.erase(t); + uiprivFree(t); +} + +void uiprivUninitTimers(void) +{ + // TODO why doesn't auto t : timers work? + for (auto t = timers.begin(); t != timers.end(); t++) + uiprivFree(t->first); + timers.clear(); } diff --git a/windows/uipriv_windows.hpp b/windows/uipriv_windows.hpp index a1c2bc29..52d74c51 100644 --- a/windows/uipriv_windows.hpp +++ b/windows/uipriv_windows.hpp @@ -103,6 +103,8 @@ struct uiprivTimer { }; extern int registerMessageFilter(void); extern void unregisterMessageFilter(void); +extern void uiprivFreeTimer(uiprivTimer *t); +extern void uiprivUninitTimers(void); // parent.cpp extern void paintContainerBackground(HWND hwnd, HDC dc, RECT *paintRect); diff --git a/windows/utilwin.cpp b/windows/utilwin.cpp index fc2d15d4..08183753 100644 --- a/windows/utilwin.cpp +++ b/windows/utilwin.cpp @@ -42,7 +42,7 @@ static LRESULT CALLBACK utilWindowWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, L if (!(*(timer->f))(timer->data)) { if (KillTimer(utilWindow, (UINT_PTR) timer) == 0) logLastError(L"error calling KillTimer() to end uiTimer() procedure"); - uiprivFree(timer); + uiprivFreeTimer(timer); } return 0; }