diff options
3 files changed, 124 insertions, 1 deletions
diff --git a/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.h b/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.h index 2631e63022d..85bef5f9be5 100644 --- a/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.h +++ b/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.h @@ -47,6 +47,7 @@ jint preFullScreenLevel; NSRect standardFrame; BOOL isMinimizing; + NSWindowTabbingMode javaWindowTabbingMode; } // An instance of either AWTWindow_Normal or AWTWindow_Panel @@ -62,6 +63,7 @@ @property (nonatomic) jint preFullScreenLevel; @property (nonatomic) NSRect standardFrame; @property (nonatomic) BOOL isMinimizing; +@property (nonatomic) NSWindowTabbingMode javaWindowTabbingMode; - (id) initWithPlatformWindow:(JNFWeakJObjectWrapper *)javaPlatformWindow ownerWindow:owner @@ -71,6 +73,8 @@ - (BOOL) isTopmostWindowUnderMouse; +- (NSWindowTabbingMode) getJavaWindowTabbingMode; + // NSWindow overrides delegate methods - (BOOL) canBecomeKeyWindow; - (void) becomeKeyWindow; diff --git a/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.m b/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.m index f4bafaf88b2..27ae9304849 100644 --- a/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.m +++ b/src/java.desktop/macosx/native/libawt_lwawt/awt/AWTWindow.m @@ -113,7 +113,7 @@ static NSPoint lastTopLeftPoint; } \ \ - (NSWindowTabbingMode)tabbingMode { \ - return NSWindowTabbingModeDisallowed; \ + return ((AWTWindow*)[self delegate]).javaWindowTabbingMode; \ } @implementation AWTWindow_Normal @@ -200,6 +200,62 @@ AWT_NS_WINDOW_IMPLEMENTATION ]; } +- (void)moveTabToNewWindow:(id)sender { + AWT_ASSERT_APPKIT_THREAD; + + [super moveTabToNewWindow:sender]; + + JNIEnv *env = [ThreadUtilities getJNIEnv]; + jobject platformWindow = [((AWTWindow *)self.delegate).javaPlatformWindow jObjectWithEnv:env]; + if (platformWindow != NULL) { + // extract the target AWT Window object out of the CPlatformWindow + static JNF_MEMBER_CACHE(jf_target, jc_CPlatformWindow, "target", "Ljava/awt/Window;"); + jobject awtWindow = JNFGetObjectField(env, platformWindow, jf_target); + if (awtWindow != NULL) { + static JNF_CLASS_CACHE(jc_Window, "java/awt/Window"); + static JNF_MEMBER_CACHE(jm_runMoveTabToNewWindowCallback, jc_Window, "runMoveTabToNewWindowCallback", "()V"); + JNFCallVoidMethod(env, awtWindow, jm_runMoveTabToNewWindowCallback); + (*env)->DeleteLocalRef(env, awtWindow); + } + (*env)->DeleteLocalRef(env, platformWindow); + } + +#ifdef DEBUG + NSLog(@"=== Move Tab to new Window ==="); +#endif +} + +// Call over Foundation from Java +- (CGFloat) getTabBarVisibleAndHeight { + if ([self respondsToSelector:@selector(tabGroup)]) { // API_AVAILABLE(macos(10.13)) + id tabGroup = [self tabGroup]; +#ifdef DEBUG + NSLog(@"=== Window tabBar: %@ ===", tabGroup); +#endif + if ([tabGroup isTabBarVisible]) { + if ([tabGroup respondsToSelector:@selector(_tabBar)]) { // private member + CGFloat height = [[tabGroup _tabBar] frame].size.height; +#ifdef DEBUG + NSLog(@"=== Window tabBar visible: %f ===", height); +#endif + return height; + } +#ifdef DEBUG + NSLog(@"=== NsWindow.tabGroup._tabBar not found ==="); +#endif + return -1; // if we don't get height return -1 and use default value in java without change native code + } +#ifdef DEBUG + NSLog(@"=== Window tabBar not visible ==="); +#endif + } else { +#ifdef DEBUG + NSLog(@"=== Window tabBar not found ==="); +#endif + } + return 0; +} + @end @implementation AWTWindow_Panel AWT_NS_WINDOW_IMPLEMENTATION @@ -221,6 +277,7 @@ AWT_NS_WINDOW_IMPLEMENTATION @synthesize preFullScreenLevel; @synthesize standardFrame; @synthesize isMinimizing; +@synthesize javaWindowTabbingMode; - (void) updateMinMaxSize:(BOOL)resizable { if (resizable) { @@ -369,6 +426,8 @@ AWT_ASSERT_APPKIT_THREAD; [self.nsWindow setTitleVisibility:NSWindowTitleHidden]; } + self.javaWindowTabbingMode = [self getJavaWindowTabbingMode]; + return self; } @@ -386,6 +445,33 @@ AWT_ASSERT_APPKIT_THREAD; return [self.nsWindow windowNumber] == [AWTWindow getTopmostWindowUnderMouseID]; } +- (NSWindowTabbingMode) getJavaWindowTabbingMode { + AWT_ASSERT_APPKIT_THREAD; + + BOOL result = NO; + + JNIEnv *env = [ThreadUtilities getJNIEnv]; + jobject platformWindow = [self.javaPlatformWindow jObjectWithEnv:env]; + if (platformWindow != NULL) { + // extract the target AWT Window object out of the CPlatformWindow + static JNF_MEMBER_CACHE(jf_target, jc_CPlatformWindow, "target", "Ljava/awt/Window;"); + jobject awtWindow = JNFGetObjectField(env, platformWindow, jf_target); + if (awtWindow != NULL) { + static JNF_CLASS_CACHE(jc_Window, "java/awt/Window"); + static JNF_MEMBER_CACHE(jm_hasTabbingMode, jc_Window, "hasTabbingMode", "()Z"); + result = JNFCallBooleanMethod(env, awtWindow, jm_hasTabbingMode) == JNI_TRUE ? YES : NO; + (*env)->DeleteLocalRef(env, awtWindow); + } + (*env)->DeleteLocalRef(env, platformWindow); + } + +#ifdef DEBUG + NSLog(@"=== getJavaWindowTabbingMode: %d ===", result); +#endif + + return result ? NSWindowTabbingModeAutomatic : NSWindowTabbingModeDisallowed; +} + + (AWTWindow *) getTopmostWindowUnderMouse { NSEnumerator *windowEnumerator = [[NSApp windows] objectEnumerator]; NSWindow *window; diff --git a/src/java.desktop/share/classes/java/awt/Window.java b/src/java.desktop/share/classes/java/awt/Window.java index f6030fc1ece..5529546608d 100644 --- a/src/java.desktop/share/classes/java/awt/Window.java +++ b/src/java.desktop/share/classes/java/awt/Window.java @@ -4004,6 +4004,39 @@ public class Window extends Container implements Accessible { ignoreMouseEvents = ignore; } + private volatile boolean hasTabbingMode; + + boolean hasTabbingMode() { + return hasTabbingMode; + } + + /** + * Set via reflection (JB JdkEx API). + */ + void setTabbingMode() { + hasTabbingMode = true; + } + + private volatile Runnable moveTabToNewWindowCallback; + + void runMoveTabToNewWindowCallback() { + if (moveTabToNewWindowCallback != null) { + Runnable callback = moveTabToNewWindowCallback; + SunToolkit.executeOnEventHandlerThread(this, new Runnable() { + public void run() { + callback.run(); + } + }); + } + } + + /** + * Set via reflection (JB JdkEx API). + */ + void setMoveTabToNewWindowCallback(Runnable moveTabToNewWindowCallback) { + this.moveTabToNewWindowCallback = moveTabToNewWindowCallback; + } + // ************************** MIXING CODE ******************************* // A window has an owner, but it does NOT have a container |