Use QT with Opencascade in WebAssembly

Hi.

I'm currently trying to use Opencascade within a Qt Application with QML in WebAssembly, and i was wondering if it was possible to achieve this. 

since i can't use the OpenGl_GraphicDriver->Init() method, giving me this error in the console output of Chrome :

exception thrown: TypeError: Cannot read property 'getContext' of undefined,TypeError: Cannot read property 'getContext' of undefined

Qt initialize the OpenGL Context, then i try with an QQuickItem, to integrate Opencascade on the beforeSynchronizing

The solution should reside in the SetWindow() of V3d_View and specifying the EGLContext as Aspect_RenderingContext, i saw a cast in the OCCT sources of Aspect_RenderingContext into EGLContext. 

m_view->SetWindow (aWindow,(Aspect_RenderingContext) theEGLContext);

However i'm having trouble getting the EGLContext from the QtApplication. I've tried to get it in several ways, including this one :

EGLContext ctx = eglGetCurrentContext(); 
// == EGL_NO_CONTEXT

or trying to recover it using the QEGLNativeContext.

Is there a way i didn't think of, for using Qt with Opencascade or did someone already tried something similar ?

Thanks for your help,

Best regards.

Kirill Gavrilov's picture

There are two ways for binding to WebGL context using Emscripten SDK - via EGL and via emscripten_webgl_create_context(). The first one is cross-platform and used by OCCT, while the latter one is platform-specific and provides additional features.

It should be noted that elements of EGL implementation in Emscripten SDK are stubs, which means that there behavior might be found confusing and misleading compared to other platforms. It is technically possible mixing EGL and emscripten_webgl calls within the same application, but such combination may require extra attention. In particular, if Qt create WebGL context using emscripten_webgl_create_context() API, then eglGetCurrentContext() would return EGL_NO_CONTEXT, because EGL initialization has not been done by Qt at all! At the same time, you may just try creating EGL context (what OCCT does by default) and it may success - practically wrapping (instead of creating new one) the same canvas element and the same existing WebGL context! Things become much more complicated if application considers using more than a single canvas + WebGL context at the same time - Emscripten SDK initially supported only single global context, and later on has been improved to support multiple, but this require considerable changes in C++/JavaScript application. For the moment, I haven't investigated utilization of multiple contexts, but it is quite possible that Qt developers already support them (which might require additional changes to reused context in OCCT viewer).

So first thing that might be useful to check is how Qt currently implements integration with WebGL.

Emmanuel BIGEON's picture

Hi,

Thank you for this thorough answer !

Qt doesn't use EGL methods to iniatilize its WebGL context, and i can only recover the EMSCRIPTEN_WEBGL_CONTEXT_HANDLE from it using emscripten_webgl_get_current_context() but it doesn't solved my problem because i need an EGLContext.

So I tried to create/recover the WebGL Context using EGL right after QT/QML is running (i still don't know if EGL reuses the same context or create another one) however it didn't worked and failed at the eglcreatecontext() step. Printing errors like get property from undefined in the qtloader.js file.

The next thing i checked, was if i could have a WebGL Context and EGLContext at the same time. In this order of initialization : WebGL then EGLContext and it worked !

So technically speaking, it seems possible but using QT is complicating things a lot. I can't use the modularize option because it instanciate the webgl context with the index.js and Qt doesn't like that.

set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -s MODULARIZE=1")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -s EXPORT_NAME='createModule'")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --extern-post-js ../index.js")

 At this point, Qt implementation of WebAssembly is the real problem and i'm gonna search for a way in the next couple days to recover an EGLContext from Qt Wasm.

Thank you for your explanation,

Best regards.

Vico's picture

Why not report this issue to QT https://bugreports.qt.io ? It should be an issue of QT.

Emmanuel BIGEON's picture

Hi,

I did, a long time ago, but QT doesn't seems to answer.
https://forum.qt.io/topic/126789/qt-webassembly-get-eglcontext-from-qapp...

Best regards.