husker-dev / openglfx

OpenGL node for JavaFX
Apache License 2.0
86 stars 12 forks source link

JOGL initialization fail on macOS #22

Open husker-dev opened 2 years ago

husker-dev commented 2 years ago

Since there are restrictions on creating an GL context on macOS, JOGL cannot be initialized - it fails on GLProfile creation in the GLProfile.initSingleton method.

I tried to figure out the exact location of the error, but I don't have a macOS device to proper check. Debug in JOGL also does not provide additional information.

Theoretical error: JOGL tries to create an NSOpenGLView in not main thread, and fails. In ideal scenario, context should be created through CGL

Sample code from sources:

val profile = GLProfile.getDefault() // << Frozen here
val context = GLDrawableFactory.getFactory(profile).createExternalGLContext()
Devan-Kerman commented 2 years ago

To my knowledge this has something to do with creating multiple contexts on macOS specifically, it's likely the same bug that causes opening a jframe alongside a GL application to fail on macOS. Something about either one thread stealing all the events, or macOS just being unable to have multiple threads with contexts.

Devan-Kerman commented 2 years ago

https://github.com/LWJGL/lwjgl3/issues/697

husker-dev commented 1 year ago

I don't think there is a simple solution to this problem.

Why is this happening?

To obtain any information about OpenGL, you need to create a context. For example, to get pointers to functions (for Windows) or the version of OpenGL itself. This is all done by JOGL and LWJGL.

Why doesn't this cause problems in LWJGL?

LWJGL does not take responsibility for creating the context. When calling GL.createCapabilities(), it is assumed that the context has already been created and is the current one. This allows us to use our own ways of creating context through GLFW, EGL, or even manually create it natively for each platform, as is done in this library.

Why can't this be bypassed in JOGL?

JOGL, unlike LWJGL, provides simpler obstructions for OpenGL. Whenever the library is used, it loads singleton classes. They contain the getting of basic information, which forces the creation of context.

Why does the error occur specifically on macOS?

As mentioned earlier, JOGL creates its own context. But does it not quite right. It uses NSOpenGLView, which require execution in the main application thread. This is the main problem - in LWJGL I can use my extra context creations without being tied to the main thread, but JOGL forces me to use their internal mechanisms.

What can be done?

Perhaps someone has dealt with such a problem and can suggest a solution. But so far I don't know how to get around this.

So, use LWJGL :)

husker-dev commented 5 months ago

Possible solution is to use performSelectorOnMainThread. This allows some code to be executed in the main thread of the process. AWT uses this function to initialize their API. But it needs to be testes with JavaFX.

I'm going to add this feature to the offscreen-jgl v2.