diff options
author | Sven Gothel <[email protected]> | 2019-07-08 05:11:56 +0200 |
---|---|---|
committer | Sven Gothel <[email protected]> | 2019-07-08 05:11:56 +0200 |
commit | 004c67c73a0309158c30929cd0d6513e23f34803 (patch) | |
tree | 0db0ee261fa3cf87aa87ab95c7417847ceda0554 /src | |
parent | 0f97d9292cc7ff97f61f68b69c5a375cc023a5af (diff) |
NEWT iOS WindowDriver: native UIWindow/UIView creation change
Astonishingly, the original code path doesn't show up the CAEAGL View/Layer (only the red test background)
even though t is 1:1 equal to this alternative calls.
Keeping the original path intact for future validation, another round of hours of analysis.
The original code path will be removed in the next commit.
Diffstat (limited to 'src')
-rw-r--r-- | src/newt/classes/jogamp/newt/driver/ios/WindowDriver.java | 69 | ||||
-rw-r--r-- | src/newt/native/IOSWindow.m | 103 |
2 files changed, 159 insertions, 13 deletions
diff --git a/src/newt/classes/jogamp/newt/driver/ios/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/ios/WindowDriver.java index 5469f74b1..39e3edc72 100644 --- a/src/newt/classes/jogamp/newt/driver/ios/WindowDriver.java +++ b/src/newt/classes/jogamp/newt/driver/ios/WindowDriver.java @@ -694,41 +694,52 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl // Internals only // + /** + * Astonishingly, the original code path doesn't show up the CAEAGL View/Layer (only the red test background) + * even though the it is 1:1 equal to the alternative calls. + * Keeping the original path intact for future validation, another round of hours of analysis. + */ + private static final boolean altCreateWindow = true; + private void createWindow(final boolean offscreenInstance, final boolean recreate, final PointImmutable pS, final int width, final int height, final int flags) { final long parentWinHandle = getParentWindowHandle(); - final long preWinHandle = getWindowHandle(); + final long oldWinHandle = getWindowHandle(); if(DEBUG_IMPLEMENTATION) { System.err.println("MacWindow.createWindow on thread "+Thread.currentThread().getName()+ ": offscreen "+offscreenInstance+", recreate "+recreate+ ", pS "+pS+", "+width+"x"+height+", state "+getReconfigStateMaskString(flags)+ - ", preWinHandle "+toHexString(preWinHandle)+", parentWin "+toHexString(parentWinHandle)+ + ", preWinHandle "+toHexString(oldWinHandle)+", parentWin "+toHexString(parentWinHandle)+ ", surfaceHandle "+toHexString(surfaceHandle)); // Thread.dumpStack(); } try { - if( 0 != preWinHandle ) { + if( 0 != oldWinHandle ) { setWindowHandle(0); if( 0 == surfaceHandle ) { throw new NativeWindowException("Internal Error - create w/ window, but no Newt NSView"); } - IOSUtil.RunOnMainThread(false, false /* kickNSApp */, new Runnable() { - @Override - public void run() { - changeContentView0(parentWinHandle, preWinHandle, 0); - close0( preWinHandle ); - } }); + if( !altCreateWindow ) { + IOSUtil.RunOnMainThread(false, false /* kickNSApp */, new Runnable() { + @Override + public void run() { + changeContentView0(parentWinHandle, oldWinHandle, 0); + close0( oldWinHandle ); + } }); + } } else { if( 0 != surfaceHandle ) { throw new NativeWindowException("Internal Error - create w/o window, but has Newt NSView"); } - surfaceHandle = createView0(pS.getX(), pS.getY(), width, height); - if( 0 == surfaceHandle ) { - throw new NativeWindowException("Could not create native view "+Thread.currentThread().getName()+" "+this); + if( !altCreateWindow ) { + surfaceHandle = createView0(pS.getX(), pS.getY(), width, height, reqPixelScale[0]); + if( 0 == surfaceHandle ) { + throw new NativeWindowException("Could not create native view "+Thread.currentThread().getName()+" "+this); + } } } @@ -750,6 +761,34 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl IOSUtil.RunOnMainThread(true, false /* kickNSApp */, new Runnable() { @Override public void run() { + if( altCreateWindow ) { + /** + * Does everything at once, same as original code path: + * 1) if oldWinHandle: changeContentView (detaching view) + close0(oldWindHandle) + * 2) create new window + * 3) create new view if previous didn't exist (oldWinHandle) + * 4) changeContentView (attaching view) etc .. + */ + final boolean isOpaque = getGraphicsConfiguration().getChosenCapabilities().isBackgroundOpaque() && !offscreenInstance; + newWin[0] = createWindow1( oldWinHandle, parentWinHandle, pS.getX(), pS.getY(), width, height, reqPixelScale[0], + 0 != ( STATE_MASK_FULLSCREEN & flags), + windowStyle, NSBackingStoreBuffered, + isOpaque, + !offscreenInstance && 0 != ( STATE_MASK_ALWAYSONTOP & flags), + !offscreenInstance && 0 != ( STATE_MASK_ALWAYSONBOTTOM & flags), + !offscreenInstance && 0 != ( STATE_MASK_VISIBLE & flags), + surfaceHandle); + final long uiView = IOSUtil.GetUIView(newWin[0], true); + surfaceHandle = uiView; + + if( offscreenInstance ) { + orderOut0(0!=parentWinHandle ? parentWinHandle : newWin[0]); + } else { + setTitle0(newWin[0], getTitle()); + } + + } else { + newWin[0] = createWindow0( pS.getX(), pS.getY(), width, height, 0 != ( STATE_MASK_FULLSCREEN & flags), windowStyle, @@ -768,9 +807,10 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl setTitle0(newWin[0], getTitle()); } } + } } }); - if ( newWin[0] == 0 ) { + if ( newWin[0] == 0 || 0 == surfaceHandle ) { throw new NativeWindowException("Could not create native window "+Thread.currentThread().getName()+" "+this); } setWindowHandle( newWin[0] ); @@ -785,6 +825,9 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl /** Must be called on Main-Thread */ private native void initWindow0(long parentWindow, long window, int x, int y, int w, int h, float reqPixelScale, boolean opaque, boolean atop, boolean abottom, boolean visible, long view); + private native long createWindow1(long oldWindow, long parentWindow, int x, int y, int w, int h, float reqPixelScale, + boolean fullscreen, int windowStyle, int backingStoreType, + boolean opaque, boolean atop, boolean abottom, boolean visible, long view); private native int getDisplayID0(long window); private native void setPixelScale0(long window, long view, float reqPixelScale); diff --git a/src/newt/native/IOSWindow.m b/src/newt/native/IOSWindow.m index 4778fed96..4c50b0e87 100644 --- a/src/newt/native/IOSWindow.m +++ b/src/newt/native/IOSWindow.m @@ -517,6 +517,109 @@ JNIEXPORT jlong JNICALL Java_jogamp_newt_driver_ios_WindowDriver_createWindow0 return (jlong) ((intptr_t) myWindow); } +#ifdef VERBOSE_ON + #define DBG_PRINT_CREATEWIN1(n) NSLog(@"createWindow1.%d - parent(win %p scale %f, view %p scale %f), window %p (scale %f, superview %p, hidden %d), view: %p (scale %f, superview %p, hidden %d), CAEAGLLayer %p (opaque %d, scale %f, isCAEAGLLayer %d, hidden %d)\n", \ + (n), parentWindow, (NULL!=parentWindow?[parentWindow contentScaleFactor]:0.0f), parentView, (NULL!=parentView?[parentView contentScaleFactor]:0.0f), \ + myWindow, [myWindow contentScaleFactor], [myWindow superview], [myWindow isHidden], \ + myView, [myView contentScaleFactor], [myView superview], [myView isHidden], \ + l, [l isOpaque], [l contentsScale], [l isKindOfClass:[CAEAGLLayer class]], [l isHidden]); fflush(stderr) +#else + #define DBG_PRINT_CREATEWIN1(n) +#endif + +/** + * Class: jogamp_newt_driver_ios_WindowDriver + * Method: createWindow1 + * Signature: (JJIIIIFZZZZJ)J + */ +JNIEXPORT jlong JNICALL Java_jogamp_newt_driver_ios_WindowDriver_createWindow1 + (JNIEnv *env, jobject jthis, jlong joldwin, jlong jparent, jint x, jint y, jint w, jint h, jfloat reqPixelScale, + jboolean fullscreen, jint styleMask, jint bufferingType, + jboolean opaque, jboolean atop, jboolean abottom, jboolean visible, jlong jview) +{ + NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init]; + [CATransaction begin]; + + NewtUIWindow* oldWindow = (NewtUIWindow*) (intptr_t) joldwin ; + NewtUIView* myView = (NewtUIView*) (intptr_t) jview ; + + NSObject* nsParentObj = (NSObject*) ((intptr_t) jparent); + UIWindow* parentWindow = NULL; + UIView* parentView = NULL; + if( nsParentObj != NULL && [nsParentObj isKindOfClass:[UIWindow class]] ) { + parentWindow = (UIWindow*) nsParentObj; + parentView = (UIView*)nsParentObj; + DBG_PRINT( "createWindow1 - Parent is UIWindow : %p (win) -> %p (view) \n", parentWindow, parentView); + } else if( nsParentObj != NULL && [nsParentObj isKindOfClass:[UIView class]] ) { + parentView = (UIView*) nsParentObj; + parentWindow = [parentView window]; + DBG_PRINT( "createWindow1 - Parent is UIView : %p -(view) > %p (win) \n", parentView, parentWindow); + } else { + DBG_PRINT( "createWindow1 - Parent is neither UIWindow nor UIView : %p\n", nsParentObj); + } + DBG_PRINT( "createWindow1.0 - %p (this), oldWin %p, parent(win %p, view %p), oldView %p, %d/%d %dx%d, reqPixelScale %f, fullscreen %d, opaque %d, atop %d, abottom %d, visible %d (START)\n", + (void*)(intptr_t)jthis, oldWindow, parentWindow, parentView, myView, (int)x, (int)y, (int)w, (int)h, (float)reqPixelScale, + fullscreen, opaque, atop, abottom, visible); + + if( NULL != oldWindow ) { + if( NULL == myView ) { + NewtCommon_throwNewRuntimeException(env, "oldWindow %p given but no view %p (this %p)", oldWindow, myView, (void*)(intptr_t)jthis); + } + changeContentView(env, jthis, parentView, oldWindow, NULL, NO); + Java_jogamp_newt_driver_ios_WindowDriver_close0(env, NULL, joldwin); + } else if( NULL != myView ) { + NewtCommon_throwNewRuntimeException(env, "view %p given but no oldWindow %p (this %p)", oldWindow, myView, (void*)(intptr_t)jthis); + } + CGRect rectWin = CGRectMake(x, y, w, h); + NewtUIWindow* myWindow = [[[[NewtUIWindow alloc] initWithFrame: rectWin + styleMask: (NSUInteger) styleMask + backing: 0 // TODO (NSBackingStoreType) bufferingType + defer: YES + isFullscreenWindow: fullscreen] autorelease] retain]; + [myWindow setBackgroundColor: [UIColor redColor]]; + if( visible ) { + // Only if calling this before adding the view, the view receives touch events. + // Another 'funny' iOS API nightmare? + [myWindow makeKeyAndVisible]; + } + DBG_PRINT( "createWindow1.1 - window %p, isHidden %d, rootViewController %p\n", myWindow, [myWindow isHidden], myWindow.rootViewController); + + CGRect rectView = CGRectMake(0, 0, w, h); + if( NULL == myView ) { + myView = [[NewtUIView alloc] initWithFrame: rectView] ; + } + CAEAGLLayer* l = (CAEAGLLayer*)[myView layer]; + DBG_PRINT_CREATEWIN1(2); + + changeContentView(env, jthis, parentView, myWindow, myView, NO); + DBG_PRINT_CREATEWIN1(3); + + if(NULL!=parentWindow) { + [myWindow attachToParent: parentWindow]; + } + DBG_PRINT_CREATEWIN1(4); + + // Immediately re-position this window based on an upper-left coordinate system + setWindowClientTopLeftPointAndSize(myWindow, x, y, w, h, NO); + // SEE comment above at makeKeyAndVisible call + // if( visible ) { + // [myWindow makeKeyAndVisible]; + // } + DBG_PRINT_CREATEWIN1(5); + + [myView setDestroyNotifySent: false]; + setJavaWindowObject(env, jthis, myView); + DBG_PRINT_CREATEWIN1(6); + + [myWindow setPixelScale: (CGFloat)reqPixelScale defer:NO]; + DBG_PRINT_CREATEWIN1(88); + + [CATransaction commit]; + [pool release]; + + return (jlong) (intptr_t) myWindow; +} + JNIEXPORT jint JNICALL Java_jogamp_newt_driver_ios_WindowDriver_getDisplayID0(JNIEnv *env, jobject jthis, jlong window) { NewtUIWindow* myWindow = (NewtUIWindow*) ((intptr_t) window); if( NULL == myWindow ) { |