summaryrefslogtreecommitdiff
path: root/accessibility/bridge/org/openoffice/accessibility
diff options
context:
space:
mode:
Diffstat (limited to 'accessibility/bridge/org/openoffice/accessibility')
-rwxr-xr-xaccessibility/bridge/org/openoffice/accessibility/AccessBridge.java245
-rwxr-xr-xaccessibility/bridge/org/openoffice/accessibility/KeyHandler.java138
-rw-r--r--accessibility/bridge/org/openoffice/accessibility/PopupWindow.java210
-rw-r--r--accessibility/bridge/org/openoffice/accessibility/WindowsAccessBridgeAdapter.java654
-rw-r--r--accessibility/bridge/org/openoffice/accessibility/java_uno_accessbridge.component34
-rwxr-xr-xaccessibility/bridge/org/openoffice/accessibility/makefile.mk62
-rwxr-xr-xaccessibility/bridge/org/openoffice/accessibility/manifest2
7 files changed, 1345 insertions, 0 deletions
diff --git a/accessibility/bridge/org/openoffice/accessibility/AccessBridge.java b/accessibility/bridge/org/openoffice/accessibility/AccessBridge.java
new file mode 100755
index 000000000000..ec479fb3949d
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/AccessBridge.java
@@ -0,0 +1,245 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+package org.openoffice.accessibility;
+
+import com.sun.star.accessibility.AccessibleRole;
+import com.sun.star.accessibility.XAccessible;
+import com.sun.star.accessibility.XAccessibleContext;
+import com.sun.star.awt.XExtendedToolkit;
+import com.sun.star.awt.XTopWindow;
+import com.sun.star.awt.XTopWindowListener;
+import com.sun.star.awt.XWindow;
+import com.sun.star.comp.loader.FactoryHelper;
+import com.sun.star.lang.XComponent;
+import com.sun.star.lang.XInitialization;
+import com.sun.star.lang.XMultiServiceFactory;
+import com.sun.star.lang.XSingleServiceFactory;
+import com.sun.star.registry.*;
+import com.sun.star.uno.*;
+
+import org.openoffice.java.accessibility.*;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+import javax.accessibility.Accessible;
+
+
+public class AccessBridge {
+ //
+ protected static java.util.Hashtable topWindowMap = new java.util.Hashtable();
+
+ private static java.awt.Window getTopWindowImpl(XAccessible xAccessible) {
+ // Because it can not be garantied that
+ // WindowsAccessBridgeAdapter.registerTopWindow() is called
+ // before windowOpened(), we have to make this operation
+ // atomic.
+ synchronized (topWindowMap) {
+ String oid = UnoRuntime.generateOid(xAccessible);
+ java.awt.Window w = (java.awt.Window) topWindowMap.get(oid);
+
+ if (w == null) {
+ w = AccessibleObjectFactory.getTopWindow(xAccessible);
+
+ if (w != null) {
+ topWindowMap.put(oid, w);
+ }
+ }
+
+ return w;
+ }
+ }
+
+ protected static java.awt.Window getTopWindow(XAccessible xAccessible) {
+ if (xAccessible != null) {
+ XAccessibleContext xAccessibleContext = xAccessible.getAccessibleContext();
+ if (xAccessibleContext != null) {
+
+ // Toolkit reports the VCL peer windows as toplevels. These have an
+ // accessible parent which represents the native frame window
+ switch(xAccessibleContext.getAccessibleRole()) {
+ case AccessibleRole.ROOT_PANE:
+ case AccessibleRole.POPUP_MENU:
+ return getTopWindow(xAccessibleContext.getAccessibleParent());
+
+ case AccessibleRole.WINDOW:
+ case AccessibleRole.FRAME:
+ case AccessibleRole.DIALOG:
+ case AccessibleRole.ALERT:
+ return getTopWindowImpl(xAccessible);
+
+ default:
+ break;
+ }
+ }
+ }
+
+ return null;
+ }
+
+ protected static java.awt.Window removeTopWindow(XAccessible xAccessible) {
+ if (xAccessible != null) {
+ XAccessibleContext xAccessibleContext = xAccessible.getAccessibleContext();
+ if (xAccessibleContext != null) {
+
+ // Toolkit reports the VCL peer windows as toplevels. These have an
+ // accessible parent which represents the native frame window
+ switch(xAccessibleContext.getAccessibleRole()) {
+ case AccessibleRole.ROOT_PANE:
+ case AccessibleRole.POPUP_MENU:
+ return removeTopWindow(xAccessibleContext.getAccessibleParent());
+
+ case AccessibleRole.WINDOW:
+ case AccessibleRole.FRAME:
+ case AccessibleRole.DIALOG:
+ return (java.awt.Window) topWindowMap.remove(UnoRuntime.generateOid(xAccessible));
+
+ default:
+ break;
+ }
+ }
+ }
+
+ return null;
+ }
+
+ public static XSingleServiceFactory __getServiceFactory(String implName,
+ XMultiServiceFactory multiFactory, XRegistryKey regKey) {
+ XSingleServiceFactory xSingleServiceFactory = null;
+
+ if (implName.equals(AccessBridge.class.getName())) {
+ // Initialize toolkit to register at Java <-> Windows access bridge
+ java.awt.Toolkit tk = java.awt.Toolkit.getDefaultToolkit();
+
+ xSingleServiceFactory = FactoryHelper.getServiceFactory(_AccessBridge.class,
+ _AccessBridge._serviceName, multiFactory, regKey);
+ }
+
+ return xSingleServiceFactory;
+ }
+
+ static public class _AccessBridge implements XTopWindowListener,
+ XInitialization, XComponent {
+ static final String _serviceName = "com.sun.star.accessibility.AccessBridge";
+ XComponentContext xComponentContext;
+
+ public _AccessBridge(XComponentContext xComponentContext) {
+ this.xComponentContext = xComponentContext;
+ }
+
+ /*
+ * XInitialization
+ */
+ public void initialize(java.lang.Object[] arguments) {
+ try {
+ // FIXME: Currently there is no way to determine if key event forwarding is needed or not,
+ // so we have to do it always ..
+ XExtendedToolkit unoToolkit = (XExtendedToolkit) AnyConverter.toObject(new Type(
+ XExtendedToolkit.class), arguments[0]);
+
+ if (unoToolkit != null) {
+ // FIXME this should be done in VCL
+ unoToolkit.addTopWindowListener(this);
+
+ String os = (String) System.getProperty("os.name");
+
+ // Try to initialize the WindowsAccessBridgeAdapter
+ if (os.startsWith("Windows")) {
+ WindowsAccessBridgeAdapter.attach(xComponentContext);
+ } else {
+ unoToolkit.addKeyHandler(new KeyHandler());
+ }
+ } else if (Build.DEBUG) {
+ System.err.println(
+ "argument 0 is not of type XExtendedToolkit.");
+ }
+ } catch (com.sun.star.lang.IllegalArgumentException e) {
+ // FIXME: output
+ }
+ }
+
+ /*
+ * XTopWindowListener
+ */
+ public void windowOpened(com.sun.star.lang.EventObject event) {
+ XAccessible xAccessible = (XAccessible) UnoRuntime.queryInterface(XAccessible.class,
+ event.Source);
+ java.awt.Window w = getTopWindow(xAccessible);
+ }
+
+ public void windowActivated(com.sun.star.lang.EventObject event) {
+ }
+
+ public void windowDeactivated(com.sun.star.lang.EventObject event) {
+ }
+
+ public void windowMinimized(com.sun.star.lang.EventObject event) {
+ }
+
+ public void windowNormalized(com.sun.star.lang.EventObject event) {
+ }
+
+ public void windowClosing(com.sun.star.lang.EventObject event) {
+ }
+
+ public void windowClosed(com.sun.star.lang.EventObject event) {
+ XAccessible xAccessible = (XAccessible) UnoRuntime.queryInterface(XAccessible.class,
+ event.Source);
+
+ java.awt.Window w = removeTopWindow(xAccessible);
+
+ if (w != null) {
+ w.dispose();
+ }
+ }
+
+ public void disposing(com.sun.star.lang.EventObject event) {
+ }
+
+ /*
+ * XComponent
+ */
+
+ public void addEventListener(com.sun.star.lang.XEventListener listener) {
+ }
+
+ public void removeEventListener(com.sun.star.lang.XEventListener listener) {
+ }
+
+ public void dispose() {
+ try {
+ java.awt.Toolkit.getDefaultToolkit().getSystemEventQueue().invokeAndWait(
+ new Runnable() {
+ public void run() {
+ }
+ } );
+ } catch (java.lang.InterruptedException e) {
+ } catch (java.lang.reflect.InvocationTargetException e) {
+ }
+ }
+ }
+}
diff --git a/accessibility/bridge/org/openoffice/accessibility/KeyHandler.java b/accessibility/bridge/org/openoffice/accessibility/KeyHandler.java
new file mode 100755
index 000000000000..1e9f2f6520ae
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/KeyHandler.java
@@ -0,0 +1,138 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+
+package org.openoffice.accessibility;
+
+import com.sun.star.uno.UnoRuntime;
+import com.sun.star.awt.XKeyHandler;
+import org.openoffice.java.accessibility.AccessibleKeyBinding;
+import org.openoffice.java.accessibility.Build;
+
+import java.awt.*;
+import java.awt.event.KeyEvent;
+import javax.accessibility.*;
+
+public class KeyHandler extends Component implements XKeyHandler, java.awt.KeyEventDispatcher {
+ EventQueue eventQueue;
+
+ public class VCLKeyEvent extends KeyEvent implements Runnable {
+ boolean consumed = true;
+
+ public VCLKeyEvent(Component c, int id, int modifiers, int keyCode, char keyChar) {
+ super(c, id, System.currentTimeMillis(), modifiers, keyCode, keyChar);
+ }
+
+ public void run() {
+ // This is a no-op ..
+ }
+
+ public void setConsumed(boolean b) {
+ consumed = b;
+ }
+
+ public boolean isConsumed() {
+ return consumed;
+ }
+ }
+
+ public KeyHandler() {
+ eventQueue = Toolkit.getDefaultToolkit().getSystemEventQueue();
+ java.awt.KeyboardFocusManager.getCurrentKeyboardFocusManager().addKeyEventDispatcher(this);
+ }
+
+ /** This method is called by the current KeyboardFocusManager requesting that this KeyEventDispatcher
+ * dispatch the specified event on its behalf
+ */
+ public boolean dispatchKeyEvent(java.awt.event.KeyEvent e) {
+ if (e instanceof VCLKeyEvent) {
+ VCLKeyEvent event = (VCLKeyEvent) e;
+ event.setConsumed(false);
+ return true;
+ }
+ return false;
+ }
+
+ /** Handler for KeyPressed events */
+ public boolean keyPressed(com.sun.star.awt.KeyEvent event) {
+// try {
+ VCLKeyEvent vke = new VCLKeyEvent(this, KeyEvent.KEY_PRESSED,
+ AccessibleKeyBinding.convertModifiers(event.Modifiers),
+ AccessibleKeyBinding.convertKeyCode(event.KeyCode),
+ event.KeyChar != 0 ? event.KeyChar : KeyEvent.CHAR_UNDEFINED);
+
+ eventQueue.postEvent(vke);
+
+ // VCL events for TABs have empty KeyChar
+ if (event.KeyCode == com.sun.star.awt.Key.TAB ) {
+ event.KeyChar = '\t';
+ }
+
+ // Synthesize KEY_TYPED event to emulate Java behavior
+ if (event.KeyChar != 0) {
+ eventQueue.postEvent(new VCLKeyEvent(this,
+ KeyEvent.KEY_TYPED,
+ AccessibleKeyBinding.convertModifiers(event.Modifiers),
+ KeyEvent.VK_UNDEFINED,
+ event.KeyChar));
+ }
+
+ // Wait until the key event is processed
+ return false;
+// eventQueue.invokeAndWait(vke);
+// return vke.isConsumed();
+// } catch(java.lang.InterruptedException e) {
+// return false;
+// } catch(java.lang.reflect.InvocationTargetException e) {
+// return false;
+// }
+ }
+
+ /** Handler for KeyReleased events */
+ public boolean keyReleased(com.sun.star.awt.KeyEvent event) {
+// try {
+ VCLKeyEvent vke = new VCLKeyEvent(this, KeyEvent.KEY_RELEASED,
+ AccessibleKeyBinding.convertModifiers(event.Modifiers),
+ AccessibleKeyBinding.convertKeyCode(event.KeyCode),
+ event.KeyChar != 0 ? event.KeyChar : KeyEvent.CHAR_UNDEFINED);
+ eventQueue.postEvent(vke);
+
+ // Wait until the key event is processed
+ return false;
+// eventQueue.invokeAndWait(vke);
+// return vke.isConsumed();
+// } catch(java.lang.InterruptedException e) {
+// return false;
+// } catch(java.lang.reflect.InvocationTargetException e) {
+// return false;
+// }
+ }
+
+ public void disposing(com.sun.star.lang.EventObject event) {
+ java.awt.KeyboardFocusManager.getCurrentKeyboardFocusManager().removeKeyEventDispatcher(this);
+ }
+};
diff --git a/accessibility/bridge/org/openoffice/accessibility/PopupWindow.java b/accessibility/bridge/org/openoffice/accessibility/PopupWindow.java
new file mode 100644
index 000000000000..a63b0589b4fa
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/PopupWindow.java
@@ -0,0 +1,210 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+package org.openoffice.accessibility;
+
+import org.openoffice.java.accessibility.*;
+
+
+/**
+ *
+ */
+public class PopupWindow extends java.awt.Window {
+ javax.accessibility.AccessibleContext accessibleContext = null;
+ ContainerProxy layeredPane = new ContainerProxy(javax.accessibility.AccessibleRole.LAYERED_PANE);
+ ContainerProxy rootPane = new ContainerProxy(javax.accessibility.AccessibleRole.ROOT_PANE);
+ ContainerProxy popupLayer = new ContainerProxy(javax.accessibility.AccessibleRole.PANEL);
+ boolean opened = false;
+ boolean visible = false;
+
+ /** Creates a new instance of PopupWindow */
+ public PopupWindow(java.awt.Window owner) {
+ super(owner);
+ super.add(rootPane);
+ rootPane.add(layeredPane);
+
+ javax.accessibility.AccessibleContext ac = rootPane.getAccessibleContext();
+
+ if (ac != null) {
+ ac.setAccessibleParent(this);
+ }
+ }
+
+ static PopupWindow create(
+ com.sun.star.accessibility.XAccessible xAccessible) {
+ java.awt.Window parent = java.awt.KeyboardFocusManager.getCurrentKeyboardFocusManager()
+ .getActiveWindow();
+
+ if (parent != null) {
+ PopupWindow w = new PopupWindow(parent);
+ w.setVisible(true);
+ AccessibleObjectFactory.invokeAndWait();
+ AccessibleObjectFactory.addChild(w, xAccessible);
+
+ return w;
+ }
+
+ return null;
+ }
+
+ public boolean isShowing() {
+ if (isVisible()) {
+ java.awt.Container parent = getParent();
+
+ return (parent == null) || parent.isShowing();
+ }
+
+ return false;
+ }
+
+ public void addNotify() {
+ }
+
+ public void removeNotify() {
+ }
+
+ public boolean isVisible() {
+ return visible;
+ }
+
+ public void setVisible(boolean b) {
+ if (visible != b) {
+ visible = b;
+
+ if (b) {
+ // If it is the first show, fire WINDOW_OPENED event
+ if (!opened) {
+ AccessibleObjectFactory.postWindowOpened(this);
+ opened = true;
+ }
+ }
+ }
+ }
+
+ public java.awt.Component add(java.awt.Component c) {
+ popupLayer.add(c);
+ layeredPane.add(popupLayer);
+
+ if (c instanceof javax.accessibility.Accessible) {
+ javax.accessibility.AccessibleContext ac = layeredPane.getAccessibleContext();
+
+ if (ac != null) {
+ ac.firePropertyChange(ac.ACCESSIBLE_CHILD_PROPERTY, null,
+ popupLayer.getAccessibleContext());
+ }
+ }
+
+ return c;
+ }
+
+ public void remove(java.awt.Component c) {
+ layeredPane.remove(popupLayer);
+
+ if (c instanceof javax.accessibility.Accessible) {
+ javax.accessibility.AccessibleContext ac = layeredPane.getAccessibleContext();
+
+ if (ac != null) {
+ ac.firePropertyChange(ac.ACCESSIBLE_CHILD_PROPERTY,
+ popupLayer.getAccessibleContext(), null);
+ }
+ }
+
+ popupLayer.remove(c);
+ }
+
+ public void dispose() {
+ setVisible(false);
+ AccessibleObjectFactory.postWindowClosed(this);
+ }
+
+ public javax.accessibility.AccessibleContext getAccessibleContext() {
+ if (accessibleContext == null) {
+ accessibleContext = new AccessiblePopupWindow();
+ }
+
+ return accessibleContext;
+ }
+
+ protected class AccessiblePopupWindow
+ extends java.awt.Window.AccessibleAWTWindow {
+ AccessiblePopupWindow() {
+ }
+ }
+
+ protected class ContainerProxy extends java.awt.Container
+ implements javax.accessibility.Accessible {
+ javax.accessibility.AccessibleContext accessibleContext = null;
+ javax.accessibility.AccessibleRole role;
+
+ protected ContainerProxy(javax.accessibility.AccessibleRole role) {
+ this.role = role;
+ }
+
+ public java.awt.Component add(java.awt.Component c) {
+ if (c instanceof javax.accessibility.Accessible) {
+ javax.accessibility.Accessible a = (javax.accessibility.Accessible) c;
+ javax.accessibility.AccessibleContext ac = a.getAccessibleContext();
+
+ if (ac != null) {
+ ac.setAccessibleParent(this);
+ }
+ }
+
+ return super.add(c);
+ }
+
+ public void remove(java.awt.Component c) {
+ if (c instanceof javax.accessibility.Accessible) {
+ javax.accessibility.Accessible a = (javax.accessibility.Accessible) c;
+ javax.accessibility.AccessibleContext ac = a.getAccessibleContext();
+
+ if (ac != null) {
+ ac.setAccessibleParent(null);
+ }
+ }
+
+ super.remove(c);
+ }
+
+ public javax.accessibility.AccessibleContext getAccessibleContext() {
+ if (accessibleContext == null) {
+ accessibleContext = new AccessibleContainerProxy();
+ }
+
+ return accessibleContext;
+ }
+
+ private class AccessibleContainerProxy
+ extends java.awt.Container.AccessibleAWTContainer {
+ AccessibleContainerProxy() {
+ }
+
+ public javax.accessibility.AccessibleRole getAccessibleRole() {
+ return ContainerProxy.this.role;
+ }
+ }
+ }
+}
diff --git a/accessibility/bridge/org/openoffice/accessibility/WindowsAccessBridgeAdapter.java b/accessibility/bridge/org/openoffice/accessibility/WindowsAccessBridgeAdapter.java
new file mode 100644
index 000000000000..28e58940867d
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/WindowsAccessBridgeAdapter.java
@@ -0,0 +1,654 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+package org.openoffice.accessibility;
+
+import com.sun.star.accessibility.AccessibleRole;
+import com.sun.star.accessibility.XAccessible;
+import com.sun.star.accessibility.XAccessibleContext;
+import com.sun.star.java.XJavaVM;
+import com.sun.star.uno.*;
+
+import org.openoffice.java.accessibility.*;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+import javax.accessibility.*;
+
+
+public class WindowsAccessBridgeAdapter {
+ private static Method registerVirtualFrame;
+ private static Method revokeVirtualFrame;
+ private static java.util.Hashtable frameMap;
+
+ protected static native byte[] getProcessID();
+
+ protected static native boolean createMapping(long jvmaccess);
+
+ // On Windows all native frames must be registered to the access bridge.
+ // Therefor the bridge exports two methods that we try to find here.
+ protected static void attach(XComponentContext xComponentContext) {
+ try {
+ Class bridge = Class.forName(
+ "com.sun.java.accessibility.AccessBridge");
+ Class[] parameterTypes = {
+ javax.accessibility.Accessible.class, Integer.class
+ };
+
+ if (bridge != null) {
+ registerVirtualFrame = bridge.getMethod("registerVirtualFrame",
+ parameterTypes);
+ revokeVirtualFrame = bridge.getMethod("revokeVirtualFrame",
+ parameterTypes);
+
+ // load the native dll
+ System.loadLibrary("java_uno_accessbridge");
+
+ Object any = xComponentContext.getValueByName(
+ "/singletons/com.sun.star.java.theJavaVirtualMachine");
+
+ if (AnyConverter.isObject(any)) {
+ XJavaVM xJavaVM = (XJavaVM) UnoRuntime.queryInterface(XJavaVM.class,
+ AnyConverter.toObject(new Type(XJavaVM.class), any));
+
+ if (xJavaVM != null) {
+ any = xJavaVM.getJavaVM(getProcessID());
+
+ if (AnyConverter.isLong(any)) {
+ createMapping(AnyConverter.toLong(any));
+ frameMap = new java.util.Hashtable();
+ }
+ }
+ }
+ }
+ } catch (NoSuchMethodException e) {
+ System.err.println("ERROR: incompatible AccessBridge found: " +
+ e.getMessage());
+
+ // Forward this exception to UNO to indicate that the service will
+ // not work correctly.
+ throw new com.sun.star.uno.RuntimeException(
+ "incompatible AccessBridge class: " + e.getMessage());
+ } catch (java.lang.SecurityException e) {
+ System.err.println("ERROR: no access to AccessBridge: " +
+ e.getMessage());
+
+ // Forward this exception to UNO to indicate that the service will not work correctly.
+ throw new com.sun.star.uno.RuntimeException(
+ "Security exception caught: " + e.getMessage());
+ } catch (ClassNotFoundException e) {
+ // Forward this exception to UNO to indicate that the service will not work correctly.
+ throw new com.sun.star.uno.RuntimeException(
+ "ClassNotFound exception caught: " + e.getMessage());
+ } catch (IllegalArgumentException e) {
+ System.err.println("IllegalArgumentException caught: " +
+ e.getMessage());
+
+ // Forward this exception to UNO to indicate that the service will not work correctly.
+ throw new com.sun.star.uno.RuntimeException(
+ "IllegalArgumentException caught: " + e.getMessage());
+ } catch (com.sun.star.lang.IllegalArgumentException e) {
+ System.err.println("UNO IllegalArgumentException caught: " +
+ e.getMessage());
+
+ // Forward this exception to UNO to indicate that the service will not work correctly.
+ throw new com.sun.star.uno.RuntimeException(
+ "UNO IllegalArgumentException caught: " + e.getMessage());
+ }
+ }
+
+ protected static boolean isAttached() {
+ return frameMap != null;
+ }
+
+ protected static Accessible getAccessibleWrapper(XAccessible xAccessible) {
+ Accessible a = null;
+
+ try {
+ XAccessibleContext xAccessibleContext = xAccessible.getAccessibleContext();
+
+ if (xAccessibleContext != null) {
+ switch (xAccessibleContext.getAccessibleRole()) {
+ case AccessibleRole.LIST:
+ a = (Accessible) AccessibleObjectFactory.getAccessibleComponent(xAccessible);
+ if (a != null) {
+ a = new ListProxy(a.getAccessibleContext());
+ }
+ break;
+
+ case AccessibleRole.MENU:
+
+ Accessible tmp = (Accessible) AccessibleObjectFactory.getAccessibleComponent(xAccessible);
+ if (tmp != null) {
+ AccessibleContext ac = tmp.getAccessibleContext();
+
+ if (ac != null) {
+ a = new PopupMenuProxy(ac);
+ }
+ }
+
+ break;
+
+ case AccessibleRole.TOOL_TIP:
+ a = PopupWindow.create(xAccessible);
+ break;
+
+ default:
+ a = (Accessible) AccessBridge.getTopWindow(xAccessible);
+ break;
+ }
+ }
+ } catch (com.sun.star.uno.RuntimeException e) {
+ }
+
+ return a;
+ }
+
+ /** Registers a native frame at the Java AccessBridge for Windows */
+ public static void registerTopWindow(int handle, XAccessible xAccessible) {
+ Integer hwnd = new Integer(handle);
+
+ if (!frameMap.contains(hwnd)) {
+ if (Build.DEBUG) {
+ System.err.println("Native frame " + hwnd + " of role " +
+ AccessibleRoleAdapter.getAccessibleRole(xAccessible) +
+ " has been opened");
+ }
+
+ Accessible a = getAccessibleWrapper(xAccessible);
+
+ if (a != null) {
+ Object[] args = { a, hwnd };
+
+ frameMap.put(hwnd, a);
+
+ if (Build.DEBUG) {
+ System.err.println("registering native frame " + hwnd);
+ }
+
+ try {
+ registerVirtualFrame.invoke(null, args);
+ } catch (IllegalAccessException e) {
+ System.err.println("IllegalAccessException caught: " +
+ e.getMessage());
+ } catch (IllegalArgumentException e) {
+ System.err.println("IllegalArgumentException caught: " +
+ e.getMessage());
+ } catch (InvocationTargetException e) {
+ System.err.println("InvokationTargetException caught: " +
+ e.getMessage());
+ }
+ }
+ }
+ }
+
+ /** Revokes a native frame at the Java AccessBridge for Windows */
+ public static void revokeTopWindow(int handle, XAccessible xAccessible) {
+ Integer hwnd = new Integer(handle);
+
+ Accessible a = (Accessible) frameMap.remove(hwnd);
+
+ if (a != null) {
+ Object[] args = { a, hwnd };
+
+ if (Build.DEBUG) {
+ System.err.println("revoking native frame " + hwnd);
+ }
+
+ try {
+ revokeVirtualFrame.invoke(null, args);
+ } catch (IllegalAccessException e) {
+ System.err.println("IllegalAccessException caught: " +
+ e.getMessage());
+ } catch (IllegalArgumentException e) {
+ System.err.println("IllegalArgumentException caught: " +
+ e.getMessage());
+ } catch (InvocationTargetException e) {
+ System.err.println("InvokationTargetException caught: " +
+ e.getMessage());
+ }
+ }
+
+ if (a instanceof PopupWindow) {
+ PopupWindow toolTipWindow = (PopupWindow) a;
+ toolTipWindow.removeAll();
+ toolTipWindow.dispose();
+ }
+ }
+
+ protected static class PopupMenuProxy extends AccessibleContext
+ implements Accessible, AccessibleComponent {
+ AccessibleContext menu;
+ AccessibleComponent menuComponent;
+ int x = 0; int y = 0; int width = 0; int height = 0;
+
+ PopupMenuProxy(AccessibleContext ac) {
+ menu = ac;
+ menuComponent = menu.getAccessibleComponent();
+
+ /** calculate the bounding rectangle by iterating over the
+ * the children.
+ */
+ int x2 = 0; int y2 = 0;
+ int count = ac.getAccessibleChildrenCount();
+ for (int i = 0; i < count; i++) {
+ Accessible a = menu.getAccessibleChild(i);
+
+ if (a != null) {
+ AccessibleContext childAC = a.getAccessibleContext();
+
+ if (childAC != null) {
+ AccessibleComponent comp = ac.getAccessibleComponent();
+
+ if (comp != null) {
+ java.awt.Point p = comp.getLocationOnScreen();
+ java.awt.Dimension d = comp.getSize();
+
+ if (p != null && d != null) {
+ if (p.x < x) {
+ x = p.x;
+ }
+ if (p.y < y) {
+ y = p.y;
+ }
+ if (p.x + d.width > x2) {
+ x2 = p.x + d.width;
+ }
+ if (p.y + d.height > y2) {
+ y2 = p.y + d.height;
+ }
+ }
+ }
+ }
+ }
+ }
+
+ width = x2 - x;
+ height = y2 - y;
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleContext getAccessibleContext() {
+ return this;
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleComponent getAccessibleComponent() {
+ return this;
+ }
+
+ /** Returns the AccessibleText associated with this object */
+ public javax.accessibility.AccessibleText getAccessibleText() {
+ return menu.getAccessibleText();
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleStateSet getAccessibleStateSet() {
+ return menu.getAccessibleStateSet();
+ }
+
+ public java.util.Locale getLocale() {
+ return menu.getLocale();
+ }
+
+ public int getAccessibleIndexInParent() {
+ return -1;
+ }
+
+ public int getAccessibleChildrenCount() {
+ return menu.getAccessibleChildrenCount();
+ }
+
+ public javax.accessibility.Accessible getAccessibleChild(int i) {
+ return menu.getAccessibleChild(i);
+ }
+
+ public javax.accessibility.AccessibleRole getAccessibleRole() {
+ return javax.accessibility.AccessibleRole.POPUP_MENU;
+ }
+
+ /*
+ * AccessibleComponent
+ */
+ public void addFocusListener(java.awt.event.FocusListener fl) {
+ menuComponent.addFocusListener(fl);
+ }
+
+ public void removeFocusListener(java.awt.event.FocusListener fl) {
+ menuComponent.removeFocusListener(fl);
+ }
+
+ /** Returns the background color of the object */
+ public java.awt.Color getBackground() {
+ return menuComponent.getBackground();
+ }
+
+ public void setBackground(java.awt.Color c) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the foreground color of the object */
+ public java.awt.Color getForeground() {
+ return menuComponent.getForeground();
+ }
+
+ public void setForeground(java.awt.Color c) {
+ menuComponent.setForeground(c);
+ }
+
+ public java.awt.Cursor getCursor() {
+ return menuComponent.getCursor();
+ }
+
+ public void setCursor(java.awt.Cursor cursor) {
+ menuComponent.setCursor(cursor);
+ }
+
+ public java.awt.Font getFont() {
+ return menuComponent.getFont();
+ }
+
+ public void setFont(java.awt.Font f) {
+ menuComponent.setFont(f);
+ }
+
+ public java.awt.FontMetrics getFontMetrics(java.awt.Font f) {
+ return menuComponent.getFontMetrics(f);
+ }
+
+ public boolean isEnabled() {
+ return menuComponent.isEnabled();
+ }
+
+ public void setEnabled(boolean b) {
+ menuComponent.setEnabled(b);
+ }
+
+ public boolean isVisible() {
+ return menuComponent.isVisible();
+ }
+
+ public void setVisible(boolean b) {
+ menuComponent.setVisible(b);
+ }
+
+ public boolean isShowing() {
+ return menuComponent.isShowing();
+ }
+
+ public boolean contains(java.awt.Point p) {
+ java.awt.Dimension d = getSize();
+
+ if (Build.DEBUG) {
+ System.err.println("PopupMenuProxy.containsPoint(" + p.x + "," +
+ p.y + ") returns " +
+ (((d.width >= 0) && (p.x < d.width) && (d.height >= 0) &&
+ (p.y < d.height)) ? "true" : "false"));
+ }
+
+ if ((d.width >= 0) && (p.x < d.width) && (d.height >= 0) &&
+ (p.y < d.height)) {
+ return true;
+ }
+
+ return false;
+ }
+
+ /** Returns the location of the object on the screen. */
+ public java.awt.Point getLocationOnScreen() {
+ return new java.awt.Point(x,y);
+ }
+
+ /** Gets the location of this component in the form of a point specifying the component's top-left corner */
+ public java.awt.Point getLocation() {
+ // This object represents a toplevel, so this is the same as getLocationOnScreen()
+ return getLocationOnScreen();
+ }
+
+ /** Moves this component to a new location */
+ public void setLocation(java.awt.Point p) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Gets the bounds of this component in the form of a Rectangle object */
+ public java.awt.Rectangle getBounds() {
+ return new java.awt.Rectangle(x, y, width, height);
+ }
+
+ /** Moves and resizes this component to conform to the new bounding rectangle r */
+ public void setBounds(java.awt.Rectangle r) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the size of this component in the form of a Dimension object */
+ public java.awt.Dimension getSize() {
+ return new java.awt.Dimension(width, height);
+ }
+
+ /** Resizes this component so that it has width d.width and height d.height */
+ public void setSize(java.awt.Dimension d) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the Accessible child, if one exists, contained at the local
+ * coordinate Point
+ */
+ public javax.accessibility.Accessible getAccessibleAt(java.awt.Point p) {
+ java.awt.Point p2 = menuComponent.getLocationOnScreen();
+ return menuComponent.getAccessibleAt(
+ new java.awt.Point(p.x + x - p2.x, p.y + y - p2.y));
+ }
+
+ public boolean isFocusTraversable() {
+ return menuComponent.isFocusTraversable();
+ }
+
+ public void requestFocus() {
+ menuComponent.requestFocus();
+ }
+ }
+
+ protected static class ListProxy extends AccessibleContext
+ implements Accessible, AccessibleComponent {
+ AccessibleContext list;
+ AccessibleComponent listComponent;
+
+ ListProxy(AccessibleContext ac) {
+ list = ac;
+ listComponent = list.getAccessibleComponent();
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleContext getAccessibleContext() {
+ return this;
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleComponent getAccessibleComponent() {
+ return this;
+ }
+
+ /** Returns the AccessibleSelection associated with this object */
+ public javax.accessibility.AccessibleSelection getAccessibleSelection() {
+ return list.getAccessibleSelection();
+ }
+
+ /** Returns the AccessibleContext associated with this object */
+ public javax.accessibility.AccessibleStateSet getAccessibleStateSet() {
+ return list.getAccessibleStateSet();
+ }
+
+ public java.util.Locale getLocale() {
+ return list.getLocale();
+ }
+
+ public int getAccessibleIndexInParent() {
+ return -1;
+ }
+
+ public int getAccessibleChildrenCount() {
+ return list.getAccessibleChildrenCount();
+ }
+
+ public javax.accessibility.Accessible getAccessibleChild(int i) {
+ return list.getAccessibleChild(i);
+ }
+
+ public javax.accessibility.AccessibleRole getAccessibleRole() {
+ return javax.accessibility.AccessibleRole.LIST;
+ }
+
+ /*
+ * AccessibleComponent
+ */
+ public void addFocusListener(java.awt.event.FocusListener fl) {
+ listComponent.addFocusListener(fl);
+ }
+
+ public void removeFocusListener(java.awt.event.FocusListener fl) {
+ listComponent.removeFocusListener(fl);
+ }
+
+ /** Returns the background color of the object */
+ public java.awt.Color getBackground() {
+ return listComponent.getBackground();
+ }
+
+ public void setBackground(java.awt.Color c) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the foreground color of the object */
+ public java.awt.Color getForeground() {
+ return listComponent.getForeground();
+ }
+
+ public void setForeground(java.awt.Color c) {
+ listComponent.setForeground(c);
+ }
+
+ public java.awt.Cursor getCursor() {
+ return listComponent.getCursor();
+ }
+
+ public void setCursor(java.awt.Cursor cursor) {
+ listComponent.setCursor(cursor);
+ }
+
+ public java.awt.Font getFont() {
+ return listComponent.getFont();
+ }
+
+ public void setFont(java.awt.Font f) {
+ listComponent.setFont(f);
+ }
+
+ public java.awt.FontMetrics getFontMetrics(java.awt.Font f) {
+ return listComponent.getFontMetrics(f);
+ }
+
+ public boolean isEnabled() {
+ return listComponent.isEnabled();
+ }
+
+ public void setEnabled(boolean b) {
+ listComponent.setEnabled(b);
+ }
+
+ public boolean isVisible() {
+ return listComponent.isVisible();
+ }
+
+ public void setVisible(boolean b) {
+ listComponent.setVisible(b);
+ }
+
+ public boolean isShowing() {
+ return listComponent.isShowing();
+ }
+
+ public boolean contains(java.awt.Point p) {
+ return listComponent.contains(p);
+ }
+
+ /** Returns the location of the object on the screen. */
+ public java.awt.Point getLocationOnScreen() {
+ return listComponent.getLocationOnScreen();
+ }
+
+ /** Gets the location of this component in the form of a point specifying
+ * the component's top-left corner
+ */
+ public java.awt.Point getLocation() {
+ // This object represents a toplevel object, so getLocation() should
+ // return the same as getLocationOnScreen().
+ return getLocationOnScreen();
+ }
+
+ /** Moves this component to a new location */
+ public void setLocation(java.awt.Point p) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Gets the bounds of this component in the form of a Rectangle object */
+ public java.awt.Rectangle getBounds() {
+ java.awt.Point p = getLocationOnScreen();
+ java.awt.Dimension d = getSize();
+ return new java.awt.Rectangle(p.x, p.y, d.width, d.height);
+ }
+
+ /** Moves and resizes this component to conform to the new bounding rectangle r */
+ public void setBounds(java.awt.Rectangle r) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the size of this component in the form of a Dimension object */
+ public java.awt.Dimension getSize() {
+ return listComponent.getSize();
+ }
+
+ /** Resizes this component so that it has width d.width and height d.height */
+ public void setSize(java.awt.Dimension d) {
+ // Not supported by UNO accessibility API
+ }
+
+ /** Returns the Accessible child, if one exists, contained at the local
+ * coordinate Point
+ */
+ public javax.accessibility.Accessible getAccessibleAt(java.awt.Point p) {
+ return listComponent.getAccessibleAt(p);
+ }
+
+ public boolean isFocusTraversable() {
+ return listComponent.isFocusTraversable();
+ }
+
+ public void requestFocus() {
+ listComponent.requestFocus();
+ }
+ }
+}
diff --git a/accessibility/bridge/org/openoffice/accessibility/java_uno_accessbridge.component b/accessibility/bridge/org/openoffice/accessibility/java_uno_accessbridge.component
new file mode 100644
index 000000000000..5fc897f2d5aa
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/java_uno_accessbridge.component
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--**********************************************************************
+*
+* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+*
+* Copyright 2000, 2010 Oracle and/or its affiliates.
+*
+* OpenOffice.org - a multi-platform office productivity suite
+*
+* This file is part of OpenOffice.org.
+*
+* OpenOffice.org is free software: you can redistribute it and/or modify
+* it under the terms of the GNU Lesser General Public License version 3
+* only, as published by the Free Software Foundation.
+*
+* OpenOffice.org is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU Lesser General Public License version 3 for more details
+* (a copy is included in the LICENSE file that accompanied this code).
+*
+* You should have received a copy of the GNU Lesser General Public License
+* version 3 along with OpenOffice.org. If not, see
+* <http://www.openoffice.org/license.html>
+* for a copy of the LGPLv3 License.
+*
+**********************************************************************-->
+
+<component loader="com.sun.star.loader.Java2"
+ xmlns="http://openoffice.org/2010/uno-components">
+ <implementation name="org.openoffice.accessibility.AccessBridge">
+ <service name="com.sun.star.accessibility.AccessBridge"/>
+ </implementation>
+</component>
diff --git a/accessibility/bridge/org/openoffice/accessibility/makefile.mk b/accessibility/bridge/org/openoffice/accessibility/makefile.mk
new file mode 100755
index 000000000000..1fa29f5bfcb1
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/makefile.mk
@@ -0,0 +1,62 @@
+#*************************************************************************
+#
+# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+#
+# Copyright 2000, 2010 Oracle and/or its affiliates.
+#
+# OpenOffice.org - a multi-platform office productivity suite
+#
+# This file is part of OpenOffice.org.
+#
+# OpenOffice.org is free software: you can redistribute it and/or modify
+# it under the terms of the GNU Lesser General Public License version 3
+# only, as published by the Free Software Foundation.
+#
+# OpenOffice.org is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU Lesser General Public License version 3 for more details
+# (a copy is included in the LICENSE file that accompanied this code).
+#
+# You should have received a copy of the GNU Lesser General Public License
+# version 3 along with OpenOffice.org. If not, see
+# <http://www.openoffice.org/license.html>
+# for a copy of the LGPLv3 License.
+#
+#*************************************************************************
+
+PRJNAME = accessibility
+PRJ = ..$/..$/..$/..
+TARGET = java_uno_accessbridge
+PACKAGE = org$/openoffice$/accessibility
+
+# --- Settings -----------------------------------------------------
+
+.INCLUDE : settings.mk
+
+JARFILES = jurt.jar unoil.jar ridl.jar
+JAVAFILES = \
+ AccessBridge.java \
+ KeyHandler.java \
+ PopupWindow.java \
+ WindowsAccessBridgeAdapter.java
+
+JAVACLASSFILES= $(foreach,i,$(JAVAFILES) $(CLASSDIR)$/$(PACKAGE)$/$(i:b).class)
+
+JARTARGET = $(TARGET).jar
+JARCOMPRESS = TRUE
+JARCLASSDIRS = $(PACKAGE) org/openoffice/java/accessibility
+CUSTOMMANIFESTFILE = manifest
+
+# --- Targets ------------------------------------------------------
+
+
+.INCLUDE : target.mk
+
+ALLTAR : $(MISC)/java_uno_accessbridge.component
+
+$(MISC)/java_uno_accessbridge.component .ERRREMOVE : \
+ $(SOLARENV)/bin/createcomponent.xslt java_uno_accessbridge.component
+ $(XSLTPROC) --nonet --stringparam uri \
+ '$(COMPONENTPREFIX_BASIS_JAVA)$(JARTARGET)' -o $@ \
+ $(SOLARENV)/bin/createcomponent.xslt java_uno_accessbridge.component
diff --git a/accessibility/bridge/org/openoffice/accessibility/manifest b/accessibility/bridge/org/openoffice/accessibility/manifest
new file mode 100755
index 000000000000..4b5ffd54d34b
--- /dev/null
+++ b/accessibility/bridge/org/openoffice/accessibility/manifest
@@ -0,0 +1,2 @@
+RegistrationClassName: org.openoffice.accessibility.AccessBridge
+UNO-Type-Path: