mozilla-a11y.patch
changeset 382 67f876aafae8
parent 380 0887a88b1e85
child 386 7784e72b1a3a
equal deleted inserted replaced
380:0887a88b1e85 382:67f876aafae8
     1 # HG changeset patch
       
     2 # User Michael Gorse <mgorse@suse.com>
       
     3 # Parent 2c115988d04c0a0a8cb75b3a597ecdb2c4c001c9
       
     4 a11y only enabled from Gnome 2's GConf setting
       
     5 https://bugzilla.novell.com/show_bug.cgi?id=732898
       
     6 https://bugzilla.mozilla.org/show_bug.cgi?id=693343
       
     7 
       
     8 diff --git a/accessible/src/atk/Makefile.in b/accessible/src/atk/Makefile.in
       
     9 --- a/accessible/src/atk/Makefile.in
       
    10 +++ b/accessible/src/atk/Makefile.in
       
    11 @@ -87,15 +87,19 @@ EXPORTS = \
       
    12  # we want to force the creation of a static lib.
       
    13  FORCE_STATIC_LIB = 1
       
    14  
       
    15  include $(topsrcdir)/config/rules.mk
       
    16  
       
    17  CFLAGS		+= $(MOZ_GTK2_CFLAGS)
       
    18  CXXFLAGS	+= $(MOZ_GTK2_CFLAGS)
       
    19  
       
    20 +ifdef MOZ_ENABLE_DBUS
       
    21 +CXXFLAGS += $(MOZ_DBUS_CFLAGS)
       
    22 +endif
       
    23 +
       
    24  LOCAL_INCLUDES += \
       
    25    -I$(srcdir) \
       
    26    -I$(srcdir)/../base \
       
    27    -I$(srcdir)/../html \
       
    28    -I$(srcdir)/../xul \
       
    29    -I$(topsrcdir)/other-licenses/atk-1.0 \
       
    30    $(NULL)
       
    31 diff --git a/accessible/src/atk/nsApplicationAccessibleWrap.cpp b/accessible/src/atk/nsApplicationAccessibleWrap.cpp
       
    32 --- a/accessible/src/atk/nsApplicationAccessibleWrap.cpp
       
    33 +++ b/accessible/src/atk/nsApplicationAccessibleWrap.cpp
       
    34 @@ -47,29 +47,29 @@
       
    35  #include "nsIPrefBranch.h"
       
    36  #include "nsIServiceManager.h"
       
    37  #include "nsAutoPtr.h"
       
    38  #include "nsAccessibilityService.h"
       
    39  #include "AtkSocketAccessible.h"
       
    40  
       
    41  #include <gtk/gtk.h>
       
    42  #include <atk/atk.h>
       
    43 +#ifdef MOZ_ENABLE_DBUS
       
    44 +#include <dbus/dbus.h>
       
    45 +#endif
       
    46 +
       
    47 +using namespace mozilla::a11y;
       
    48  
       
    49  typedef GType (* AtkGetTypeType) (void);
       
    50  GType g_atk_hyperlink_impl_type = G_TYPE_INVALID;
       
    51  static bool sATKChecked = false;
       
    52  static PRLibrary *sATKLib = nsnull;
       
    53  static const char sATKLibName[] = "libatk-1.0.so.0";
       
    54  static const char sATKHyperlinkImplGetTypeSymbol[] =
       
    55      "atk_hyperlink_impl_get_type";
       
    56 -static const char sAccEnv [] = "GNOME_ACCESSIBILITY";
       
    57 -static const char sSysPrefService [] =
       
    58 -    "@mozilla.org/system-preference-service;1";
       
    59 -static const char sAccessibilityKey [] =
       
    60 -    "config.use_system_prefs.accessibility";
       
    61  
       
    62  /* gail function pointer */
       
    63  static guint (* gail_add_global_event_listener) (GSignalEmissionHook listener,
       
    64                                                   const gchar *event_type);
       
    65  static void (* gail_remove_global_event_listener) (guint remove_listener);
       
    66  static void (* gail_remove_key_event_listener) (guint remove_listener);
       
    67  static AtkObject * (*gail_get_root) (void);
       
    68  
       
    69 @@ -609,36 +609,17 @@ toplevel_event_watcher(GSignalInvocation
       
    70    }
       
    71  
       
    72    return TRUE;
       
    73  }
       
    74  
       
    75  bool
       
    76  nsApplicationAccessibleWrap::Init()
       
    77  {
       
    78 -    // XXX following code is copied from widget/src/gtk2/nsWindow.cpp
       
    79 -    // we should put it to somewhere that can be used from both modules
       
    80 -    // see bug 390761
       
    81 -
       
    82 -    // check if accessibility enabled/disabled by environment variable
       
    83 -    bool isGnomeATEnabled = false;
       
    84 -    const char *envValue = PR_GetEnv(sAccEnv);
       
    85 -    if (envValue) {
       
    86 -        isGnomeATEnabled = !!atoi(envValue);
       
    87 -    } else {
       
    88 -        //check gconf-2 setting
       
    89 -        nsresult rv;
       
    90 -        nsCOMPtr<nsIPrefBranch> sysPrefService =
       
    91 -            do_GetService(sSysPrefService, &rv);
       
    92 -        if (NS_SUCCEEDED(rv) && sysPrefService) {
       
    93 -            sysPrefService->GetBoolPref(sAccessibilityKey, &isGnomeATEnabled);
       
    94 -        }
       
    95 -    }
       
    96 -
       
    97 -    if (isGnomeATEnabled) {
       
    98 +    if (ShouldA11yBeEnabled()) {
       
    99          // load and initialize gail library
       
   100          nsresult rv = LoadGtkModule(sGail);
       
   101          if (NS_SUCCEEDED(rv)) {
       
   102              (*sGail.init)();
       
   103          }
       
   104          else {
       
   105              MAI_LOG_DEBUG(("Fail to load lib: %s\n", sGail.libName));
       
   106          }
       
   107 @@ -877,8 +858,129 @@ LoadGtkModule(GnomeAccessibilityModule& 
       
   108                         aModule.init ? aModule.shutdownName : aModule.initName,
       
   109                         aModule.libName));
       
   110          PR_UnloadLibrary(aModule.lib);
       
   111          aModule.lib = NULL;
       
   112          return NS_ERROR_FAILURE;
       
   113      }
       
   114      return NS_OK;
       
   115  }
       
   116 +
       
   117 +namespace mozilla {
       
   118 +namespace a11y {
       
   119 +
       
   120 +#ifdef MOZ_ENABLE_DBUS
       
   121 +  static DBusPendingCall *a11yPendingCall = NULL;
       
   122 +#endif
       
   123 +
       
   124 +void
       
   125 +PreInit()
       
   126 +{
       
   127 +  static bool sChecked = false;
       
   128 +  if (sChecked)
       
   129 +    return;
       
   130 +  sChecked = true;
       
   131 +  DBusError error;
       
   132 +  dbus_error_init(&error);
       
   133 +  DBusConnection* bus = dbus_bus_get(DBUS_BUS_SESSION, &error);
       
   134 +  if (!bus)
       
   135 +    return;
       
   136 +  dbus_connection_set_exit_on_disconnect(bus, false);
       
   137 +
       
   138 +  DBusMessage *message;
       
   139 +  message = dbus_message_new_method_call("org.a11y.Bus", "/org/a11y/bus",
       
   140 +                                         "org.freedesktop.DBus.Properties",
       
   141 +                                         "Get");
       
   142 +  if (!message)
       
   143 +    goto dbus_done;
       
   144 +
       
   145 +  static const char* iface = "org.a11y.Status";
       
   146 +  static const char* member = "IsEnabled";
       
   147 +  dbus_message_append_args(message, DBUS_TYPE_STRING, &iface,
       
   148 +                           DBUS_TYPE_STRING, &member, DBUS_TYPE_INVALID);
       
   149 +  dbus_connection_send_with_reply(bus, message, &a11yPendingCall, 1000);
       
   150 +
       
   151 +dbus_done:
       
   152 +  if (message)
       
   153 +    dbus_message_unref(message);
       
   154 +  if (bus)
       
   155 +    dbus_connection_unref(bus);
       
   156 +  dbus_error_free(&error);
       
   157 +}
       
   158 +
       
   159 +bool
       
   160 +ShouldA11yBeEnabled()
       
   161 +{
       
   162 +  static bool sChecked = false, sShouldEnable = false;
       
   163 +  if (sChecked)
       
   164 +    return sShouldEnable;
       
   165 +
       
   166 +  sChecked = true;
       
   167 +
       
   168 +  // check if accessibility enabled/disabled by environment variable
       
   169 +  static const char sAccEnv [] = "GNOME_ACCESSIBILITY";
       
   170 +  const char* envValue = PR_GetEnv(sAccEnv);
       
   171 +  if (envValue)
       
   172 +    return sShouldEnable = !!atoi(envValue);
       
   173 +
       
   174 +#ifdef MOZ_ENABLE_DBUS
       
   175 +  PreInit();
       
   176 +  bool dbusSuccess = false;
       
   177 +  DBusMessage *reply = nsnull;
       
   178 +  if (a11yPendingCall) {
       
   179 +    dbus_pending_call_block(a11yPendingCall);
       
   180 +    reply = dbus_pending_call_steal_reply(a11yPendingCall);
       
   181 +    dbus_pending_call_unref(a11yPendingCall);
       
   182 +    a11yPendingCall = nsnull;
       
   183 +  }
       
   184 +  if (!reply ||
       
   185 +      dbus_message_get_type(reply) != DBUS_MESSAGE_TYPE_METHOD_RETURN ||
       
   186 +      strcmp(dbus_message_get_signature (reply), "v"))
       
   187 +    goto dbus_done;
       
   188 +
       
   189 +  DBusMessageIter iter, iter_variant, iter_struct;
       
   190 +  dbus_bool_t dResult;
       
   191 +  dbus_message_iter_init(reply, &iter);
       
   192 +  dbus_message_iter_recurse (&iter, &iter_variant);
       
   193 +  switch (dbus_message_iter_get_arg_type(&iter_variant)) {
       
   194 +    case DBUS_TYPE_STRUCT:
       
   195 +      // at-spi2-core 2.2.0-2.2.1 had a bug where it returned a struct
       
   196 +      dbus_message_iter_recurse(&iter_variant, &iter_struct);
       
   197 +      if (dbus_message_iter_get_arg_type(&iter_struct) == DBUS_TYPE_BOOLEAN) {
       
   198 +        dbus_message_iter_get_basic(&iter_struct, &dResult);
       
   199 +        sShouldEnable = dResult;
       
   200 +        dbusSuccess = true;
       
   201 +      }
       
   202 +
       
   203 +      break;
       
   204 +    case DBUS_TYPE_BOOLEAN:
       
   205 +      dbus_message_iter_get_basic(&iter_variant, &dResult);
       
   206 +      sShouldEnable = dResult;
       
   207 +      dbusSuccess = true;
       
   208 +      break;
       
   209 +    default:
       
   210 +      break;
       
   211 +  }
       
   212 +
       
   213 +  dbus_done:
       
   214 +  if (reply)
       
   215 +    dbus_message_unref(reply);
       
   216 +
       
   217 +  if (dbusSuccess)
       
   218 +    return sShouldEnable;
       
   219 +#endif
       
   220 +
       
   221 +  //check gconf-2 setting
       
   222 +  nsresult rv = NS_OK;
       
   223 +  static const char sSysPrefService [] =
       
   224 +    "@mozilla.org/system-preference-service;1";
       
   225 +  static const char sAccessibilityKey [] =
       
   226 +    "config.use_system_prefs.accessibility";
       
   227 +  nsCOMPtr<nsIPrefBranch> sysPrefService =
       
   228 +    do_GetService(sSysPrefService, &rv);
       
   229 +  if (NS_SUCCEEDED(rv) && sysPrefService)
       
   230 +    sysPrefService->GetBoolPref(sAccessibilityKey, &sShouldEnable);
       
   231 +
       
   232 +  return sShouldEnable;
       
   233 +}
       
   234 +} // namespace a11y
       
   235 +} // namespace mozilla
       
   236 +
       
   237 diff --git a/accessible/src/base/nsAccessibilityService.h b/accessible/src/base/nsAccessibilityService.h
       
   238 --- a/accessible/src/base/nsAccessibilityService.h
       
   239 +++ b/accessible/src/base/nsAccessibilityService.h
       
   240 @@ -46,16 +46,33 @@
       
   241  
       
   242  #include "mozilla/a11y/FocusManager.h"
       
   243  
       
   244  #include "nsIObserver.h"
       
   245  
       
   246  namespace mozilla {
       
   247  namespace a11y {
       
   248  
       
   249 +#ifdef MOZ_ACCESSIBILITY_ATK
       
   250 +/**
       
   251 + * + * Perform initialization that should be done as soon as possible, in
       
   252 + * order
       
   253 + * + * to minimize startup time.
       
   254 + * + * XXX: this function and the next defined in
       
   255 + * nsApplicationAccessibleWrap.cpp
       
   256 + * + */
       
   257 +void PreInit();
       
   258 +
       
   259 +/**
       
   260 + * + * Is platform accessibility enabled.
       
   261 + * + * Only used on linux with atk for now.
       
   262 + * + */
       
   263 +bool ShouldA11yBeEnabled();
       
   264 +#endif
       
   265 +
       
   266  /**
       
   267   * Return focus manager.
       
   268   */
       
   269  FocusManager* FocusMgr();
       
   270  
       
   271  } // namespace a11y
       
   272  } // namespace mozilla
       
   273  
       
   274 diff --git a/widget/src/gtk2/nsWindow.cpp b/widget/src/gtk2/nsWindow.cpp
       
   275 --- a/widget/src/gtk2/nsWindow.cpp
       
   276 +++ b/widget/src/gtk2/nsWindow.cpp
       
   277 @@ -105,29 +105,21 @@
       
   278  #include "nsIStringBundle.h"
       
   279  #include "nsGfxCIID.h"
       
   280  #include "nsIObserverService.h"
       
   281  
       
   282  #include "nsIdleService.h"
       
   283  #include "nsIPropertyBag2.h"
       
   284  
       
   285  #ifdef ACCESSIBILITY
       
   286 -#include "nsIAccessibilityService.h"
       
   287 +#include "nsAccessibilityService.h"
       
   288  #include "nsIAccessibleDocument.h"
       
   289 -#include "prenv.h"
       
   290 -#include "stdlib.h"
       
   291  
       
   292  using namespace mozilla;
       
   293  
       
   294 -static bool sAccessibilityChecked = false;
       
   295 -/* static */
       
   296 -bool nsWindow::sAccessibilityEnabled = false;
       
   297 -static const char sSysPrefService [] = "@mozilla.org/system-preference-service;1";
       
   298 -static const char sAccEnv [] = "GNOME_ACCESSIBILITY";
       
   299 -static const char sAccessibilityKey [] = "config.use_system_prefs.accessibility";
       
   300  #endif
       
   301  
       
   302  /* For SetIcon */
       
   303  #include "nsAppDirectoryServiceDefs.h"
       
   304  #include "nsXPIDLString.h"
       
   305  #include "nsIFile.h"
       
   306  #include "nsILocalFile.h"
       
   307  
       
   308 @@ -1111,19 +1103,18 @@ nsWindow::Show(bool aState)
       
   309              NativeResize(mBounds.x, mBounds.y, mBounds.width, mBounds.height,
       
   310                           false);
       
   311          } else if (mNeedsResize) {
       
   312              NativeResize(mBounds.width, mBounds.height, false);
       
   313          }
       
   314      }
       
   315  
       
   316  #ifdef ACCESSIBILITY
       
   317 -    if (aState && sAccessibilityEnabled) {
       
   318 +    if (aState && a11y::ShouldA11yBeEnabled())
       
   319          CreateRootAccessible();
       
   320 -    }
       
   321  #endif
       
   322  
       
   323      NativeShow(aState);
       
   324  
       
   325      return NS_OK;
       
   326  }
       
   327  
       
   328  NS_IMETHODIMP
       
   329 @@ -3885,16 +3876,21 @@ nsWindow::Create(nsIWidget        *aPare
       
   330      nsIWidget *baseParent = aInitData &&
       
   331          (aInitData->mWindowType == eWindowType_dialog ||
       
   332           aInitData->mWindowType == eWindowType_toplevel ||
       
   333           aInitData->mWindowType == eWindowType_invisible) ?
       
   334          nsnull : aParent;
       
   335  
       
   336      NS_ASSERTION(!mWindowGroup, "already have window group (leaking it)");
       
   337  
       
   338 +#ifdef ACCESSIBILITY
       
   339 +    // Send a DBus message to check whether a11y is enabled
       
   340 +    a11y::PreInit();
       
   341 +#endif
       
   342 +
       
   343      // Ensure that the toolkit is created.
       
   344      nsGTKToolkit::GetToolkit();
       
   345  
       
   346      // initialize all the common bits of this class
       
   347      BaseCreate(baseParent, aRect, aHandleEventFunction, aContext, aInitData);
       
   348  
       
   349      // Do we need to listen for resizes?
       
   350      bool listenForResizes = false;;
       
   351 @@ -4278,43 +4274,16 @@ nsWindow::Create(nsIWidget        *aPare
       
   352          LOG(("\tmGdkWindow %p %lx\n", (void *)mGdkWindow,
       
   353               gdk_x11_window_get_xid(mGdkWindow)));
       
   354      }
       
   355  
       
   356      // resize so that everything is set to the right dimensions
       
   357      if (!mIsTopLevel)
       
   358          Resize(mBounds.x, mBounds.y, mBounds.width, mBounds.height, false);
       
   359  
       
   360 -#ifdef ACCESSIBILITY
       
   361 -    nsresult rv;
       
   362 -    if (!sAccessibilityChecked) {
       
   363 -        sAccessibilityChecked = true;
       
   364 -
       
   365 -        //check if accessibility enabled/disabled by environment variable
       
   366 -        const char *envValue = PR_GetEnv(sAccEnv);
       
   367 -        if (envValue) {
       
   368 -            sAccessibilityEnabled = atoi(envValue) != 0;
       
   369 -            LOG(("Accessibility Env %s=%s\n", sAccEnv, envValue));
       
   370 -        }
       
   371 -        //check gconf-2 setting
       
   372 -        else {
       
   373 -            nsCOMPtr<nsIPrefBranch> sysPrefService =
       
   374 -                do_GetService(sSysPrefService, &rv);
       
   375 -            if (NS_SUCCEEDED(rv) && sysPrefService) {
       
   376 -
       
   377 -                // do the work to get gconf setting.
       
   378 -                // will be done soon later.
       
   379 -                sysPrefService->GetBoolPref(sAccessibilityKey,
       
   380 -                                            &sAccessibilityEnabled);
       
   381 -            }
       
   382 -
       
   383 -        }
       
   384 -    }
       
   385 -#endif
       
   386 -
       
   387  #ifdef MOZ_DFB
       
   388      if (!mDFB) {
       
   389           DirectFBCreate( &mDFB );
       
   390  
       
   391           D_ASSUME( mDFB != NULL );
       
   392  
       
   393           if (mDFB)
       
   394                mDFB->GetDisplayLayer( mDFB, DLID_PRIMARY, &mDFBLayer );
       
   395 @@ -6504,19 +6473,18 @@ nsWindow::DispatchAccessibleEvent()
       
   396      DispatchEvent(&event, status);
       
   397  
       
   398      return event.mAccessible;
       
   399  }
       
   400  
       
   401  void
       
   402  nsWindow::DispatchEventToRootAccessible(PRUint32 aEventType)
       
   403  {
       
   404 -    if (!sAccessibilityEnabled) {
       
   405 +    if (!a11y::ShouldA11yBeEnabled())
       
   406          return;
       
   407 -    }
       
   408  
       
   409      nsCOMPtr<nsIAccessibilityService> accService =
       
   410          do_GetService("@mozilla.org/accessibilityService;1");
       
   411      if (!accService) {
       
   412          return;
       
   413      }
       
   414  
       
   415      // Get the root document accessible and fire event to it.