Bug 228890 [Commands] WidgetMethodHandler should not use obsolete Swing API any when possible
diff --git a/bundles/org.eclipse.ui.workbench/Eclipse UI/org/eclipse/ui/internal/handlers/WidgetMethodHandler.java b/bundles/org.eclipse.ui.workbench/Eclipse UI/org/eclipse/ui/internal/handlers/WidgetMethodHandler.java
index ee54d8a..5b1c453 100644
--- a/bundles/org.eclipse.ui.workbench/Eclipse UI/org/eclipse/ui/internal/handlers/WidgetMethodHandler.java
+++ b/bundles/org.eclipse.ui.workbench/Eclipse UI/org/eclipse/ui/internal/handlers/WidgetMethodHandler.java
@@ -7,6 +7,7 @@
*
* Contributors:
* IBM Corporation - initial API and implementation
+ * Bruno Haible haible@ilog.fr - bug 228890
*******************************************************************************/
package org.eclipse.ui.internal.handlers;
@@ -52,66 +53,66 @@
final Control focusControl = Display.getCurrent()
.getFocusControl();
if ((focusControl instanceof Composite)
- && ((((Composite) focusControl).getStyle() & SWT.EMBEDDED) != 0)) {
- /*
- * Okay. Have a seat. Relax a while. This is going to be a
+ && ((((Composite) focusControl).getStyle() & SWT.EMBEDDED) != 0)) {
+ /*
+ * Okay. Have a seat. Relax a while. This is going to be a
* bumpy ride. If it is an embedded widget, then it *might*
* be a Swing widget. At the point where this handler is
- * executing, the key event is already bound to be
- * swallowed. If I don't do something, then the key will be
- * gone for good. So, I will try to forward the event to the
- * Swing widget. Unfortunately, we can't even count on the
- * Swing libraries existing, so I need to use reflection
- * everywhere. And, to top it off, I need to dispatch the
- * event on the Swing event queue, which means that it will
- * be carried out asynchronously to the SWT event queue.
- */
- try {
- final Object focusComponent = getFocusComponent();
- if (focusComponent != null) {
- Runnable methodRunnable = new Runnable() {
- public void run() {
- try {
- methodToExecute.invoke(focusComponent,
- null);
- } catch (final IllegalAccessException e) {
- // The method is protected, so do
- // nothing.
- } catch (final InvocationTargetException e) {
- /*
- * I would like to log this exception --
- * and possibly show a dialog to the
- * user -- but I have to go back to the
- * SWT event loop to do this. So, back
- * we go....
- */
- focusControl.getDisplay().asyncExec(
- new Runnable() {
- public void run() {
- ExceptionHandler
- .getInstance()
- .handleException(
- new ExecutionException(
- "An exception occurred while executing " //$NON-NLS-1$
- + methodToExecute
- .getName(),
- e
- .getTargetException()));
- }
- });
- }
- }
- };
+ * executing, the key event is already bound to be
+ * swallowed. If I don't do something, then the key will be
+ * gone for good. So, I will try to forward the event to the
+ * Swing widget. Unfortunately, we can't even count on the
+ * Swing libraries existing, so I need to use reflection
+ * everywhere. And, to top it off, I need to dispatch the
+ * event on the Swing event queue, which means that it will
+ * be carried out asynchronously to the SWT event queue.
+ */
+ try {
+ final Object focusComponent = getFocusComponent();
+ if (focusComponent != null) {
+ Runnable methodRunnable = new Runnable() {
+ public void run() {
+ try {
+ methodToExecute.invoke(focusComponent,
+ null);
+ } catch (final IllegalAccessException e) {
+ // The method is protected, so do
+ // nothing.
+ } catch (final InvocationTargetException e) {
+ /*
+ * I would like to log this exception --
+ * and possibly show a dialog to the
+ * user -- but I have to go back to the
+ * SWT event loop to do this. So, back
+ * we go....
+ */
+ focusControl.getDisplay().asyncExec(
+ new Runnable() {
+ public void run() {
+ ExceptionHandler
+ .getInstance()
+ .handleException(
+ new ExecutionException(
+ "An exception occurred while executing " //$NON-NLS-1$
+ + methodToExecute
+ .getName(),
+ e
+ .getTargetException()));
+ }
+ });
+ }
+ }
+ };
- swingInvokeLater(methodRunnable);
- }
- } catch (final ClassNotFoundException e) {
- // There is no Swing support, so do nothing.
+ swingInvokeLater(methodRunnable);
+ }
+ } catch (final ClassNotFoundException e) {
+ // There is no Swing support, so do nothing.
- } catch (final NoSuchMethodException e) {
- // The API has changed, which seems amazingly unlikely.
- throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
- }
+ } catch (final NoSuchMethodException e) {
+ // The API has changed, which seems amazingly unlikely.
+ throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
+ }
} else {
@@ -146,19 +147,19 @@
throws ClassNotFoundException, NoSuchMethodException,
IllegalAccessException, InvocationTargetException {
final Class swingUtilitiesClass = Class
- .forName("javax.swing.SwingUtilities"); //$NON-NLS-1$
+ .forName("javax.swing.SwingUtilities"); //$NON-NLS-1$
final Method swingUtilitiesInvokeLaterMethod = swingUtilitiesClass
- .getMethod("invokeLater", //$NON-NLS-1$
- new Class[] { Runnable.class });
- swingUtilitiesInvokeLaterMethod.invoke(
- swingUtilitiesClass,
- new Object[] { methodRunnable });
+ .getMethod("invokeLater", //$NON-NLS-1$
+ new Class[] { Runnable.class });
+ swingUtilitiesInvokeLaterMethod.invoke(swingUtilitiesClass,
+ new Object[] { methodRunnable });
}
/**
* Find the swing focus component, if it is available.
*
- * @return Hopefully, the swing focus component, but it can return <code>null</code>.
+ * @return Hopefully, the swing focus component, but it can return
+ * <code>null</code>.
* @throws ClassNotFoundException
* @throws NoSuchMethodException
* @throws IllegalAccessException
@@ -167,10 +168,39 @@
protected Object getFocusComponent() throws ClassNotFoundException,
NoSuchMethodException, IllegalAccessException,
InvocationTargetException {
+ /*
+ * Before JRE 1.4, one has to use
+ * javax.swing.FocusManager.getCurrentManager().getFocusOwner(). Since
+ * JRE 1.4, one has to use
+ * java.awt.KeyboardFocusManager.getCurrentKeyboardFocusManager
+ * ().getFocusOwner(); the use of the older API would install a
+ * LegacyGlueFocusTraversalPolicy which causes endless recursions in
+ * some situations.
+ */
+ Class keyboardFocusManagerClass = null;
+ try {
+ keyboardFocusManagerClass = Class
+ .forName("java.awt.KeyboardFocusManager"); //$NON-NLS-1$
+ } catch (ClassNotFoundException e) {
+ // switch to the old guy
+ }
+ if (keyboardFocusManagerClass != null) {
+ // Use JRE 1.4 API
+ final Method keyboardFocusManagerGetCurrentKeyboardFocusManagerMethod = keyboardFocusManagerClass
+ .getMethod("getCurrentKeyboardFocusManager", null); //$NON-NLS-1$
+ final Object keyboardFocusManager = keyboardFocusManagerGetCurrentKeyboardFocusManagerMethod
+ .invoke(keyboardFocusManagerClass, null);
+ final Method keyboardFocusManagerGetFocusOwner = keyboardFocusManagerClass
+ .getMethod("getFocusOwner", null); //$NON-NLS-1$
+ final Object focusComponent = keyboardFocusManagerGetFocusOwner
+ .invoke(keyboardFocusManager, null);
+ return focusComponent;
+ }
+ // Use JRE 1.3 API
final Class focusManagerClass = Class
- .forName("javax.swing.FocusManager"); //$NON-NLS-1$
+ .forName("javax.swing.FocusManager"); //$NON-NLS-1$
final Method focusManagerGetCurrentManagerMethod = focusManagerClass
- .getMethod("getCurrentManager", null); //$NON-NLS-1$
+ .getMethod("getCurrentManager", null); //$NON-NLS-1$
final Object focusManager = focusManagerGetCurrentManagerMethod
.invoke(focusManagerClass, null);
final Method focusManagerGetFocusOwner = focusManagerClass
@@ -178,6 +208,7 @@
final Object focusComponent = focusManagerGetFocusOwner
.invoke(focusManager, null);
return focusComponent;
+
}
public final boolean isEnabled() {
@@ -190,9 +221,9 @@
* @return The method on the focus control; <code>null</code> if none.
*/
protected Method getMethodToExecute() {
- Display display = Display.getCurrent();
- if (display == null)
- return null;
+ Display display = Display.getCurrent();
+ if (display == null)
+ return null;
final Control focusControl = display.getFocusControl();
Method method = null;
@@ -216,9 +247,9 @@
* through to the underlying Swing component hierarchy. Insha'allah,
* this will work.
*/
- try {
- final Object focusComponent = getFocusComponent();
- if (focusComponent != null) {
+ try {
+ final Object focusComponent = getFocusComponent();
+ if (focusComponent != null) {
final Class clazz = focusComponent.getClass();
try {
@@ -227,20 +258,20 @@
// Do nothing.
}
}
- } catch (final ClassNotFoundException e) {
- // There is no Swing support, so do nothing.
+ } catch (final ClassNotFoundException e) {
+ // There is no Swing support, so do nothing.
- } catch (final NoSuchMethodException e) {
- // The API has changed, which seems amazingly unlikely.
- throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
- } catch (IllegalAccessException e) {
- // The API has changed, which seems amazingly unlikely.
- throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
- } catch (InvocationTargetException e) {
- // The API has changed, which seems amazingly unlikely.
- throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
- }
- }
+ } catch (final NoSuchMethodException e) {
+ // The API has changed, which seems amazingly unlikely.
+ throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
+ } catch (IllegalAccessException e) {
+ // The API has changed, which seems amazingly unlikely.
+ throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
+ } catch (InvocationTargetException e) {
+ // The API has changed, which seems amazingly unlikely.
+ throw new Error("Something is seriously wrong here"); //$NON-NLS-1$
+ }
+ }
return method;
}
@@ -248,8 +279,10 @@
/*
* (non-Javadoc)
*
- * @see org.eclipse.core.runtime.IExecutableExtension#setInitializationData(org.eclipse.core.runtime.IConfigurationElement,
- * java.lang.String, java.lang.Object)
+ * @see
+ * org.eclipse.core.runtime.IExecutableExtension#setInitializationData(org
+ * .eclipse.core.runtime.IConfigurationElement, java.lang.String,
+ * java.lang.Object)
*/
public void setInitializationData(IConfigurationElement config,
String propertyName, Object data) {