e034c91075684321c98ed724e378c9ee8a0913e8
[platform/upstream/atk.git] / atk / atkobject.c
1 /* ATK -  Accessibility Toolkit
2  * Copyright 2001 Sun Microsystems Inc.
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the
16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17  * Boston, MA 02111-1307, USA.
18  */
19
20 #include <string.h>
21 #include <locale.h>
22
23 #include <glib-object.h>
24
25 #ifdef G_OS_WIN32
26 #define STRICT
27 #include <windows.h>
28 #undef STRICT
29 #undef FOCUS_EVENT              /* <windows.h> pollutes the namespace
30                                  * like a six hundred pound gorilla */
31 #endif
32
33 #include "atk.h"
34 #include "atkmarshal.h"
35 #include "atkintl.h"
36
37 /**
38  * SECTION:atkobject
39  * @Short_description: The base object class for the Accessibility Toolkit API.
40  * @Title:AtkObject
41  *
42  * This class is the primary class for accessibility support via the
43  * Accessibility ToolKit (ATK).  Objects which are instances of
44  * #AtkObject (or instances of AtkObject-derived types) are queried
45  * for properties which relate basic (and generic) properties of a UI
46  * component such as name and description.  Instances of #AtkObject
47  * may also be queried as to whether they implement other ATK
48  * interfaces (e.g. #AtkAction, #AtkComponent, etc.), as appropriate
49  * to the role which a given UI component plays in a user interface.
50  *
51  * All UI components in an application which provide useful
52  * information or services to the user must provide corresponding
53  * #AtkObject instances on request (in GTK+, for instance, usually on
54  * a call to #gtk_widget_get_accessible ()), either via ATK support
55  * built into the toolkit for the widget class or ancestor class, or
56  * in the case of custom widgets, if the inherited #AtkObject
57  * implementation is insufficient, via instances of a new #AtkObject
58  * subclass.
59  *
60  * See also: #AtkObjectFactory, #AtkRegistry.  (GTK+ users see also
61  * #GtkAccessible).
62  *
63  */
64
65 static GPtrArray *role_names = NULL;
66
67 enum
68 {
69   PROP_0,  /* gobject convention */
70
71   PROP_NAME,
72   PROP_DESCRIPTION,
73   PROP_PARENT,      /* ancestry has changed */
74   PROP_VALUE,
75   PROP_ROLE,
76   PROP_LAYER,
77   PROP_MDI_ZORDER,
78   PROP_TABLE_CAPTION,
79   PROP_TABLE_COLUMN_DESCRIPTION,
80   PROP_TABLE_COLUMN_HEADER,
81   PROP_TABLE_ROW_DESCRIPTION,
82   PROP_TABLE_ROW_HEADER,
83   PROP_TABLE_SUMMARY,
84   PROP_TABLE_CAPTION_OBJECT,
85   PROP_HYPERTEXT_NUM_LINKS,
86   PROP_LAST         /* gobject convention */
87 };
88
89 enum {
90   CHILDREN_CHANGED,
91   FOCUS_EVENT,
92   PROPERTY_CHANGE,
93   STATE_CHANGE,
94   VISIBLE_DATA_CHANGED,
95   ACTIVE_DESCENDANT_CHANGED,
96   
97   LAST_SIGNAL
98 };
99
100 /* These are listed here for extraction by intltool */
101 #if 0
102   N_("invalid")
103   N_("accelerator label")
104   N_("alert")
105   N_("animation")
106   N_("arrow")
107   N_("calendar")
108   N_("canvas")
109   N_("check box")
110   N_("check menu item")
111   N_("color chooser")
112   N_("column header")
113   N_("combo box")
114   N_("dateeditor")
115   N_("desktop icon")
116   N_("desktop frame")
117   N_("dial")
118   N_("dialog")
119   N_("directory pane")
120   N_("drawing area")
121   N_("file chooser")
122   N_("filler")
123   /* I know it looks wrong but that is what Java returns */
124   N_("fontchooser")
125   N_("frame")
126   N_("glass pane")
127   N_("html container")
128   N_("icon")
129   N_("image")
130   N_("internal frame")
131   N_("label")
132   N_("layered pane")
133   N_("list")
134   N_("list item")
135   N_("menu")
136   N_("menu bar")
137   N_("menu item")
138   N_("option pane")
139   N_("page tab")
140   N_("page tab list")
141   N_("panel")
142   N_("password text")
143   N_("popup menu")
144   N_("progress bar")
145   N_("push button")
146   N_("radio button")
147   N_("radio menu item")
148   N_("root pane")
149   N_("row header")
150   N_("scroll bar")
151   N_("scroll pane")
152   N_("separator")
153   N_("slider")
154   N_("split pane")
155   N_("spin button")
156   N_("statusbar")
157   N_("table")
158   N_("table cell")
159   N_("table column header")
160   N_("table row header")
161   N_("tear off menu item")
162   N_("terminal")
163   N_("text")
164   N_("toggle button")
165   N_("tool bar")
166   N_("tool tip")
167   N_("tree")
168   N_("tree table")
169   N_("unknown")
170   N_("viewport")
171   N_("window")
172   N_("header")
173   N_("footer")
174   N_("paragraph")
175   N_("ruler")
176   N_("application")
177   N_("autocomplete")
178   N_("edit bar")
179   N_("embedded component")
180   N_("entry")
181   N_("chart")
182   N_("caption")
183   N_("document frame")
184   N_("heading")
185   N_("page")
186   N_("section")
187   N_("redundant object")
188   N_("form")
189   N_("link")
190   N_("input method window")
191   N_("table row")
192   N_("tree item")
193   N_("document spreadsheet")
194   N_("document presentation")
195   N_("document text")
196   N_("document web")
197   N_("document email")
198   N_("comment")
199   N_("list box")
200   N_("grouping")
201   N_("image map")
202   N_("notification")
203   N_("info bar")
204   N_("level bar")
205   N_("title bar")
206   N_("block quote")
207   N_("audio")
208   N_("video")
209   N_("definition")
210   N_("article")
211   N_("landmark")
212   N_("log")
213   N_("marquee")
214   N_("math")
215   N_("rating")
216   N_("timer")
217   N_("description list")
218   N_("description term")
219   N_("description value")
220 #endif /* 0 */
221
222 static void            atk_object_class_init        (AtkObjectClass  *klass);
223 static void            atk_object_init              (AtkObject       *accessible,
224                                                      AtkObjectClass  *klass);
225 static AtkRelationSet* atk_object_real_ref_relation_set 
226                                                     (AtkObject       *accessible);
227 static void            atk_object_real_initialize   (AtkObject       *accessible,
228                                                      gpointer        data);
229 static void            atk_object_real_set_property (GObject         *object,
230                                                      guint            prop_id,
231                                                      const GValue    *value,
232                                                      GParamSpec      *pspec);
233 static void            atk_object_real_get_property (GObject         *object,
234                                                      guint            prop_id,
235                                                      GValue          *value,
236                                                      GParamSpec      *pspec);
237 static void            atk_object_finalize          (GObject         *object);
238 static const gchar*    atk_object_real_get_name     (AtkObject       *object);
239 static const gchar*    atk_object_real_get_description
240                                                    (AtkObject       *object);
241 static AtkObject*      atk_object_real_get_parent  (AtkObject       *object);
242 static AtkRole         atk_object_real_get_role    (AtkObject       *object);
243 static AtkLayer        atk_object_real_get_layer   (AtkObject       *object);
244 static AtkStateSet*    atk_object_real_ref_state_set
245                                                    (AtkObject       *object);
246 static void            atk_object_real_set_name    (AtkObject       *object,
247                                                     const gchar     *name);
248 static void            atk_object_real_set_description
249                                                    (AtkObject       *object,
250                                                     const gchar     *description);
251 static void            atk_object_real_set_parent  (AtkObject       *object,
252                                                     AtkObject       *parent);
253 static void            atk_object_real_set_role    (AtkObject       *object,
254                                                     AtkRole         role);
255 static void            atk_object_notify           (GObject         *obj,
256                                                     GParamSpec      *pspec);
257 static const gchar*    atk_object_real_get_object_locale
258                                                    (AtkObject       *object);
259
260 static guint atk_object_signals[LAST_SIGNAL] = { 0, };
261
262 static gpointer parent_class = NULL;
263
264 static const gchar* const atk_object_name_property_name = "accessible-name";
265 static const gchar* const atk_object_name_property_description = "accessible-description";
266 static const gchar* const atk_object_name_property_parent = "accessible-parent";
267 static const gchar* const atk_object_name_property_value = "accessible-value";
268 static const gchar* const atk_object_name_property_role = "accessible-role";
269 static const gchar* const atk_object_name_property_component_layer = "accessible-component-layer";
270 static const gchar* const atk_object_name_property_component_mdi_zorder = "accessible-component-mdi-zorder";
271 static const gchar* const atk_object_name_property_table_caption = "accessible-table-caption";
272 static const gchar* const atk_object_name_property_table_column_description = "accessible-table-column-description";
273 static const gchar* const atk_object_name_property_table_column_header = "accessible-table-column-header";
274 static const gchar* const atk_object_name_property_table_row_description = "accessible-table-row-description";
275 static const gchar* const atk_object_name_property_table_row_header = "accessible-table-row-header";
276 static const gchar* const atk_object_name_property_table_summary = "accessible-table-summary";
277 static const gchar* const atk_object_name_property_table_caption_object = "accessible-table-caption-object";
278 static const gchar* const atk_object_name_property_hypertext_num_links = "accessible-hypertext-nlinks";
279
280 #ifdef G_OS_WIN32
281
282 static HMODULE atk_dll;
283
284 BOOL WINAPI
285 DllMain (HINSTANCE hinstDLL,
286          DWORD     fdwReason,
287          LPVOID    lpvReserved)
288 {
289   switch (fdwReason)
290     {
291     case DLL_PROCESS_ATTACH:
292       atk_dll = (HMODULE) hinstDLL;
293       break;
294     }
295
296   return TRUE;
297 }
298
299 static const char *
300 get_atk_locale_dir (void)
301 {
302   static gchar *atk_localedir = NULL;
303
304   if (!atk_localedir)
305     {
306       const gchar *p;
307       gchar *root, *temp;
308       
309       /* ATK_LOCALEDIR might end in either /lib/locale or
310        * /share/locale. Scan for that slash.
311        */
312       p = ATK_LOCALEDIR + strlen (ATK_LOCALEDIR);
313       while (*--p != '/')
314         ;
315       while (*--p != '/')
316         ;
317
318       root = g_win32_get_package_installation_directory_of_module (atk_dll);
319       temp = g_build_filename (root, p, NULL);
320       g_free (root);
321
322       /* atk_localedir is passed to bindtextdomain() which isn't
323        * UTF-8-aware.
324        */
325       atk_localedir = g_win32_locale_filename_from_utf8 (temp);
326       g_free (temp);
327     }
328   return atk_localedir;
329 }
330
331 #undef ATK_LOCALEDIR
332
333 #define ATK_LOCALEDIR get_atk_locale_dir()
334
335 #endif
336
337 static void
338 gettext_initialization (void)
339 {
340 #ifdef ENABLE_NLS
341   static gboolean gettext_initialized = FALSE;
342
343   if (!gettext_initialized)
344     {
345       const char *dir = g_getenv ("ATK_ALT_LOCALEDIR");
346
347       gettext_initialized = TRUE;
348       if (dir == NULL)
349         dir = ATK_LOCALEDIR;
350
351       bindtextdomain (GETTEXT_PACKAGE, dir);
352 #ifdef HAVE_BIND_TEXTDOMAIN_CODESET
353       bind_textdomain_codeset (GETTEXT_PACKAGE, "UTF-8");
354 #endif
355     }
356 #endif
357 }
358
359 static void
360 compact_role_name (gchar *role_name)
361 {
362   gchar *p = role_name;
363
364   while (*p)
365     {
366       if (*p == '-')
367         *p = ' ';
368       p++;
369     }
370 }
371
372 static void
373 initialize_role_names ()
374 {
375   GTypeClass *enum_class;
376   GEnumValue *enum_value;
377   int i;
378   gchar *role_name = NULL;
379
380   if (role_names)
381     return;
382
383   role_names = g_ptr_array_new ();
384   enum_class = g_type_class_ref (ATK_TYPE_ROLE);
385   if (!G_IS_ENUM_CLASS(enum_class))
386     return;
387
388   for (i = 0; i < ATK_ROLE_LAST_DEFINED; i++)
389     {
390       enum_value = g_enum_get_value (G_ENUM_CLASS (enum_class), i);
391       role_name = g_strdup (enum_value->value_nick);
392       // We want the role names to be in the format "check button" and not "check-button"
393       compact_role_name (role_name);
394       g_ptr_array_add (role_names, role_name);
395     }
396
397   g_type_class_unref (enum_class);
398
399 }
400
401 GType
402 atk_object_get_type (void)
403 {
404   static GType type = 0;
405
406   if (!type)
407     {
408       static const GTypeInfo typeInfo =
409       {
410         sizeof (AtkObjectClass),
411         (GBaseInitFunc) NULL,
412         (GBaseFinalizeFunc) NULL,
413         (GClassInitFunc) atk_object_class_init,
414         (GClassFinalizeFunc) NULL,
415         NULL,
416         sizeof (AtkObject),
417         0,
418         (GInstanceInitFunc) atk_object_init,
419       } ;
420       type = g_type_register_static (G_TYPE_OBJECT, "AtkObject", &typeInfo, 0) ;
421     }
422   return type;
423 }
424
425 static void
426 atk_object_class_init (AtkObjectClass *klass)
427 {
428   GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
429
430   parent_class = g_type_class_peek_parent (klass);
431
432   gobject_class->set_property = atk_object_real_set_property;
433   gobject_class->get_property = atk_object_real_get_property;
434   gobject_class->finalize = atk_object_finalize;
435   gobject_class->notify = atk_object_notify;
436
437   klass->get_name = atk_object_real_get_name;
438   klass->get_description = atk_object_real_get_description;
439   klass->get_parent = atk_object_real_get_parent;
440   klass->get_n_children = NULL;
441   klass->ref_child = NULL;
442   klass->get_index_in_parent = NULL;
443   klass->ref_relation_set = atk_object_real_ref_relation_set;
444   klass->get_role = atk_object_real_get_role;
445   klass->get_layer = atk_object_real_get_layer;
446   klass->get_mdi_zorder = NULL;
447   klass->initialize = atk_object_real_initialize;
448   klass->ref_state_set = atk_object_real_ref_state_set;
449   klass->set_name = atk_object_real_set_name;
450   klass->set_description = atk_object_real_set_description;
451   klass->set_parent = atk_object_real_set_parent;
452   klass->set_role = atk_object_real_set_role;
453   klass->get_object_locale = atk_object_real_get_object_locale;
454
455   /*
456    * We do not define default signal handlers here
457    */
458   klass->children_changed = NULL;
459   klass->focus_event = NULL;
460   klass->property_change = NULL;
461   klass->visible_data_changed = NULL;
462   klass->active_descendant_changed = NULL;
463
464   gettext_initialization ();
465
466   g_object_class_install_property (gobject_class,
467                                    PROP_NAME,
468                                    g_param_spec_string (atk_object_name_property_name,
469                                                         _("Accessible Name"),
470                                                         _("Object instance\'s name formatted for assistive technology access"),
471                                                         NULL,
472                                                         G_PARAM_READWRITE));
473   g_object_class_install_property (gobject_class,
474                                    PROP_DESCRIPTION,
475                                    g_param_spec_string (atk_object_name_property_description,
476                                                         _("Accessible Description"),
477                                                         _("Description of an object, formatted for assistive technology access"),
478                                                         NULL,
479                                                         G_PARAM_READWRITE));
480   g_object_class_install_property (gobject_class,
481                                    PROP_PARENT,
482                                    g_param_spec_object (atk_object_name_property_parent,
483                                                         _("Accessible Parent"),
484                                                         _("Parent of the current accessible as returned by atk_object_get_parent()"),
485                                                         ATK_TYPE_OBJECT,
486                                                         G_PARAM_READWRITE));
487   g_object_class_install_property (gobject_class,
488                                    PROP_VALUE,
489                                    g_param_spec_double (atk_object_name_property_value,
490                                                         _("Accessible Value"),
491                                                         _("Is used to notify that the value has changed"),
492                                                         0.0,
493                                                         G_MAXDOUBLE,
494                                                         0.0,
495                                                         G_PARAM_READWRITE));
496   g_object_class_install_property (gobject_class,
497                                    PROP_ROLE,
498                                    g_param_spec_int    (atk_object_name_property_role,
499                                                         _("Accessible Role"),
500                                                         _("The accessible role of this object"),
501                                                         0,
502                                                         G_MAXINT,
503                                                         ATK_ROLE_UNKNOWN,
504                                                         G_PARAM_READWRITE));
505   g_object_class_install_property (gobject_class,
506                                    PROP_LAYER,
507                                    g_param_spec_int    (atk_object_name_property_component_layer,
508                                                         _("Accessible Layer"),
509                                                         _("The accessible layer of this object"),
510                                                         0,
511                                                         G_MAXINT,
512                                                         0,
513                                                         G_PARAM_READABLE));
514   g_object_class_install_property (gobject_class,
515                                    PROP_MDI_ZORDER,
516                                    g_param_spec_int    (atk_object_name_property_component_mdi_zorder,
517                                                         _("Accessible MDI Value"),
518                                                         _("The accessible MDI value of this object"),
519                                                         G_MININT,
520                                                         G_MAXINT,
521                                                         G_MININT,
522                                                         G_PARAM_READABLE));
523   g_object_class_install_property (gobject_class,
524                                    PROP_TABLE_CAPTION,
525                                    g_param_spec_string (atk_object_name_property_table_caption,
526                                                         _("Accessible Table Caption"),
527                                                         _("Is used to notify that the table caption has changed; this property should not be used. accessible-table-caption-object should be used instead"),
528                                                         NULL,
529                                                         G_PARAM_READWRITE));
530   g_object_class_install_property (gobject_class,
531                                    PROP_TABLE_COLUMN_HEADER,
532                                    g_param_spec_object (atk_object_name_property_table_column_header,
533                                                         _("Accessible Table Column Header"),
534                                                         _("Is used to notify that the table column header has changed"),
535                                                         ATK_TYPE_OBJECT,
536                                                         G_PARAM_READWRITE));
537   g_object_class_install_property (gobject_class,
538                                    PROP_TABLE_COLUMN_DESCRIPTION,
539                                    g_param_spec_string (atk_object_name_property_table_column_description,
540                                                         _("Accessible Table Column Description"),
541                                                         _("Is used to notify that the table column description has changed"),
542                                                         NULL,
543                                                         G_PARAM_READWRITE));
544   g_object_class_install_property (gobject_class,
545                                    PROP_TABLE_ROW_HEADER,
546                                    g_param_spec_object (atk_object_name_property_table_row_header,
547                                                         _("Accessible Table Row Header"),
548                                                         _("Is used to notify that the table row header has changed"),
549                                                         ATK_TYPE_OBJECT,
550                                                         G_PARAM_READWRITE));
551   g_object_class_install_property (gobject_class,
552                                    PROP_TABLE_ROW_DESCRIPTION,
553                                    g_param_spec_string (atk_object_name_property_table_row_description,
554                                                         _("Accessible Table Row Description"),
555                                                         _("Is used to notify that the table row description has changed"),
556                                                         NULL,
557                                                         G_PARAM_READWRITE));
558   g_object_class_install_property (gobject_class,
559                                    PROP_TABLE_SUMMARY,
560                                    g_param_spec_object (atk_object_name_property_table_summary,
561                                                         _("Accessible Table Summary"),
562                                                         _("Is used to notify that the table summary has changed"),
563                                                         ATK_TYPE_OBJECT,
564                                                         G_PARAM_READWRITE));
565   g_object_class_install_property (gobject_class,
566                                    PROP_TABLE_CAPTION_OBJECT,
567                                    g_param_spec_object (atk_object_name_property_table_caption_object,
568                                                         _("Accessible Table Caption Object"),
569                                                         _("Is used to notify that the table caption has changed"),
570                                                         ATK_TYPE_OBJECT,
571                                                         G_PARAM_READWRITE));
572   g_object_class_install_property (gobject_class,
573                                    PROP_HYPERTEXT_NUM_LINKS,
574                                    g_param_spec_int    (atk_object_name_property_hypertext_num_links,
575                                                         _("Number of Accessible Hypertext Links"),
576                                                         _("The number of links which the current AtkHypertext has"),
577                                                         0,
578                                                         G_MAXINT,
579                                                         0,
580                                                         G_PARAM_READABLE));
581
582   /**
583    * AtkObject::children-changed:
584    * @atkobject: the object which received the signal.
585    * @arg1: The index of the added or removed child. The value can be
586    * -1. This is used if the value is not known by the implementor
587    * when the child is added/removed or irrelevant.
588    * @arg2: A gpointer to the child AtkObject which was added or
589    * removed. If the child was removed, it is possible that it is not
590    * available for the implementor. In that case this pointer can be
591    * NULL.
592    *
593    * The signal "children-changed" is emitted when a child is added or
594    * removed form an object. It supports two details: "add" and
595    * "remove"
596    */
597   atk_object_signals[CHILDREN_CHANGED] =
598     g_signal_new ("children_changed",
599                   G_TYPE_FROM_CLASS (klass),
600                   G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
601                   G_STRUCT_OFFSET (AtkObjectClass, children_changed),
602                   NULL, NULL,
603                   g_cclosure_marshal_VOID__UINT_POINTER,
604                   G_TYPE_NONE,
605                   2, G_TYPE_UINT, G_TYPE_POINTER);
606
607   /**
608    * AtkObject::focus-event:
609    * @atkobject: the object which received the signal
610    * @arg1: a boolean value which indicates whether the object gained
611    * or lost focus.
612    *
613    * The signal "focus-event" is emitted when an object gained or lost
614    * focus.
615    *
616    * Deprecated: Since 2.9.4. Use #AtkObject::state-change signal instead.
617    */
618   atk_object_signals[FOCUS_EVENT] =
619     g_signal_new ("focus_event",
620                   G_TYPE_FROM_CLASS (klass),
621                   G_SIGNAL_RUN_LAST,
622                   G_STRUCT_OFFSET (AtkObjectClass, focus_event), 
623                   NULL, NULL,
624                   g_cclosure_marshal_VOID__BOOLEAN,
625                   G_TYPE_NONE,
626                   1, G_TYPE_BOOLEAN);
627   /**
628    * AtkObject::property-change:
629    * @atkobject: the object which received the signal.
630    * @arg1: an #AtkPropertyValues containing the new value of the
631    *   property which changed.
632    *
633    * The signal "property-change" is emitted when an object's property
634    * value changes. @arg1 contains an #AtkPropertyValues with the name
635    * and the new value of the property whose value has changed. Note
636    * that, as with GObject notify, getting this signal does not
637    * guarantee that the value of the property has actually changed; it
638    * may also be emitted when the setter of the property is called to
639    * reinstate the previous value.
640    *
641    * Toolkit implementor note: ATK implementors should use
642    * g_object_notify() to emit property-changed
643    * notifications. #AtkObject::property-changed is needed by the
644    * implementation of atk_add_global_event_listener() because GObject
645    * notify doesn't support emission hooks.
646    */
647   atk_object_signals[PROPERTY_CHANGE] =
648     g_signal_new ("property_change",
649                   G_TYPE_FROM_CLASS (klass),
650                   G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
651                   G_STRUCT_OFFSET (AtkObjectClass, property_change),
652                   (GSignalAccumulator) NULL, NULL,
653                   g_cclosure_marshal_VOID__POINTER,
654                   G_TYPE_NONE, 1,
655                   G_TYPE_POINTER);
656
657   /**
658    * AtkObject::state-change:
659    * @atkobject: the object which received the signal.
660    * @arg1: The name of the state which has changed
661    * @arg2: A boolean which indicates whether the state has been set or unset.
662    *
663    * The "state-change" signal is emitted when an object's state
664    * changes.  The detail value identifies the state type which has
665    * changed.
666    */
667   atk_object_signals[STATE_CHANGE] =
668     g_signal_new ("state_change",
669                   G_TYPE_FROM_CLASS (klass),
670                   G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
671                   G_STRUCT_OFFSET (AtkObjectClass, state_change),
672                   (GSignalAccumulator) NULL, NULL,
673                   atk_marshal_VOID__STRING_BOOLEAN,
674                   G_TYPE_NONE, 2,
675                   G_TYPE_STRING,
676                   G_TYPE_BOOLEAN);
677
678   /**
679    * AtkObject::visible-data-changed:
680    * @atkobject: the object which received the signal.
681    *
682    * The "visible-data-changed" signal is emitted when the visual
683    * appearance of the object changed.
684    */
685   atk_object_signals[VISIBLE_DATA_CHANGED] =
686     g_signal_new ("visible_data_changed",
687                   G_TYPE_FROM_CLASS (klass),
688                   G_SIGNAL_RUN_LAST,
689                   G_STRUCT_OFFSET (AtkObjectClass, visible_data_changed),
690                   (GSignalAccumulator) NULL, NULL,
691                   g_cclosure_marshal_VOID__VOID,
692                   G_TYPE_NONE, 0);
693
694   /**
695    * AtkObject::active-descendant-changed:
696    * @atkobject: the object which received the signal.
697    * @arg1: the newly focused object.
698    *
699    * The "active-descendant-changed" signal is emitted by an object
700    * which has the state ATK_STATE_MANAGES_DESCENDANTS when the focus
701    * object in the object changes. For instance, a table will emit the
702    * signal when the cell in the table which has focus changes.
703    */
704   atk_object_signals[ACTIVE_DESCENDANT_CHANGED] =
705     g_signal_new ("active_descendant_changed",
706                   G_TYPE_FROM_CLASS (klass),
707                   G_SIGNAL_RUN_LAST | G_SIGNAL_DETAILED,
708                   G_STRUCT_OFFSET (AtkObjectClass, active_descendant_changed),
709                   NULL, NULL,
710                   g_cclosure_marshal_VOID__POINTER,
711                   G_TYPE_NONE,
712                   1, G_TYPE_POINTER);
713 }
714
715 static void
716 atk_object_init  (AtkObject        *accessible,
717                   AtkObjectClass   *klass)
718 {
719   accessible->name = NULL;
720   accessible->description = NULL;
721   accessible->accessible_parent = NULL;
722   accessible->relation_set = atk_relation_set_new();
723   accessible->role = ATK_ROLE_UNKNOWN;
724 }
725
726 GType
727 atk_implementor_get_type (void)
728 {
729   static GType type = 0;
730
731   if (!type)
732     {
733       static const GTypeInfo typeInfo =
734       {
735         sizeof (AtkImplementorIface),
736         (GBaseInitFunc) NULL,
737         (GBaseFinalizeFunc) NULL,
738       } ;
739
740       type = g_type_register_static (G_TYPE_INTERFACE, "AtkImplementorIface", &typeInfo, 0) ;
741     }
742
743   return type;
744 }
745
746 /**
747  * atk_object_get_name:
748  * @accessible: an #AtkObject
749  *
750  * Gets the accessible name of the accessible.
751  *
752  * Returns: a character string representing the accessible name of the object.
753  **/
754 const gchar*
755 atk_object_get_name (AtkObject *accessible)
756 {
757   AtkObjectClass *klass;
758
759   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
760
761   klass = ATK_OBJECT_GET_CLASS (accessible);
762   if (klass->get_name)
763     return (klass->get_name) (accessible);
764   else
765     return NULL;
766 }
767
768 /**
769  * atk_object_get_description:
770  * @accessible: an #AtkObject
771  *
772  * Gets the accessible description of the accessible.
773  *
774  * Returns: a character string representing the accessible description
775  * of the accessible.
776  *
777  **/
778 const gchar*
779 atk_object_get_description (AtkObject *accessible)
780 {
781   AtkObjectClass *klass;
782
783   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
784
785   klass = ATK_OBJECT_GET_CLASS (accessible);
786   if (klass->get_description)
787     return (klass->get_description) (accessible);
788   else
789     return NULL;
790 }
791
792 /**
793  * atk_object_get_parent:
794  * @accessible: an #AtkObject
795  *
796  * Gets the accessible parent of the accessible. By default this is
797  * the one assigned with atk_object_set_parent(), but it is assumed
798  * that ATK implementors have ways to get the parent of the object
799  * without the need of assigning it manually with
800  * atk_object_set_parent(), and will return it with this method.
801  *
802  * If you are only interested on the parent assigned with
803  * atk_object_set_parent(), use atk_object_peek_parent().
804  *
805  * Returns: (transfer none): an #AtkObject representing the accessible
806  * parent of the accessible
807  **/
808 AtkObject*
809 atk_object_get_parent (AtkObject *accessible)
810 {
811   AtkObjectClass *klass;
812
813   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
814
815   klass = ATK_OBJECT_GET_CLASS (accessible);
816   if (klass->get_parent)
817     return (klass->get_parent) (accessible);
818   else
819     return NULL;
820 }
821
822 /**
823  * atk_object_peek_parent:
824  * @accessible: an #AtkObject
825  *
826  * Gets the accessible parent of the accessible, if it has been
827  * manually assigned with atk_object_set_parent. Otherwise, this
828  * function returns %NULL.
829  *
830  * This method is intended as an utility for ATK implementors, and not
831  * to be exposed to accessible tools. See atk_object_get_parent() for
832  * further reference.
833  *
834  * Returns: (transfer none): an #AtkObject representing the accessible
835  * parent of the accessible if assigned
836  **/
837 AtkObject*
838 atk_object_peek_parent (AtkObject *accessible)
839 {
840   return accessible->accessible_parent;
841 }
842
843 /**
844  * atk_object_get_n_accessible_children:
845  * @accessible: an #AtkObject
846  *
847  * Gets the number of accessible children of the accessible.
848  *
849  * Returns: an integer representing the number of accessible children
850  * of the accessible.
851  **/
852 gint
853 atk_object_get_n_accessible_children (AtkObject *accessible)
854 {
855   AtkObjectClass *klass;
856
857   g_return_val_if_fail (ATK_IS_OBJECT (accessible), 0);
858
859   klass = ATK_OBJECT_GET_CLASS (accessible);
860   if (klass->get_n_children)
861     return (klass->get_n_children) (accessible);
862   else
863     return 0;
864 }
865
866 /**
867  * atk_object_ref_accessible_child:
868  * @accessible: an #AtkObject
869  * @i: a gint representing the position of the child, starting from 0
870  *
871  * Gets a reference to the specified accessible child of the object.
872  * The accessible children are 0-based so the first accessible child is
873  * at index 0, the second at index 1 and so on.
874  *
875  * Returns: (transfer full): an #AtkObject representing the specified
876  * accessible child of the accessible.
877  **/
878 AtkObject*
879 atk_object_ref_accessible_child (AtkObject   *accessible,
880                                  gint        i)
881 {
882   AtkObjectClass *klass;
883
884   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
885
886   klass = ATK_OBJECT_GET_CLASS (accessible);
887   if (klass->ref_child)
888     return (klass->ref_child) (accessible, i);
889   else
890     return NULL;
891 }
892
893 /**
894  * atk_object_ref_relation_set:
895  * @accessible: an #AtkObject
896  *
897  * Gets the #AtkRelationSet associated with the object.
898  *
899  * Returns: (transfer full): an #AtkRelationSet representing the relation set
900  * of the object.
901  **/
902 AtkRelationSet*
903 atk_object_ref_relation_set (AtkObject *accessible)
904 {
905   AtkObjectClass *klass;
906
907   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
908
909   klass = ATK_OBJECT_GET_CLASS (accessible);
910   if (klass->ref_relation_set)
911     return (klass->ref_relation_set) (accessible);
912   else
913     return NULL;
914 }
915
916 /**
917  * atk_role_register:
918  * @name: a character string describing the new role.
919  *
920  * Registers the role specified by @name. @name must be a meaningful
921  * name. So it should not be empty, or consisting on whitespaces.
922  *
923  * Deprecated: Since 2.12. If your application/toolkit doesn't find a
924  * suitable role for a specific object defined at #AtkRole, please
925  * submit a bug in order to add a new role to the specification.
926  *
927  * Returns: an #AtkRole for the new role if added
928  * properly. ATK_ROLE_INVALID in case of error.
929  **/
930 AtkRole
931 atk_role_register (const gchar *name)
932 {
933   gboolean valid = FALSE;
934   gint i = 0;
935   glong length = g_utf8_strlen (name, -1);
936
937   for (i=0; i < length; i++) {
938     if (name[i]!=' ') {
939       valid = TRUE;
940       break;
941     }
942   }
943
944   if (!valid)
945     return ATK_ROLE_INVALID;
946
947   if (!role_names)
948     initialize_role_names ();
949
950   g_ptr_array_add (role_names, g_strdup (name));
951   return role_names->len - 1;
952 }
953
954 /**
955  * atk_object_get_role:
956  * @accessible: an #AtkObject
957  *
958  * Gets the role of the accessible.
959  *
960  * Returns: an #AtkRole which is the role of the accessible
961  **/
962 AtkRole
963 atk_object_get_role (AtkObject *accessible) 
964 {
965   AtkObjectClass *klass;
966
967   g_return_val_if_fail (ATK_IS_OBJECT (accessible), ATK_ROLE_UNKNOWN);
968
969   klass = ATK_OBJECT_GET_CLASS (accessible);
970   if (klass->get_role)
971     return (klass->get_role) (accessible);
972   else
973     return ATK_ROLE_UNKNOWN;
974 }
975
976 /**
977  * atk_object_get_layer:
978  * @accessible: an #AtkObject
979  *
980  * Gets the layer of the accessible.
981  *
982  * Deprecated: Use atk_component_get_layer instead.
983  *
984  * Returns: an #AtkLayer which is the layer of the accessible
985  **/
986 AtkLayer
987 atk_object_get_layer (AtkObject *accessible) 
988 {
989   AtkObjectClass *klass;
990
991   g_return_val_if_fail (ATK_IS_OBJECT (accessible), ATK_LAYER_INVALID);
992
993   klass = ATK_OBJECT_GET_CLASS (accessible);
994   if (klass->get_layer)
995     return (klass->get_layer) (accessible);
996   else
997     return ATK_LAYER_INVALID;
998 }
999
1000 /**
1001  * atk_object_get_mdi_zorder:
1002  * @accessible: an #AtkObject
1003  *
1004  * Gets the zorder of the accessible. The value G_MININT will be returned 
1005  * if the layer of the accessible is not ATK_LAYER_MDI.
1006  *
1007  * Deprecated: Use atk_component_get_mdi_zorder instead.
1008  *
1009  * Returns: a gint which is the zorder of the accessible, i.e. the depth at 
1010  * which the component is shown in relation to other components in the same 
1011  * container.
1012  *
1013  **/
1014 gint
1015 atk_object_get_mdi_zorder (AtkObject *accessible) 
1016 {
1017   AtkObjectClass *klass;
1018
1019   g_return_val_if_fail (ATK_IS_OBJECT (accessible), G_MININT);
1020
1021   klass = ATK_OBJECT_GET_CLASS (accessible);
1022   if (klass->get_mdi_zorder)
1023     return (klass->get_mdi_zorder) (accessible);
1024   else
1025     return G_MININT;
1026 }
1027
1028 /**
1029  * atk_object_ref_state_set:
1030  * @accessible: an #AtkObject
1031  *
1032  * Gets a reference to the state set of the accessible; the caller must
1033  * unreference it when it is no longer needed.
1034  *
1035  * Returns: (transfer full): a reference to an #AtkStateSet which is the state
1036  * set of the accessible
1037  **/
1038 AtkStateSet*
1039 atk_object_ref_state_set (AtkObject *accessible) 
1040 {
1041   AtkObjectClass *klass;
1042
1043   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
1044
1045   klass = ATK_OBJECT_GET_CLASS (accessible);
1046   if (klass->ref_state_set)
1047     return (klass->ref_state_set) (accessible);
1048   else
1049     return NULL;
1050 }
1051
1052 /**
1053  * atk_object_get_index_in_parent:
1054  * @accessible: an #AtkObject
1055  *
1056  * Gets the 0-based index of this accessible in its parent; returns -1 if the
1057  * accessible does not have an accessible parent.
1058  *
1059  * Returns: an integer which is the index of the accessible in its parent
1060  **/
1061 gint
1062 atk_object_get_index_in_parent (AtkObject *accessible)
1063 {
1064   AtkObjectClass *klass;
1065
1066   g_return_val_if_fail (ATK_OBJECT (accessible), -1);
1067
1068   klass = ATK_OBJECT_GET_CLASS (accessible);
1069   if (klass->get_index_in_parent)
1070     return (klass->get_index_in_parent) (accessible);
1071   else
1072     return -1;
1073 }
1074
1075 /**
1076  * atk_object_set_name:
1077  * @accessible: an #AtkObject
1078  * @name: a character string to be set as the accessible name
1079  *
1080  * Sets the accessible name of the accessible. You can't set the name
1081  * to NULL. This is reserved for the initial value. In this aspect
1082  * NULL is similar to ATK_ROLE_UNKNOWN. If you want to set the name to
1083  * a empty value you can use "".
1084  **/
1085 void
1086 atk_object_set_name (AtkObject    *accessible,
1087                      const gchar  *name)
1088 {
1089   AtkObjectClass *klass;
1090   gboolean notify = FALSE;
1091
1092   g_return_if_fail (ATK_IS_OBJECT (accessible));
1093   g_return_if_fail (name != NULL);
1094
1095   klass = ATK_OBJECT_GET_CLASS (accessible);
1096   if (klass->set_name)
1097     {
1098       /* Do not notify for initial name setting. See bug 665870 */
1099       notify = (accessible->name != NULL);
1100
1101       (klass->set_name) (accessible, name);
1102       if (notify)
1103         g_object_notify (G_OBJECT (accessible), atk_object_name_property_name);
1104     }
1105 }
1106
1107 /**
1108  * atk_object_set_description:
1109  * @accessible: an #AtkObject
1110  * @description: a character string to be set as the accessible description
1111  *
1112  * Sets the accessible description of the accessible. You can't set
1113  * the description to NULL. This is reserved for the initial value. In
1114  * this aspect NULL is similar to ATK_ROLE_UNKNOWN. If you want to set
1115  * the name to a empty value you can use "".
1116  **/
1117 void
1118 atk_object_set_description (AtkObject   *accessible,
1119                             const gchar *description)
1120 {
1121   AtkObjectClass *klass;
1122   gboolean notify = FALSE;
1123
1124   g_return_if_fail (ATK_IS_OBJECT (accessible));
1125   g_return_if_fail (description != NULL);
1126
1127   klass = ATK_OBJECT_GET_CLASS (accessible);
1128   if (klass->set_description)
1129     {
1130       /* Do not notify for initial name setting. See bug 665870 */
1131       notify = (accessible->description != NULL);
1132
1133       (klass->set_description) (accessible, description);
1134       if (notify)
1135         g_object_notify (G_OBJECT (accessible),
1136                          atk_object_name_property_description);
1137     }
1138 }
1139
1140 /**
1141  * atk_object_set_parent:
1142  * @accessible: an #AtkObject
1143  * @parent: an #AtkObject to be set as the accessible parent
1144  *
1145  * Sets the accessible parent of the accessible. @parent can be NULL.
1146  **/
1147 void
1148 atk_object_set_parent (AtkObject *accessible,
1149                        AtkObject *parent)
1150 {
1151   AtkObjectClass *klass;
1152
1153   g_return_if_fail (ATK_IS_OBJECT (accessible));
1154
1155   klass = ATK_OBJECT_GET_CLASS (accessible);
1156   if (klass->set_parent)
1157     {
1158       (klass->set_parent) (accessible, parent);
1159       g_object_notify (G_OBJECT (accessible), atk_object_name_property_parent);
1160     }
1161 }
1162
1163 /**
1164  * atk_object_set_role:
1165  * @accessible: an #AtkObject
1166  * @role: an #AtkRole to be set as the role
1167  *
1168  * Sets the role of the accessible.
1169  **/
1170 void
1171 atk_object_set_role (AtkObject *accessible, 
1172                      AtkRole   role)
1173 {
1174   AtkObjectClass *klass;
1175   AtkRole old_role;
1176
1177   g_return_if_fail (ATK_IS_OBJECT (accessible));
1178
1179   klass = ATK_OBJECT_GET_CLASS (accessible);
1180   if (klass->set_role)
1181     {
1182       old_role = atk_object_get_role (accessible);
1183       if (old_role != role)
1184         {
1185           (klass->set_role) (accessible, role);
1186           if (old_role != ATK_ROLE_UNKNOWN)
1187           /* Do not notify for initial role setting */
1188             g_object_notify (G_OBJECT (accessible), atk_object_name_property_role);
1189         }
1190     }
1191 }
1192
1193 /**
1194  * atk_object_connect_property_change_handler:
1195  * @accessible: an #AtkObject
1196  * @handler: a function to be called when a property changes its value
1197  *
1198  * Deprecated: Since 2.12. Connect directly to property-change or
1199  * notify signals.
1200  *
1201  * Returns: a #guint which is the handler id used in 
1202  * atk_object_remove_property_change_handler()
1203  **/
1204 guint
1205 atk_object_connect_property_change_handler (AtkObject *accessible,
1206                                             AtkPropertyChangeHandler *handler)
1207 {
1208   AtkObjectClass *klass;
1209
1210   g_return_val_if_fail (ATK_IS_OBJECT (accessible), 0);
1211   g_return_val_if_fail ((handler != NULL), 0);
1212
1213   klass = ATK_OBJECT_GET_CLASS (accessible);
1214   if (klass->connect_property_change_handler)
1215     return (klass->connect_property_change_handler) (accessible, handler);
1216   else
1217     return 0;
1218 }
1219
1220 /**
1221  * atk_object_remove_property_change_handler:
1222  * @accessible: an #AtkObject
1223  * @handler_id: a guint which identifies the handler to be removed.
1224  *
1225  * Deprecated: Since 2.12.
1226  *
1227  * Removes a property change handler.
1228  **/
1229 void
1230 atk_object_remove_property_change_handler  (AtkObject *accessible,
1231                                             guint      handler_id)
1232 {
1233   AtkObjectClass *klass;
1234
1235   g_return_if_fail (ATK_IS_OBJECT (accessible));
1236
1237   klass = ATK_OBJECT_GET_CLASS (accessible);
1238   if (klass->remove_property_change_handler)
1239     (klass->remove_property_change_handler) (accessible, handler_id);
1240 }
1241
1242 /**
1243  * atk_object_notify_state_change:
1244  * @accessible: an #AtkObject
1245  * @state: an #AtkState whose state is changed
1246  * @value: a gboolean which indicates whether the state is being set on or off
1247  * 
1248  * Emits a state-change signal for the specified state. 
1249  **/
1250 void
1251 atk_object_notify_state_change (AtkObject *accessible,
1252                                 AtkState  state,
1253                                 gboolean  value)
1254 {
1255   const gchar* name;
1256
1257   g_return_if_fail (ATK_IS_OBJECT (accessible));
1258
1259   name = atk_state_type_get_name (state);
1260   g_signal_emit (accessible, atk_object_signals[STATE_CHANGE],
1261                  g_quark_from_string (name),
1262                  name, value, NULL);
1263 }
1264
1265 /**
1266  * atk_implementor_ref_accessible:
1267  * @implementor: The #GObject instance which should implement #AtkImplementorIface
1268  * if a non-null return value is required.
1269  * 
1270  * Gets a reference to an object's #AtkObject implementation, if
1271  * the object implements #AtkObjectIface
1272  *
1273  * Returns: (transfer full): a reference to an object's #AtkObject
1274  * implementation
1275  */
1276 AtkObject *
1277 atk_implementor_ref_accessible (AtkImplementor *implementor)
1278 {
1279   AtkImplementorIface *iface;
1280   AtkObject           *accessible = NULL;
1281
1282   g_return_val_if_fail (ATK_IS_IMPLEMENTOR (implementor), NULL);
1283
1284   iface = ATK_IMPLEMENTOR_GET_IFACE (implementor);
1285
1286   if (iface != NULL) 
1287     accessible =  iface->ref_accessible (implementor);
1288
1289   g_return_val_if_fail ((accessible != NULL), NULL);
1290
1291   return accessible;
1292 }
1293
1294         
1295 /**
1296  * atk_object_get_attributes:
1297  * @accessible: An #AtkObject.
1298  *
1299  * Get a list of properties applied to this object as a whole, as an #AtkAttributeSet consisting of 
1300  * name-value pairs. As such these attributes may be considered weakly-typed properties or annotations, 
1301  * as distinct from strongly-typed object data available via other get/set methods.
1302  * Not all objects have explicit "name-value pair" #AtkAttributeSet properties.
1303  *
1304  * Since: 1.12
1305  *
1306  * Returns: (transfer full): an #AtkAttributeSet consisting of all
1307  * explicit properties/annotations applied to the object, or an empty
1308  * set if the object has no name-value pair attributes assigned to
1309  * it. This #atkattributeset should be freed by a call to
1310  * atk_attribute_set_free().
1311  */
1312 AtkAttributeSet *
1313 atk_object_get_attributes (AtkObject                  *accessible)
1314 {
1315   AtkObjectClass *klass;
1316
1317   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
1318
1319   klass = ATK_OBJECT_GET_CLASS (accessible);
1320   if (klass->get_attributes)
1321     return (klass->get_attributes) (accessible); 
1322   else 
1323     return NULL;
1324         
1325 }
1326
1327 static AtkRelationSet*
1328 atk_object_real_ref_relation_set (AtkObject *accessible)
1329 {
1330   g_return_val_if_fail (accessible->relation_set, NULL);
1331   g_object_ref (accessible->relation_set); 
1332
1333   return accessible->relation_set;
1334 }
1335
1336 static void
1337 atk_object_real_set_property (GObject      *object,
1338                               guint         prop_id,
1339                               const GValue *value,
1340                               GParamSpec   *pspec)
1341 {
1342   AtkObject *accessible;
1343
1344   accessible = ATK_OBJECT (object);
1345
1346   switch (prop_id)
1347     {
1348     case PROP_NAME:
1349       atk_object_set_name (accessible, g_value_get_string (value));
1350       break;
1351     case PROP_DESCRIPTION:
1352       atk_object_set_description (accessible, g_value_get_string (value));
1353       break;
1354     case PROP_ROLE:
1355       atk_object_set_role (accessible, g_value_get_int (value));
1356       break;
1357     case PROP_PARENT:
1358       atk_object_set_parent (accessible, g_value_get_object (value));
1359       break;
1360     case PROP_VALUE:
1361       if (ATK_IS_VALUE (accessible))
1362         atk_value_set_current_value (ATK_VALUE (accessible), value);
1363       break;
1364     case PROP_TABLE_SUMMARY:
1365       if (ATK_IS_TABLE (accessible))
1366         atk_table_set_summary (ATK_TABLE (accessible), g_value_get_object (value));
1367       break;
1368     case PROP_TABLE_CAPTION_OBJECT:
1369       if (ATK_IS_TABLE (accessible))
1370         atk_table_set_caption (ATK_TABLE (accessible), g_value_get_object (value));
1371       break;
1372     default:
1373       break;
1374     }
1375 }
1376
1377 static void
1378 atk_object_real_get_property (GObject      *object,
1379                               guint         prop_id,
1380                               GValue       *value,
1381                               GParamSpec   *pspec)
1382 {
1383   AtkObject *accessible;
1384
1385   accessible = ATK_OBJECT (object);
1386
1387   switch (prop_id)
1388     {
1389     case PROP_NAME:
1390       g_value_set_string (value, atk_object_get_name (accessible));
1391       break;
1392     case PROP_DESCRIPTION:
1393       g_value_set_string (value, atk_object_get_description (accessible));
1394       break;
1395     case PROP_ROLE:
1396       g_value_set_int (value, atk_object_get_role (accessible));
1397       break;
1398     case PROP_LAYER:
1399       if (ATK_IS_COMPONENT (accessible))
1400         g_value_set_int (value, atk_component_get_layer (ATK_COMPONENT (accessible)));
1401       break;
1402     case PROP_MDI_ZORDER:
1403       if (ATK_IS_COMPONENT (accessible))
1404         g_value_set_int (value, atk_component_get_mdi_zorder (ATK_COMPONENT (accessible)));
1405       break;
1406     case PROP_PARENT:
1407       g_value_set_object (value, atk_object_get_parent (accessible));
1408       break;
1409     case PROP_VALUE:
1410       if (ATK_IS_VALUE (accessible))
1411         atk_value_get_current_value (ATK_VALUE (accessible), value);
1412       break;
1413     case PROP_TABLE_SUMMARY:
1414       if (ATK_IS_TABLE (accessible))
1415         g_value_set_object (value, atk_table_get_summary (ATK_TABLE (accessible)));
1416       break;
1417     case PROP_TABLE_CAPTION_OBJECT:
1418       if (ATK_IS_TABLE (accessible))
1419         g_value_set_object (value, atk_table_get_caption (ATK_TABLE (accessible)));
1420       break;
1421     case PROP_HYPERTEXT_NUM_LINKS:
1422       if (ATK_IS_HYPERTEXT (accessible))
1423         g_value_set_int (value, atk_hypertext_get_n_links (ATK_HYPERTEXT (accessible)));
1424       break;
1425     default:
1426       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
1427       break;
1428     }
1429 }
1430
1431 static void
1432 atk_object_finalize (GObject *object)
1433 {
1434   AtkObject        *accessible;
1435
1436   g_return_if_fail (ATK_IS_OBJECT (object));
1437
1438   accessible = ATK_OBJECT (object);
1439
1440   g_free (accessible->name);
1441   g_free (accessible->description);
1442
1443   /*
1444    * Free memory allocated for relation set if it have been allocated.
1445    */
1446   if (accessible->relation_set)
1447     g_object_unref (accessible->relation_set);
1448
1449   if (accessible->accessible_parent)
1450     g_object_unref (accessible->accessible_parent);
1451
1452   G_OBJECT_CLASS (parent_class)->finalize (object);
1453 }
1454
1455 static const gchar*
1456 atk_object_real_get_name (AtkObject *object)
1457 {
1458   return object->name;
1459 }
1460
1461 static const gchar*
1462 atk_object_real_get_description (AtkObject *object)
1463 {
1464   return object->description;
1465 }
1466
1467 static AtkObject*
1468 atk_object_real_get_parent (AtkObject       *object)
1469 {
1470   return atk_object_peek_parent (object);
1471 }
1472
1473 static AtkRole
1474 atk_object_real_get_role (AtkObject       *object)
1475 {
1476   return object->role;
1477 }
1478
1479 static AtkLayer
1480 atk_object_real_get_layer (AtkObject       *object)
1481 {
1482   return object->layer;
1483 }
1484
1485 static AtkStateSet*
1486 atk_object_real_ref_state_set (AtkObject *accessible) 
1487 {
1488   AtkStateSet *state_set;
1489   AtkObject *focus_object;
1490
1491   state_set = atk_state_set_new ();
1492
1493   focus_object = atk_get_focus_object ();
1494   if (focus_object == accessible)
1495     atk_state_set_add_state (state_set, ATK_STATE_FOCUSED);
1496
1497   return state_set; 
1498 }
1499
1500 static void
1501 atk_object_real_set_name (AtkObject       *object,
1502                           const gchar     *name)
1503 {
1504   g_free (object->name);
1505   object->name = g_strdup (name);
1506 }
1507
1508 static void
1509 atk_object_real_set_description (AtkObject       *object,
1510                                  const gchar     *description)
1511 {
1512   g_free (object->description);
1513   object->description = g_strdup (description);
1514 }
1515
1516 static void
1517 atk_object_real_set_parent (AtkObject       *object,
1518                             AtkObject       *parent)
1519 {
1520   if (object->accessible_parent)
1521     g_object_unref (object->accessible_parent);
1522
1523   object->accessible_parent = parent;
1524   if (object->accessible_parent)
1525     g_object_ref (object->accessible_parent);
1526 }
1527
1528 static void
1529 atk_object_real_set_role (AtkObject *object,
1530                           AtkRole   role)
1531 {
1532   object->role = role;
1533 }
1534
1535 /**
1536  * atk_object_initialize:
1537  * @accessible: a #AtkObject
1538  * @data: a #gpointer which identifies the object for which the AtkObject was created.
1539  *
1540  * This function is called when implementing subclasses of #AtkObject.
1541  * It does initialization required for the new object. It is intended
1542  * that this function should called only in the ..._new() functions used
1543  * to create an instance of a subclass of #AtkObject
1544  **/
1545 void
1546 atk_object_initialize (AtkObject  *accessible,
1547                        gpointer   data)
1548 {
1549   AtkObjectClass *klass;
1550
1551   g_return_if_fail (ATK_IS_OBJECT (accessible));
1552
1553   klass = ATK_OBJECT_GET_CLASS (accessible);
1554   if (klass->initialize)
1555     klass->initialize (accessible, data);
1556 }
1557
1558 /*
1559  * This function is a signal handler for notify signal which gets emitted
1560  * when a property changes value.
1561  *
1562  * It constructs an AtkPropertyValues structure and emits a "property_changed"
1563  * signal which causes the user specified AtkPropertyChangeHandler
1564  * to be called.
1565  */
1566 static void
1567 atk_object_notify (GObject     *obj,
1568                    GParamSpec  *pspec)
1569 {
1570   AtkPropertyValues values = { NULL, };
1571
1572   g_value_init (&values.new_value, pspec->value_type);
1573   g_object_get_property (obj, pspec->name, &values.new_value);
1574   values.property_name = pspec->name;
1575   g_signal_emit (obj, atk_object_signals[PROPERTY_CHANGE],
1576                  g_quark_from_string (pspec->name),
1577                  &values, NULL);
1578   g_value_unset (&values.new_value);
1579 }
1580
1581 /**
1582  * atk_role_get_name:
1583  * @role: The #AtkRole whose name is required
1584  *
1585  * Gets the description string describing the #AtkRole @role.
1586  *
1587  * Returns: the string describing the AtkRole
1588  */
1589 const gchar*
1590 atk_role_get_name (AtkRole role)
1591 {
1592   g_return_val_if_fail (role >= 0, NULL);
1593
1594   if (!role_names)
1595     initialize_role_names ();
1596
1597   if (role < role_names->len)
1598     return g_ptr_array_index (role_names, role);
1599
1600   return NULL;
1601 }
1602
1603 /**
1604  * atk_role_get_localized_name:
1605  * @role: The #AtkRole whose localized name is required
1606  *
1607  * Gets the localized description string describing the #AtkRole @role.
1608  *
1609  * Returns: the localized string describing the AtkRole
1610  **/
1611 const gchar*
1612 atk_role_get_localized_name (AtkRole role)
1613 {
1614   gettext_initialization ();
1615
1616   return dgettext (GETTEXT_PACKAGE, atk_role_get_name (role));
1617 }
1618
1619 static const gchar*
1620 atk_object_real_get_object_locale (AtkObject *object)
1621 {
1622   return setlocale (LC_MESSAGES, NULL);
1623 }
1624
1625 /**
1626  * atk_object_get_object_locale:
1627  * @accessible: an #AtkObject
1628  *
1629  * Gets a UTF-8 string indicating the POSIX-style LC_MESSAGES locale
1630  * of @accessible.
1631  *
1632  * Since: 2.8
1633  *
1634  * Returns: a UTF-8 string indicating the POSIX-style LC_MESSAGES
1635  *          locale of @accessible.
1636  **/
1637 const gchar*
1638 atk_object_get_object_locale (AtkObject *accessible)
1639 {
1640   AtkObjectClass *klass;
1641
1642   g_return_val_if_fail (ATK_IS_OBJECT (accessible), NULL);
1643
1644   klass = ATK_OBJECT_GET_CLASS (accessible);
1645   if (klass->get_object_locale)
1646     return (klass->get_object_locale) (accessible);
1647   else
1648     return NULL;
1649 }
1650
1651
1652 /**
1653  * atk_role_for_name:
1654  * @name: a string which is the (non-localized) name of an ATK role.
1655  *
1656  * Get the #AtkRole type corresponding to a rolew name.
1657  *
1658  * Returns: the #AtkRole enumerated type corresponding to the specified name,
1659  *          or #ATK_ROLE_INVALID if no matching role is found.
1660  **/
1661 AtkRole
1662 atk_role_for_name (const gchar *name)
1663 {
1664   AtkRole role = ATK_ROLE_INVALID;
1665   gint i;
1666
1667   g_return_val_if_fail (name, ATK_ROLE_INVALID);
1668
1669   if (!role_names)
1670     initialize_role_names ();
1671
1672   for (i = 0; i < role_names->len; i++)
1673     {
1674       gchar *role_name = (gchar *)g_ptr_array_index (role_names, i);
1675
1676       g_return_val_if_fail (role_name, ATK_ROLE_INVALID);
1677
1678       if (strcmp (name, role_name) == 0)
1679         {
1680           role = i;
1681           break;
1682         }
1683     }
1684
1685   return role;
1686 }
1687
1688 /**
1689  * atk_object_add_relationship:
1690  * @object: The #AtkObject to which an AtkRelation is to be added. 
1691  * @relationship: The #AtkRelationType of the relation
1692  * @target: The #AtkObject which is to be the target of the relation.
1693  *
1694  * Adds a relationship of the specified type with the specified target.
1695  *
1696  * Returns: TRUE if the relationship is added.
1697  **/
1698 gboolean
1699 atk_object_add_relationship (AtkObject       *object,
1700                              AtkRelationType relationship,
1701                              AtkObject       *target)
1702 {
1703   AtkObject *array[1];
1704   AtkRelation *relation;
1705
1706   g_return_val_if_fail (ATK_IS_OBJECT (object), FALSE);
1707   g_return_val_if_fail (ATK_IS_OBJECT (target), FALSE);
1708
1709   if (atk_relation_set_contains_target (object->relation_set,
1710                                         relationship, target))
1711     return FALSE;
1712
1713   array[0] = target;
1714   relation = atk_relation_new (array, 1, relationship);
1715   atk_relation_set_add (object->relation_set, relation);
1716   g_object_unref (relation);
1717
1718   return TRUE;
1719 }
1720
1721 /**
1722  * atk_object_remove_relationship:
1723  * @object: The #AtkObject from which an AtkRelation is to be removed. 
1724  * @relationship: The #AtkRelationType of the relation
1725  * @target: The #AtkObject which is the target of the relation to be removed.
1726  *
1727  * Removes a relationship of the specified type with the specified target.
1728  *
1729  * Returns: TRUE if the relationship is removed.
1730  **/
1731 gboolean
1732 atk_object_remove_relationship (AtkObject       *object,
1733                                 AtkRelationType relationship,
1734                                 AtkObject       *target)
1735 {
1736   gboolean ret = FALSE;
1737   AtkRelation *relation;
1738   GPtrArray *array;
1739
1740   g_return_val_if_fail (ATK_IS_OBJECT (object), FALSE);
1741   g_return_val_if_fail (ATK_IS_OBJECT (target), FALSE);
1742
1743   relation = atk_relation_set_get_relation_by_type (object->relation_set, relationship);
1744
1745   if (relation)
1746     {
1747       ret = atk_relation_remove_target (relation, target);
1748       array = atk_relation_get_target (relation);
1749       if (!array || array->len == 0)
1750         atk_relation_set_remove (object->relation_set, relation);
1751     }
1752   return ret;
1753 }
1754
1755 static void
1756 atk_object_real_initialize (AtkObject *accessible,
1757                             gpointer  data)
1758 {
1759   return;
1760 }