/* * Copyright (C) 2012 The Android Open Source Project * * Licensed under the Eclipse Public License, Version 1.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.eclipse.org/org/documents/epl-v10.php * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * * References: * Based on the SWT snippet example at * http://dev.eclipse.org/viewcvs/viewvc.cgi/org.eclipse.swt.snippets/src/org/eclipse/swt/snippets/Snippet354.java?view=co */ package com.android.menubar; import org.eclipse.swt.events.SelectionAdapter; import org.eclipse.swt.events.SelectionEvent; import org.eclipse.swt.widgets.Display; import org.eclipse.swt.widgets.Menu; import org.eclipse.swt.widgets.MenuItem; import java.lang.reflect.Method; public class MenuBarEnhancer37 implements IMenuBarEnhancer { private static final int kAboutMenuItem = -1; // SWT.ID_ABOUT in SWT 3.7 private static final int kPreferencesMenuItem = -2; // SWT.ID_PREFERENCES in SWT 3.7 private static final int kQuitMenuItem = -6; // SWT.ID_QUIT in SWT 3.7 public MenuBarEnhancer37() { } public MenuBarMode getMenuBarMode() { return MenuBarMode.MAC_OS; } /** * Setup the About and Preferences native menut items with the * given application name and links them to the callback. * * @param appName The application name. * @param display The SWT display. Must not be null. * @param callbacks The callbacks invoked by the menus. */ public void setupMenu( String appName, Display display, IMenuBarCallback callbacks) { try { // Initialize the menuItems. initialize(display, appName, callbacks); } catch (Exception e) { throw new IllegalStateException(e); } // Schedule disposal of callback object display.disposeExec(new Runnable() { public void run() { } }); } /** * Checks whether the required SWT 3.7 APIs are available. * <br/> * Calling this will load the class, which is OK since this class doesn't * directly use any SWT 3.7 API -- instead it uses reflection so that the * code can be loaded under SWT 3.6. * * @param display The current SWT display. * @return True if the SWT 3.7 API are available and this enhancer can be used. */ public static boolean isSupported(Display display) { try { Object sysMenu = call0(display, "getSystemMenu"); if (sysMenu instanceof Menu) { return findMenuById((Menu)sysMenu, kPreferencesMenuItem) != null && findMenuById((Menu)sysMenu, kAboutMenuItem) != null; } } catch (Exception ignore) {} return false; } private void initialize( Display display, String appName, final IMenuBarCallback callbacks) throws Exception { Object sysMenu = call0(display, "getSystemMenu"); if (sysMenu instanceof Menu) { MenuItem menu = findMenuById((Menu)sysMenu, kPreferencesMenuItem); if (menu != null) { menu.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent event) { callbacks.onPreferencesMenuSelected(); } }); } menu = findMenuById((Menu)sysMenu, kAboutMenuItem); if (menu != null) { menu.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent event) { callbacks.onAboutMenuSelected(); } }); menu.setText("About " + appName); } menu = findMenuById((Menu)sysMenu, kQuitMenuItem); if (menu != null) { // We already support the "quit" operation, no need for an extra handler here. menu.setText("Quit " + appName); } } } private static Object call0(Object obj, String method) { try { Method m = obj.getClass().getMethod(method, (Class<?>[])null); if (m != null) { return m.invoke(obj, (Object[])null); } } catch (Exception ignore) {} return null; } private static MenuItem findMenuById(Menu menu, int id) { MenuItem[] items = menu.getItems(); for (int i = items.length - 1; i >= 0; i--) { MenuItem item = items[i]; Object menuId = call0(item, "getID"); if (menuId instanceof Integer) { if (((Integer) menuId).intValue() == id) { return item; } } } return null; } }