summaryrefslogtreecommitdiffstats
path: root/src/corelib/kernel/qeventdispatcher_wasm.cpp
diff options
context:
space:
mode:
authorMorten Sørvig <morten.sorvig@qt.io>2023-12-07 12:11:23 +0100
committerMorten Sørvig <morten.sorvig@qt.io>2023-12-18 23:07:07 +0100
commitf2e227742fe90d2420ab433ae18449f46a210ae8 (patch)
treee0e1fbe300bed9cb72d868d98cd4f0c66605110b /src/corelib/kernel/qeventdispatcher_wasm.cpp
parent37b3cc65499fb9332f9b9ed539bb279217682b1d (diff)
wasm: delay "qtLoaded" qtloader.js event
Currently we send qtLoaded in response to Emscripten onRuntimeInitialized, which is sent just before or at the time main() is called. This can be too early if Qt (app) initialization is not instantaneous, in which case we risk displaying a blank page in between hiding the loading screen and showing the application. Change this to send qtLoaded when QCoreApplication has finished its constructor and the event loop is running. Also add the possibility of registering startup tasks which can delay sending qtLoaded further. We now require a QCoreApplication (or a subclass) instance for the qtLoaded event. onRuntimeInitialized can be used as a replacement if anyone needs the previous behavior. Change-Id: I9298e881d2909aac4040c5f2068e6c7d196196cc Reviewed-by: Lorn Potter <lorn.potter@gmail.com>
Diffstat (limited to 'src/corelib/kernel/qeventdispatcher_wasm.cpp')
-rw-r--r--src/corelib/kernel/qeventdispatcher_wasm.cpp42
1 files changed, 42 insertions, 0 deletions
diff --git a/src/corelib/kernel/qeventdispatcher_wasm.cpp b/src/corelib/kernel/qeventdispatcher_wasm.cpp
index cc24b5ff7c..aa44158551 100644
--- a/src/corelib/kernel/qeventdispatcher_wasm.cpp
+++ b/src/corelib/kernel/qeventdispatcher_wasm.cpp
@@ -217,6 +217,9 @@ QEventDispatcherWasm::QEventDispatcherWasm()
#if QT_CONFIG(thread)
g_mainThread = pthread_self();
#endif
+ // Call the "onLoaded" JavaScript callback, unless startup tasks
+ // have been registered which should complete first.
+ checkCallQtLoaded();
} else {
#if QT_CONFIG(thread)
std::lock_guard<std::mutex> lock(g_staticDataMutex);
@@ -895,6 +898,45 @@ void QEventDispatcherWasm::socketSelect(int timeout, int socket, bool waitForRea
}
namespace {
+ int g_startupTasks = 0;
+}
+
+// The following functions manages sending the "qtLoaded" event/callback
+// from qtloader.js on startup, once Qt initialization has been completed
+// and the application is ready to display the first frame. This can be
+// either as soon as the event loop is running, or later, if additional
+// startup tasks (e.g. local font loading) have been registered.
+
+void QEventDispatcherWasm::registerStartupTask()
+{
+ ++g_startupTasks;
+}
+
+void QEventDispatcherWasm::completeStarupTask()
+{
+ --g_startupTasks;
+ checkCallQtLoaded();
+}
+
+void QEventDispatcherWasm::checkCallQtLoaded()
+{
+ if (g_startupTasks > 0)
+ return;
+
+ static bool qtLoadedCalled = false;
+ if (qtLoadedCalled)
+ return;
+ qtLoadedCalled = true;
+
+ QTimer::singleShot(0, [](){
+ emscripten::val qt = emscripten::val::module_property("qt");
+ if (qt.isUndefined())
+ return;
+ qt.call<void>("onLoaded");
+ });
+}
+
+namespace {
void trampoline(void *context) {
auto async_fn = [](void *context){