< prev index next >

src/java.desktop/macosx/native/libosxui/ScreenMenu.m

Print this page
rev 54094 : 8257853: Remove dependencies on JNF's JNI utility functions in AWT and 2D code
rev 54096 : 8259651: [macOS] Replace JNF_COCOA_ENTER/EXIT macros
rev 54097 : 8259869: [macOS] Remove desktop module dependencies on JNF Reference APIs
rev 54098 : 8260616: Removing remaining JNF dependencies in the java.desktop module
8259729: Missed JNFInstanceOf -> IsInstanceOf conversion


  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 #import "ScreenMenu.h"
  27 
  28 #import "com_apple_laf_ScreenMenu.h"
  29 #import "java_awt_Event.h"
  30 #import "java_awt_event_KeyEvent.h"
  31 #import "java_awt_event_InputEvent.h"
  32 #import "java_awt_event_MouseEvent.h"
  33 
  34 #import <JavaNativeFoundation/JavaNativeFoundation.h>
  35 #import <JavaRuntimeSupport/JavaRuntimeSupport.h>
  36 
  37 #import "ThreadUtilities.h"
  38 #import "CMenuBar.h"

  39 
  40 static JNF_CLASS_CACHE(sjc_ScreenMenu, "com/apple/laf/ScreenMenu");


  41 
  42 static jint ns2awtModifiers(NSUInteger keyMods) {
  43     jint result = 0;
  44     if (keyMods & NSShiftKeyMask)        result |= java_awt_Event_SHIFT_MASK;
  45     if (keyMods & NSControlKeyMask)        result |= java_awt_Event_CTRL_MASK;
  46     if (keyMods & NSAlternateKeyMask)    result |= java_awt_Event_ALT_MASK;
  47     if (keyMods & NSCommandKeyMask)        result |= java_awt_Event_META_MASK;
  48     return result;
  49 }
  50 
  51 static jint ns2awtMouseButton(NSInteger mouseButton) {
  52     switch (mouseButton) {
  53         case 1: return java_awt_event_InputEvent_BUTTON1_MASK;
  54         case 2: return java_awt_event_InputEvent_BUTTON2_MASK;
  55         case 3: return java_awt_event_InputEvent_BUTTON3_MASK;
  56     }
  57     return 0;
  58 }
  59 
  60 
  61 @interface NativeToJavaDelegate : NSObject <JRSMenuDelegate, NSMenuDelegate>
  62 {
  63 @public
  64     NSMenu *nsmenu;
  65     JNFJObjectWrapper *javaObjectWrapper;
  66 }
  67 
  68 @property (nonatomic, retain) NSMenu *nsmenu;
  69 @property (nonatomic, retain) JNFJObjectWrapper *javaObjectWrapper;
  70 
  71 - (id)initFromMenu:(NSMenu *)menu javaObj:(JNFJObjectWrapper *)obj;
  72 - (NSMenu*)menu;
  73 @end
  74 
  75 
  76 @implementation NativeToJavaDelegate
  77 
  78 @synthesize nsmenu;
  79 @synthesize javaObjectWrapper;
  80 
  81 - (id)initFromMenu:(NSMenu *)aMenu javaObj:(JNFJObjectWrapper *)obj
  82 {
  83     self = [super init];
  84     if (self) {
  85         self.nsmenu = aMenu;
  86         self.javaObjectWrapper = obj;
  87     }
  88     return self;
  89 }
  90 
  91 - (NSMenu *)menu {
  92     return self.nsmenu;
  93 }
  94 
  95 - (void)menuWillOpen:(NSMenu *)menu
  96 {
  97     if (self.javaObjectWrapper == nil) {
  98 #ifdef DEBUG
  99         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 100 #endif
 101         return;
 102     }
 103 
 104     JNIEnv *env = [ThreadUtilities getJNIEnv];
 105 JNF_COCOA_ENTER(env);
 106     //NSLog(@"menuWillOpen %@", [menu title]);
 107     static JNF_MEMBER_CACHE(jm_ScreenMenu_invokeOpenLater, sjc_ScreenMenu, "invokeOpenLater", "()V");
 108     JNFCallVoidMethod(env, [self.javaObjectWrapper jObject], jm_ScreenMenu_invokeOpenLater); // AWT_THREADING Safe (AWTRunLoopMode)
 109 JNF_COCOA_EXIT(env);


 110 
 111 }
 112 
 113 - (void)menuDidClose:(NSMenu *)menu
 114 {
 115     if (self.javaObjectWrapper == nil) {
 116 #ifdef DEBUG
 117         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 118 #endif
 119         return;
 120     }
 121 
 122     JNIEnv *env = [ThreadUtilities getJNIEnv];
 123 JNF_COCOA_ENTER(env);
 124     //NSLog(@"menuDidClose %@", [menu title]);
 125     static JNF_MEMBER_CACHE(jm_ScreenMenu_invokeMenuClosing, sjc_ScreenMenu, "invokeMenuClosing", "()V");
 126     JNFCallVoidMethod(env, [self.javaObjectWrapper jObject], jm_ScreenMenu_invokeMenuClosing); // AWT_THREADING Safe (AWTRunLoopMode)
 127 JNF_COCOA_EXIT(env);


 128 }
 129 
 130 
 131 - (void)handleJavaMenuItemTargetedAtIndex:(NSUInteger)menuIndex rect:(NSRect)rect
 132 {
 133     if (self.javaObjectWrapper == nil) {
 134 #ifdef DEBUG
 135         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 136 #endif
 137         return;
 138     }
 139 
 140     JNIEnv *env = [ThreadUtilities getJNIEnv];
 141 JNF_COCOA_ENTER(env);
 142     // Send that to Java so we can test which item was hit.
 143     static JNF_MEMBER_CACHE(jm_ScreenMenu_updateSelectedItem, sjc_ScreenMenu, "handleItemTargeted", "(IIIII)V");
 144     JNFCallVoidMethod(env, [self.javaObjectWrapper jObject], jm_ScreenMenu_updateSelectedItem, menuIndex,
 145                     NSMinY(rect), NSMinX(rect), NSMaxY(rect), NSMaxX(rect)); // AWT_THREADING Safe (AWTRunLoopMode)


 146 
 147 JNF_COCOA_EXIT(env);
 148 }
 149 










 150 
 151 // Called from event handler callback
 152 - (void)handleJavaMouseEvent:(NSEvent *)event
 153 {
 154     NSInteger kind = [event type];
 155     jint javaKind = 0;
 156 
 157     switch (kind) {
 158         case NSLeftMouseUp: case NSRightMouseUp: case NSOtherMouseUp:
 159             javaKind = java_awt_event_MouseEvent_MOUSE_RELEASED;
 160             break;
 161         case NSLeftMouseDown: case NSRightMouseDown: case NSOtherMouseDown:
 162             javaKind = java_awt_event_MouseEvent_MOUSE_PRESSED;
 163             break;
 164         case NSMouseMoved:
 165             javaKind = java_awt_event_MouseEvent_MOUSE_MOVED;
 166             break;
 167         case NSLeftMouseDragged: case NSRightMouseDragged: case NSOtherMouseDragged:
 168             javaKind = java_awt_event_MouseEvent_MOUSE_DRAGGED;
 169             break;
 170     }
 171 
 172     // Get the coordinates of the mouse in global coordinates (must be global, since our tracking rects are global.)
 173     NSPoint globalPoint = [event locationInWindow];
 174     jint javaX = globalPoint.x;
 175     jint javaY = globalPoint.y;
 176 
 177     // Convert the event modifiers into Java modifiers
 178     jint javaModifiers = ns2awtModifiers([event modifierFlags]) | ns2awtMouseButton([event buttonNumber]);
 179 
 180     // Get the event time
 181     jlong javaWhen = JNFNSTimeIntervalToJavaMillis([event timestamp]);
 182 
 183     // Call the mouse event handler, which will generate Java mouse events.
 184     JNIEnv *env = [ThreadUtilities getJNIEnv];
 185 JNF_COCOA_ENTER(env);
 186     static JNF_MEMBER_CACHE(jm_ScreenMenu_handleMouseEvent, sjc_ScreenMenu, "handleMouseEvent", "(IIIIJ)V");
 187     JNFCallVoidMethod(env, [self.javaObjectWrapper jObject], jm_ScreenMenu_handleMouseEvent, javaKind, javaX, javaY, javaModifiers, javaWhen); // AWT_THREADING Safe (AWTRunLoopMode)
 188 JNF_COCOA_EXIT(env);



 189 }
 190 
 191 @end
 192 
 193 
 194 /*
 195  * Class:     com_apple_laf_ScreenMenu
 196  * Method:    addMenuListeners
 197  * Signature: (Lcom/apple/laf/ScreenMenu;J[J)V
 198  */
 199 JNIEXPORT jlong JNICALL Java_com_apple_laf_ScreenMenu_addMenuListeners
 200 (JNIEnv *env, jclass clz, jobject listener, jlong nativeMenu)
 201 {
 202     NativeToJavaDelegate *delegate = nil;
 203 
 204 JNF_COCOA_ENTER(env);
 205 
 206     JNFJObjectWrapper *wrapper = [JNFJObjectWrapper wrapperWithJObject:listener withEnv:env];
 207     NSMenu *menu = jlong_to_ptr(nativeMenu);
 208 
 209     delegate = [[[NativeToJavaDelegate alloc] initFromMenu:menu javaObj:wrapper] autorelease];
 210     CFRetain(delegate); // GC
 211 
 212     [JNFRunLoop performOnMainThreadWaiting:YES withBlock:^{
 213         NSMenu *menu = delegate.nsmenu;
 214         if ([menu isJavaMenu]) {
 215             [menu setDelegate:delegate];
 216             [menu setJavaMenuDelegate:delegate];
 217         }
 218     }];
 219 
 220 JNF_COCOA_EXIT(env);
 221 
 222     return ptr_to_jlong(delegate);
 223 }
 224 
 225 /*
 226  * Class:     com_apple_laf_ScreenMenu
 227  * Method:    removeMenuListeners
 228  * Signature: (JJ)V
 229  */
 230 JNIEXPORT void JNICALL Java_com_apple_laf_ScreenMenu_removeMenuListeners
 231 (JNIEnv *env, jclass clz, jlong fModelPtr)
 232 {
 233     if (fModelPtr == 0L) return;
 234 
 235 JNF_COCOA_ENTER(env);
 236 
 237     NativeToJavaDelegate *delegate = (NativeToJavaDelegate *)jlong_to_ptr(fModelPtr);
 238 
 239     [JNFRunLoop performOnMainThreadWaiting:YES withBlock:^{
 240         NSMenu *menu = delegate.nsmenu;
 241         [menu setJavaMenuDelegate:nil];
 242         [menu setDelegate:nil];
 243         delegate.nsmenu = nil;
 244         delegate.javaObjectWrapper = nil;
 245     }];
 246 



 247     CFRelease(delegate); // GC
 248 
 249 JNF_COCOA_EXIT(env);
 250 }


  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 #import "ScreenMenu.h"
  27 
  28 #import "com_apple_laf_ScreenMenu.h"
  29 #import "java_awt_Event.h"
  30 #import "java_awt_event_KeyEvent.h"
  31 #import "java_awt_event_InputEvent.h"
  32 #import "java_awt_event_MouseEvent.h"
  33 

  34 #import <JavaRuntimeSupport/JavaRuntimeSupport.h>
  35 
  36 #import "ThreadUtilities.h"
  37 #import "CMenuBar.h"
  38 #import "JNIUtilities.h"
  39 
  40 static jclass sjc_ScreenMenu = NULL;
  41 #define GET_SCREENMENU_CLASS() \
  42      GET_CLASS(sjc_ScreenMenu, "com/apple/laf/ScreenMenu");
  43 
  44 static jint ns2awtModifiers(NSUInteger keyMods) {
  45     jint result = 0;
  46     if (keyMods & NSShiftKeyMask)        result |= java_awt_Event_SHIFT_MASK;
  47     if (keyMods & NSControlKeyMask)        result |= java_awt_Event_CTRL_MASK;
  48     if (keyMods & NSAlternateKeyMask)    result |= java_awt_Event_ALT_MASK;
  49     if (keyMods & NSCommandKeyMask)        result |= java_awt_Event_META_MASK;
  50     return result;
  51 }
  52 
  53 static jint ns2awtMouseButton(NSInteger mouseButton) {
  54     switch (mouseButton) {
  55         case 1: return java_awt_event_InputEvent_BUTTON1_MASK;
  56         case 2: return java_awt_event_InputEvent_BUTTON2_MASK;
  57         case 3: return java_awt_event_InputEvent_BUTTON3_MASK;
  58     }
  59     return 0;
  60 }
  61 
  62 
  63 @interface NativeToJavaDelegate : NSObject <JRSMenuDelegate, NSMenuDelegate>
  64 {
  65 @public
  66     NSMenu *nsmenu;
  67     jobject javaObject;
  68 }
  69 
  70 @property (nonatomic, retain) NSMenu *nsmenu;
  71 @property (nonatomic) jobject javaObject;
  72 
  73 - (id)initFromMenu:(NSMenu *)menu javaObj:(jobject)obj;
  74 - (NSMenu*)menu;
  75 @end
  76 
  77 
  78 @implementation NativeToJavaDelegate
  79 
  80 @synthesize nsmenu;
  81 @synthesize javaObject;
  82 
  83 - (id)initFromMenu:(NSMenu *)aMenu javaObj:(jobject)obj
  84 {
  85     self = [super init];
  86     if (self) {
  87         self.nsmenu = aMenu;
  88         self.javaObject = obj;
  89     }
  90     return self;
  91 }
  92 
  93 - (NSMenu *)menu {
  94     return self.nsmenu;
  95 }
  96 
  97 - (void)menuWillOpen:(NSMenu *)menu
  98 {
  99     if (self.javaObject == nil) {
 100 #ifdef DEBUG
 101         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 102 #endif
 103         return;
 104     }
 105 
 106     JNIEnv *env = [ThreadUtilities getJNIEnv];
 107 JNI_COCOA_ENTER(env);
 108     //NSLog(@"menuWillOpen %@", [menu title]);
 109     GET_SCREENMENU_CLASS();
 110     DECLARE_METHOD(jm_ScreenMenu_invokeOpenLater, sjc_ScreenMenu, "invokeOpenLater", "()V");
 111     (*env)->CallVoidMethod(env, self.javaObject, jm_ScreenMenu_invokeOpenLater);
 112     CHECK_EXCEPTION();
 113 JNI_COCOA_EXIT(env);
 114 
 115 }
 116 
 117 - (void)menuDidClose:(NSMenu *)menu
 118 {
 119     if (self.javaObject == nil) {
 120 #ifdef DEBUG
 121         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 122 #endif
 123         return;
 124     }
 125 
 126     JNIEnv *env = [ThreadUtilities getJNIEnv];
 127 JNI_COCOA_ENTER(env);
 128     //NSLog(@"menuDidClose %@", [menu title]);
 129     GET_SCREENMENU_CLASS();
 130     DECLARE_METHOD(jm_ScreenMenu_invokeMenuClosing, sjc_ScreenMenu, "invokeMenuClosing", "()V");
 131     (*env)->CallVoidMethod(env, self.javaObject, jm_ScreenMenu_invokeMenuClosing);
 132     CHECK_EXCEPTION();
 133 JNI_COCOA_EXIT(env);
 134 }
 135 
 136 
 137 - (void)handleJavaMenuItemTargetedAtIndex:(NSUInteger)menuIndex rect:(NSRect)rect
 138 {
 139     if (self.javaObject== nil) {
 140 #ifdef DEBUG
 141         NSLog(@"_javaObject is NULL: (%s - %s : %d)", __FILE__, __FUNCTION__, __LINE__);
 142 #endif
 143         return;
 144     }
 145 
 146     JNIEnv *env = [ThreadUtilities getJNIEnv];
 147 JNI_COCOA_ENTER(env);
 148     // Send that to Java so we can test which item was hit.
 149     GET_SCREENMENU_CLASS();
 150     DECLARE_METHOD(jm_ScreenMenu_updateSelectedItem, sjc_ScreenMenu, "handleItemTargeted", "(IIIII)V");
 151     (*env)->CallVoidMethod(env, self.javaObject, jm_ScreenMenu_updateSelectedItem, menuIndex,
 152                     NSMinY(rect), NSMinX(rect), NSMaxY(rect), NSMaxX(rect));
 153     CHECK_EXCEPTION();
 154 
 155 JNI_COCOA_EXIT(env);
 156 }
 157 
 158 /*
 159  * The input is an NSTimeInterval (a double representing seconds and fractions of seconds)
 160  * 0.0 means midnight Jan 1, 2001.
 161  * The output is a Java long representing time in milliseconds since midnight Jan 1st 1970.
 162  * There is a Cocoa constant representing that difference : NSTimeIntervalSince1970
 163  */
 164 static jlong NSTimeIntervalToJavaMilliseconds(NSTimeInterval interval) {
 165     NSTimeInterval interval1970 = interval + NSTimeIntervalSince1970;
 166     return (jlong)(interval1970 * 1000);
 167 }
 168 
 169 // Called from event handler callback
 170 - (void)handleJavaMouseEvent:(NSEvent *)event
 171 {
 172     NSInteger kind = [event type];
 173     jint javaKind = 0;
 174 
 175     switch (kind) {
 176         case NSLeftMouseUp: case NSRightMouseUp: case NSOtherMouseUp:
 177             javaKind = java_awt_event_MouseEvent_MOUSE_RELEASED;
 178             break;
 179         case NSLeftMouseDown: case NSRightMouseDown: case NSOtherMouseDown:
 180             javaKind = java_awt_event_MouseEvent_MOUSE_PRESSED;
 181             break;
 182         case NSMouseMoved:
 183             javaKind = java_awt_event_MouseEvent_MOUSE_MOVED;
 184             break;
 185         case NSLeftMouseDragged: case NSRightMouseDragged: case NSOtherMouseDragged:
 186             javaKind = java_awt_event_MouseEvent_MOUSE_DRAGGED;
 187             break;
 188     }
 189 
 190     // Get the coordinates of the mouse in global coordinates (must be global, since our tracking rects are global.)
 191     NSPoint globalPoint = [event locationInWindow];
 192     jint javaX = globalPoint.x;
 193     jint javaY = globalPoint.y;
 194 
 195     // Convert the event modifiers into Java modifiers
 196     jint javaModifiers = ns2awtModifiers([event modifierFlags]) | ns2awtMouseButton([event buttonNumber]);
 197 
 198     // Get the event time
 199     jlong javaWhen = NSTimeIntervalToJavaMilliseconds([event timestamp]);
 200 
 201     // Call the mouse event handler, which will generate Java mouse events.
 202     JNIEnv *env = [ThreadUtilities getJNIEnv];
 203 JNI_COCOA_ENTER(env);
 204     GET_SCREENMENU_CLASS();
 205     DECLARE_METHOD(jm_ScreenMenu_handleMouseEvent, sjc_ScreenMenu, "handleMouseEvent", "(IIIIJ)V");
 206     (*env)->CallVoidMethod(env, self.javaObject, jm_ScreenMenu_handleMouseEvent,
 207              javaKind, javaX, javaY, javaModifiers, javaWhen);
 208     CHECK_EXCEPTION();
 209 JNI_COCOA_EXIT(env);
 210 }
 211 
 212 @end
 213 
 214 
 215 /*
 216  * Class:     com_apple_laf_ScreenMenu
 217  * Method:    addMenuListeners
 218  * Signature: (Lcom/apple/laf/ScreenMenu;J[J)V
 219  */
 220 JNIEXPORT jlong JNICALL Java_com_apple_laf_ScreenMenu_addMenuListeners
 221 (JNIEnv *env, jclass clz, jobject listener, jlong nativeMenu)
 222 {
 223     NativeToJavaDelegate *delegate = nil;
 224 
 225 JNI_COCOA_ENTER(env);
 226 
 227     jobject listenerRef = (*env)->NewGlobalRef(env, listener);
 228     NSMenu *menu = jlong_to_ptr(nativeMenu);
 229 
 230     delegate = [[[NativeToJavaDelegate alloc] initFromMenu:menu javaObj:listenerRef] autorelease];
 231     CFRetain(delegate); // GC
 232 
 233     [ThreadUtilities performOnMainThreadWaiting:YES block:^{
 234         NSMenu *menu = delegate.nsmenu;
 235         if ([menu isJavaMenu]) {
 236             [menu setDelegate:delegate];
 237             [menu setJavaMenuDelegate:delegate];
 238         }
 239     }];
 240 
 241 JNI_COCOA_EXIT(env);
 242 
 243     return ptr_to_jlong(delegate);
 244 }
 245 
 246 /*
 247  * Class:     com_apple_laf_ScreenMenu
 248  * Method:    removeMenuListeners
 249  * Signature: (JJ)V
 250  */
 251 JNIEXPORT void JNICALL Java_com_apple_laf_ScreenMenu_removeMenuListeners
 252 (JNIEnv *env, jclass clz, jlong fModelPtr)
 253 {
 254     if (fModelPtr == 0L) return;
 255 
 256 JNI_COCOA_ENTER(env);
 257 
 258     NativeToJavaDelegate *delegate = (NativeToJavaDelegate *)jlong_to_ptr(fModelPtr);
 259 
 260     [ThreadUtilities performOnMainThreadWaiting:YES block:^{
 261         NSMenu *menu = delegate.nsmenu;
 262         [menu setJavaMenuDelegate:nil];
 263         [menu setDelegate:nil];
 264         delegate.nsmenu = nil;

 265     }];
 266 
 267     (*env)->DeleteGlobalRef(env, delegate.javaObject);
 268     delegate.javaObject = nil;
 269 
 270     CFRelease(delegate); // GC
 271 
 272 JNI_COCOA_EXIT(env);
 273 }
< prev index next >