summaryrefslogtreecommitdiff
path: root/src/app.c
diff options
context:
space:
mode:
authorJaakko Keränen <jaakko.keranen@iki.fi>2021-03-20 18:51:03 +0200
committerJaakko Keränen <jaakko.keranen@iki.fi>2021-03-20 18:51:03 +0200
commit5dfb890cf841579edaeb2633025db218e86f45c2 (patch)
treea6937d904579b8d7051cf033e03e99464d298c98 /src/app.c
parentaa70507d43d17ca2c426acd6bf91548fe267ac19 (diff)
App: Periodic commands without timers/threads
Now the periodic commands get posted on the main thread at intervals, and the event loop cooperates by not sleeping if there are periodic commands pending. The macOS animation hangup seems to be unrelated, though — perhaps some internal SDL/Metal machinery related to app refresh stopping for a while?
Diffstat (limited to 'src/app.c')
-rw-r--r--src/app.c32
1 files changed, 26 insertions, 6 deletions
diff --git a/src/app.c b/src/app.c
index 31bd33ed..0611b6dd 100644
--- a/src/app.c
+++ b/src/app.c
@@ -837,6 +837,9 @@ void trimCache_App(void) {
837} 837}
838 838
839iLocalDef iBool isWaitingAllowed_App_(iApp *d) { 839iLocalDef iBool isWaitingAllowed_App_(iApp *d) {
840 if (!isEmpty_Periodic(&d->periodic)) {
841 return iFalse;
842 }
840 if (d->warmupFrames > 0) { 843 if (d->warmupFrames > 0) {
841 return iFalse; 844 return iFalse;
842 } 845 }
@@ -853,14 +856,26 @@ iLocalDef iBool isWaitingAllowed_App_(iApp *d) {
853 return !value_Atomic(&d->pendingRefresh) && isEmpty_SortedArray(&d->tickers); 856 return !value_Atomic(&d->pendingRefresh) && isEmpty_SortedArray(&d->tickers);
854} 857}
855 858
859static iBool nextEvent_App_(iApp *d, enum iAppEventMode eventMode, SDL_Event *event) {
860 if (eventMode == waitForNewEvents_AppEventMode && isWaitingAllowed_App_(d)) {
861 /* If there are periodic commands pending, wait only for a short while. */
862 if (!isEmpty_Periodic(&d->periodic)) {
863 return SDL_WaitEventTimeout(event, 500);
864 }
865 /* We may be allowed to block here until an event comes in. */
866 if (isWaitingAllowed_App_(d)) {
867 return SDL_WaitEvent(event);
868 }
869 }
870 return SDL_PollEvent(event);
871}
872
856void processEvents_App(enum iAppEventMode eventMode) { 873void processEvents_App(enum iAppEventMode eventMode) {
857 iApp *d = &app_; 874 iApp *d = &app_;
858 SDL_Event ev; 875 SDL_Event ev;
859 iBool gotEvents = iFalse; 876 iBool gotEvents = iFalse;
860 while ((isWaitingAllowed_App_(d) && eventMode == waitForNewEvents_AppEventMode && 877 postCommands_Periodic(&d->periodic);
861 SDL_WaitEvent(&ev)) || 878 while (nextEvent_App_(d, eventMode, &ev)) {
862 ((!isWaitingAllowed_App_(d) || eventMode == postedEventsOnly_AppEventMode) &&
863 SDL_PollEvent(&ev))) {
864#if defined (iPlatformAppleMobile) 879#if defined (iPlatformAppleMobile)
865 if (processEvent_iOS(&ev)) { 880 if (processEvent_iOS(&ev)) {
866 continue; 881 continue;
@@ -1064,13 +1079,18 @@ static int run_App_(iApp *d) {
1064 1079
1065void refresh_App(void) { 1080void refresh_App(void) {
1066 iApp *d = &app_; 1081 iApp *d = &app_;
1082 destroyPending_Widget();
1067#if defined (LAGRANGE_IDLE_SLEEP) 1083#if defined (LAGRANGE_IDLE_SLEEP)
1068 if (d->warmupFrames == 0 && d->isIdling) { 1084 if (d->warmupFrames == 0 && d->isIdling) {
1069 return; 1085 return;
1070 } 1086 }
1071#endif 1087#endif
1072 set_Atomic(&d->pendingRefresh, iFalse); 1088 if (!exchange_Atomic(&d->pendingRefresh, iFalse)) {
1073 destroyPending_Widget(); 1089 /* Refreshing wasn't pending. */
1090 if (isFinished_Anim(&d->window->rootOffset)) {
1091 return;
1092 }
1093 }
1074// iTime draw; 1094// iTime draw;
1075// initCurrent_Time(&draw); 1095// initCurrent_Time(&draw);
1076 draw_Window(d->window); 1096 draw_Window(d->window);