Commit 01af7b02540ca7614188a34794287389f39fda48

Sylvain Beucler 2020-06-27T16:22:50

emscripten: support pseudo-synchronous screen refresh and events update using asyncify

diff --git a/src/timer/unix/SDL_systimer.c b/src/timer/unix/SDL_systimer.c
index 411705a..7a44d05 100644
--- a/src/timer/unix/SDL_systimer.c
+++ b/src/timer/unix/SDL_systimer.c
@@ -31,6 +31,10 @@
 #include "SDL_assert.h"
 #include "../SDL_timer_c.h"
 
+#ifdef __EMSCRIPTEN__
+#include <emscripten.h>
+#endif
+
 /* The clock_gettime provides monotonous time, so we should use it if
    it's available. The clock_gettime function is behind ifdef
    for __USE_POSIX199309
@@ -186,6 +190,13 @@ SDL_GetPerformanceFrequency(void)
 void
 SDL_Delay(Uint32 ms)
 {
+#ifdef __EMSCRIPTEN__
+    if (emscripten_has_asyncify()) {
+        /* pseudo-synchronous pause */
+        emscripten_sleep(ms);
+        return;
+    }
+#endif
     int was_error;
 
 #if HAVE_NANOSLEEP
diff --git a/src/video/emscripten/SDL_emscriptenframebuffer.c b/src/video/emscripten/SDL_emscriptenframebuffer.c
index 3c07d31..5c845fd 100644
--- a/src/video/emscripten/SDL_emscriptenframebuffer.c
+++ b/src/video/emscripten/SDL_emscriptenframebuffer.c
@@ -162,6 +162,12 @@ int Emscripten_UpdateWindowFramebuffer(_THIS, SDL_Window * window, const SDL_Rec
                      SDL_GetWindowID(window), ++frame_number);
         SDL_SaveBMP(surface, file);
     }*/
+
+    if (emscripten_has_asyncify()) {
+        /* give back control to browser for screen refresh */
+        emscripten_sleep(0);
+    }
+
     return 0;
 }
 
diff --git a/src/video/emscripten/SDL_emscriptenopengles.c b/src/video/emscripten/SDL_emscriptenopengles.c
index f806bbe..3852fc7 100644
--- a/src/video/emscripten/SDL_emscriptenopengles.c
+++ b/src/video/emscripten/SDL_emscriptenopengles.c
@@ -82,9 +82,19 @@ Emscripten_GLES_LoadLibrary(_THIS, const char *path) {
 }
 
 SDL_EGL_CreateContext_impl(Emscripten)
-SDL_EGL_SwapWindow_impl(Emscripten)
 SDL_EGL_MakeCurrent_impl(Emscripten)
 
+int
+Emscripten_GLES_SwapWindow(_THIS, SDL_Window * window)
+{
+    EGLBoolean ret = SDL_EGL_SwapBuffers(_this, ((SDL_WindowData *) window->driverdata)->egl_surface);
+    if (emscripten_has_asyncify()) {
+        /* give back control to browser for screen refresh */
+        emscripten_sleep(0);
+    }
+    return ret;
+}
+
 void
 Emscripten_GLES_GetDrawableSize(_THIS, SDL_Window * window, int * w, int * h)
 {