LCOV - code coverage report
Current view: top level - vcl/unx/gtk/a11y - atkwrapper.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 0 310 0.0 %
Date: 2012-08-25 Functions: 0 22 0.0 %
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: 0 0 -

           Branch data     Line data    Source code
       1                 :            : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2                 :            : /*************************************************************************
       3                 :            :  *
       4                 :            :  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       5                 :            :  *
       6                 :            :  * Copyright 2000, 2010 Oracle and/or its affiliates.
       7                 :            :  *
       8                 :            :  * OpenOffice.org - a multi-platform office productivity suite
       9                 :            :  *
      10                 :            :  * This file is part of OpenOffice.org.
      11                 :            :  *
      12                 :            :  * OpenOffice.org is free software: you can redistribute it and/or modify
      13                 :            :  * it under the terms of the GNU Lesser General Public License version 3
      14                 :            :  * only, as published by the Free Software Foundation.
      15                 :            :  *
      16                 :            :  * OpenOffice.org is distributed in the hope that it will be useful,
      17                 :            :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      18                 :            :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      19                 :            :  * GNU Lesser General Public License version 3 for more details
      20                 :            :  * (a copy is included in the LICENSE file that accompanied this code).
      21                 :            :  *
      22                 :            :  * You should have received a copy of the GNU Lesser General Public License
      23                 :            :  * version 3 along with OpenOffice.org.  If not, see
      24                 :            :  * <http://www.openoffice.org/license.html>
      25                 :            :  * for a copy of the LGPLv3 License.
      26                 :            :  *
      27                 :            :  ************************************************************************/
      28                 :            : 
      29                 :            : 
      30                 :            : #include <com/sun/star/uno/Any.hxx>
      31                 :            : #include <com/sun/star/uno/Type.hxx>
      32                 :            : #include <com/sun/star/uno/Sequence.hxx>
      33                 :            : #include <com/sun/star/accessibility/AccessibleRole.hpp>
      34                 :            : #include <com/sun/star/accessibility/AccessibleRelation.hpp>
      35                 :            : #include <com/sun/star/accessibility/AccessibleRelationType.hpp>
      36                 :            : #include <com/sun/star/accessibility/AccessibleStateType.hpp>
      37                 :            : #include <com/sun/star/accessibility/XAccessible.hpp>
      38                 :            : #include <com/sun/star/accessibility/XAccessibleText.hpp>
      39                 :            : #include <com/sun/star/accessibility/XAccessibleTextMarkup.hpp>
      40                 :            : #include <com/sun/star/accessibility/XAccessibleTextAttributes.hpp>
      41                 :            : #include <com/sun/star/accessibility/XAccessibleValue.hpp>
      42                 :            : #include <com/sun/star/accessibility/XAccessibleAction.hpp>
      43                 :            : #include <com/sun/star/accessibility/XAccessibleContext.hpp>
      44                 :            : #include <com/sun/star/accessibility/XAccessibleComponent.hpp>
      45                 :            : #include <com/sun/star/accessibility/XAccessibleEventBroadcaster.hpp>
      46                 :            : #include <com/sun/star/accessibility/XAccessibleMultiLineText.hpp>
      47                 :            : #include <com/sun/star/accessibility/XAccessibleStateSet.hpp>
      48                 :            : #include <com/sun/star/accessibility/XAccessibleRelationSet.hpp>
      49                 :            : #include <com/sun/star/accessibility/XAccessibleTable.hpp>
      50                 :            : #include <com/sun/star/accessibility/XAccessibleEditableText.hpp>
      51                 :            : #include <com/sun/star/accessibility/XAccessibleImage.hpp>
      52                 :            : #include <com/sun/star/accessibility/XAccessibleHyperlink.hpp>
      53                 :            : #include <com/sun/star/accessibility/XAccessibleHypertext.hpp>
      54                 :            : #include <com/sun/star/accessibility/XAccessibleSelection.hpp>
      55                 :            : #include <com/sun/star/awt/XExtendedToolkit.hpp>
      56                 :            : #include <com/sun/star/awt/XTopWindow.hpp>
      57                 :            : #include <com/sun/star/awt/XTopWindowListener.hpp>
      58                 :            : #include <com/sun/star/awt/XWindow.hpp>
      59                 :            : #include <com/sun/star/lang/XComponent.hpp>
      60                 :            : #include <com/sun/star/lang/XServiceInfo.hpp>
      61                 :            : #include <com/sun/star/lang/XInitialization.hpp>
      62                 :            : #include <com/sun/star/lang/XMultiServiceFactory.hpp>
      63                 :            : #include <com/sun/star/lang/XSingleServiceFactory.hpp>
      64                 :            : #include <com/sun/star/beans/Property.hpp>
      65                 :            : 
      66                 :            : #include <rtl/ref.hxx>
      67                 :            : #include <cppuhelper/factory.hxx>
      68                 :            : #include <cppuhelper/queryinterface.hxx>
      69                 :            : 
      70                 :            : #include "atkwrapper.hxx"
      71                 :            : #include "atkregistry.hxx"
      72                 :            : #include "atklistener.hxx"
      73                 :            : 
      74                 :            : #ifdef ENABLE_TRACING
      75                 :            : #include <stdio.h>
      76                 :            : #endif
      77                 :            : 
      78                 :            : #include <string.h>
      79                 :            : 
      80                 :            : using namespace ::com::sun::star;
      81                 :            : 
      82                 :            : static GObjectClass *parent_class = NULL;
      83                 :            : 
      84                 :          0 : static AtkRelationType mapRelationType( sal_Int16 nRelation )
      85                 :            : {
      86                 :          0 :     AtkRelationType type = ATK_RELATION_NULL;
      87                 :            : 
      88                 :          0 :     switch( nRelation )
      89                 :            :     {
      90                 :            :         case accessibility::AccessibleRelationType::CONTENT_FLOWS_FROM:
      91                 :          0 :             type = ATK_RELATION_FLOWS_FROM;
      92                 :          0 :             break;
      93                 :            : 
      94                 :            :         case accessibility::AccessibleRelationType::CONTENT_FLOWS_TO:
      95                 :          0 :             type = ATK_RELATION_FLOWS_TO;
      96                 :          0 :             break;
      97                 :            : 
      98                 :            :         case accessibility::AccessibleRelationType::CONTROLLED_BY:
      99                 :          0 :             type = ATK_RELATION_CONTROLLED_BY;
     100                 :          0 :             break;
     101                 :            : 
     102                 :            :         case accessibility::AccessibleRelationType::CONTROLLER_FOR:
     103                 :          0 :             type = ATK_RELATION_CONTROLLER_FOR;
     104                 :          0 :             break;
     105                 :            : 
     106                 :            :         case accessibility::AccessibleRelationType::LABEL_FOR:
     107                 :          0 :             type = ATK_RELATION_LABEL_FOR;
     108                 :          0 :             break;
     109                 :            : 
     110                 :            :         case accessibility::AccessibleRelationType::LABELED_BY:
     111                 :          0 :             type = ATK_RELATION_LABELLED_BY;
     112                 :          0 :             break;
     113                 :            : 
     114                 :            :         case accessibility::AccessibleRelationType::MEMBER_OF:
     115                 :          0 :             type = ATK_RELATION_MEMBER_OF;
     116                 :          0 :             break;
     117                 :            : 
     118                 :            :         case accessibility::AccessibleRelationType::SUB_WINDOW_OF:
     119                 :          0 :             type = ATK_RELATION_SUBWINDOW_OF;
     120                 :          0 :             break;
     121                 :            : 
     122                 :            :         case accessibility::AccessibleRelationType::NODE_CHILD_OF:
     123                 :          0 :             type = ATK_RELATION_NODE_CHILD_OF;
     124                 :          0 :             break;
     125                 :            : 
     126                 :            :         default:
     127                 :          0 :             break;
     128                 :            :     }
     129                 :            : 
     130                 :          0 :     return type;
     131                 :            : }
     132                 :            : 
     133                 :            : 
     134                 :          0 : AtkStateType mapAtkState( sal_Int16 nState )
     135                 :            : {
     136                 :          0 :     AtkStateType type = ATK_STATE_INVALID;
     137                 :            : 
     138                 :            :     // A perfect / complete mapping ...
     139                 :          0 :     switch( nState )
     140                 :            :     {
     141                 :            : #define MAP_DIRECT( a ) \
     142                 :            :         case accessibility::AccessibleStateType::a: \
     143                 :            :             type = ATK_STATE_##a; break
     144                 :            : 
     145                 :          0 :         MAP_DIRECT( INVALID );
     146                 :          0 :         MAP_DIRECT( ACTIVE );
     147                 :          0 :         MAP_DIRECT( ARMED );
     148                 :          0 :         MAP_DIRECT( BUSY );
     149                 :          0 :         MAP_DIRECT( CHECKED );
     150                 :          0 :         MAP_DIRECT( EDITABLE );
     151                 :          0 :         MAP_DIRECT( ENABLED );
     152                 :          0 :         MAP_DIRECT( EXPANDABLE );
     153                 :          0 :         MAP_DIRECT( EXPANDED );
     154                 :          0 :         MAP_DIRECT( FOCUSABLE );
     155                 :          0 :         MAP_DIRECT( FOCUSED );
     156                 :          0 :         MAP_DIRECT( HORIZONTAL );
     157                 :          0 :         MAP_DIRECT( ICONIFIED );
     158                 :          0 :         MAP_DIRECT( INDETERMINATE );
     159                 :          0 :         MAP_DIRECT( MANAGES_DESCENDANTS );
     160                 :          0 :         MAP_DIRECT( MODAL );
     161                 :          0 :         MAP_DIRECT( MULTI_LINE );
     162                 :          0 :         MAP_DIRECT( OPAQUE );
     163                 :          0 :         MAP_DIRECT( PRESSED );
     164                 :          0 :         MAP_DIRECT( RESIZABLE );
     165                 :          0 :         MAP_DIRECT( SELECTABLE );
     166                 :          0 :         MAP_DIRECT( SELECTED );
     167                 :          0 :         MAP_DIRECT( SENSITIVE );
     168                 :          0 :         MAP_DIRECT( SHOWING );
     169                 :          0 :         MAP_DIRECT( SINGLE_LINE );
     170                 :          0 :         MAP_DIRECT( STALE );
     171                 :          0 :         MAP_DIRECT( TRANSIENT );
     172                 :          0 :         MAP_DIRECT( VERTICAL );
     173                 :          0 :         MAP_DIRECT( VISIBLE );
     174                 :            :         // a spelling error ...
     175                 :            :         case accessibility::AccessibleStateType::DEFUNC:
     176                 :          0 :             type = ATK_STATE_DEFUNCT; break;
     177                 :            :         case accessibility::AccessibleStateType::MULTI_SELECTABLE:
     178                 :          0 :             type = ATK_STATE_MULTISELECTABLE; break;
     179                 :            :     default:
     180                 :          0 :         break;
     181                 :            :     }
     182                 :            : 
     183                 :          0 :     return type;
     184                 :            : }
     185                 :            : 
     186                 :          0 : static inline AtkRole registerRole( const gchar * name )
     187                 :            : {
     188                 :          0 :     AtkRole ret = atk_role_for_name( name );
     189                 :          0 :     if( ATK_ROLE_INVALID == ret )
     190                 :          0 :         ret = atk_role_register( name );
     191                 :            : 
     192                 :          0 :     return ret;
     193                 :            : }
     194                 :            : 
     195                 :          0 : static AtkRole mapToAtkRole( sal_Int16 nRole )
     196                 :            : {
     197                 :          0 :     AtkRole role = ATK_ROLE_UNKNOWN;
     198                 :            : 
     199                 :            :     static AtkRole roleMap[] = {
     200                 :            :         ATK_ROLE_UNKNOWN,
     201                 :            :         ATK_ROLE_ALERT,
     202                 :            :         ATK_ROLE_COLUMN_HEADER,
     203                 :            :         ATK_ROLE_CANVAS,
     204                 :            :         ATK_ROLE_CHECK_BOX,
     205                 :            :         ATK_ROLE_CHECK_MENU_ITEM,
     206                 :            :         ATK_ROLE_COLOR_CHOOSER,
     207                 :            :         ATK_ROLE_COMBO_BOX,
     208                 :            :         ATK_ROLE_DATE_EDITOR,
     209                 :            :         ATK_ROLE_DESKTOP_ICON,
     210                 :            :         ATK_ROLE_DESKTOP_FRAME,   // ? pane
     211                 :            :         ATK_ROLE_DIRECTORY_PANE,
     212                 :            :         ATK_ROLE_DIALOG,
     213                 :            :         ATK_ROLE_UNKNOWN,         // DOCUMENT - registered below
     214                 :            :         ATK_ROLE_UNKNOWN,         // EMBEDDED_OBJECT - registered below
     215                 :            :         ATK_ROLE_UNKNOWN,         // END_NOTE - registered below
     216                 :            :         ATK_ROLE_FILE_CHOOSER,
     217                 :            :         ATK_ROLE_FILLER,
     218                 :            :         ATK_ROLE_FONT_CHOOSER,
     219                 :            :         ATK_ROLE_FOOTER,
     220                 :            :         ATK_ROLE_TEXT,            // FOOTNOTE - registered below
     221                 :            :         ATK_ROLE_FRAME,
     222                 :            :         ATK_ROLE_GLASS_PANE,
     223                 :            :         ATK_ROLE_IMAGE,           // GRAPHIC
     224                 :            :         ATK_ROLE_UNKNOWN,         // GROUP_BOX - registered below
     225                 :            :         ATK_ROLE_HEADER,
     226                 :            :         ATK_ROLE_PARAGRAPH,       // HEADING - registered below
     227                 :            :         ATK_ROLE_TEXT,            // HYPER_LINK - registered below
     228                 :            :         ATK_ROLE_ICON,
     229                 :            :         ATK_ROLE_INTERNAL_FRAME,
     230                 :            :         ATK_ROLE_LABEL,
     231                 :            :         ATK_ROLE_LAYERED_PANE,
     232                 :            :         ATK_ROLE_LIST,
     233                 :            :         ATK_ROLE_LIST_ITEM,
     234                 :            :         ATK_ROLE_MENU,
     235                 :            :         ATK_ROLE_MENU_BAR,
     236                 :            :         ATK_ROLE_MENU_ITEM,
     237                 :            :         ATK_ROLE_OPTION_PANE,
     238                 :            :         ATK_ROLE_PAGE_TAB,
     239                 :            :         ATK_ROLE_PAGE_TAB_LIST,
     240                 :            :         ATK_ROLE_PANEL,
     241                 :            :         ATK_ROLE_PARAGRAPH,
     242                 :            :         ATK_ROLE_PASSWORD_TEXT,
     243                 :            :         ATK_ROLE_POPUP_MENU,
     244                 :            :         ATK_ROLE_PUSH_BUTTON,
     245                 :            :         ATK_ROLE_PROGRESS_BAR,
     246                 :            :         ATK_ROLE_RADIO_BUTTON,
     247                 :            :         ATK_ROLE_RADIO_MENU_ITEM,
     248                 :            :         ATK_ROLE_ROW_HEADER,
     249                 :            :         ATK_ROLE_ROOT_PANE,
     250                 :            :         ATK_ROLE_SCROLL_BAR,
     251                 :            :         ATK_ROLE_SCROLL_PANE,
     252                 :            :         ATK_ROLE_UNKNOWN,        // SHAPE - registered below
     253                 :            :         ATK_ROLE_SEPARATOR,
     254                 :            :         ATK_ROLE_SLIDER,
     255                 :            :         ATK_ROLE_SPIN_BUTTON,    // SPIN_BOX ?
     256                 :            :         ATK_ROLE_SPLIT_PANE,
     257                 :            :         ATK_ROLE_STATUSBAR,
     258                 :            :         ATK_ROLE_TABLE,
     259                 :            :         ATK_ROLE_TABLE_CELL,
     260                 :            :         ATK_ROLE_TEXT,
     261                 :            :         ATK_ROLE_INTERNAL_FRAME, // TEXT_FRAME - registered below
     262                 :            :         ATK_ROLE_TOGGLE_BUTTON,
     263                 :            :         ATK_ROLE_TOOL_BAR,
     264                 :            :         ATK_ROLE_TOOL_TIP,
     265                 :            :         ATK_ROLE_TREE,
     266                 :            :         ATK_ROLE_VIEWPORT,
     267                 :            :         ATK_ROLE_WINDOW,
     268                 :            :         ATK_ROLE_PUSH_BUTTON,   // BUTTON_DROPDOWN
     269                 :            :         ATK_ROLE_PUSH_BUTTON,   // BUTTON_MENU
     270                 :            :         ATK_ROLE_UNKNOWN,       // CAPTION - registered below
     271                 :            :         ATK_ROLE_UNKNOWN,       // CHART - registered below
     272                 :            :         ATK_ROLE_UNKNOWN,       // EDIT_BAR - registered below
     273                 :            :         ATK_ROLE_UNKNOWN,       // FORM - registered below
     274                 :            :         ATK_ROLE_UNKNOWN,       // IMAGE_MAP - registered below
     275                 :            :         ATK_ROLE_UNKNOWN,       // NOTE - registered below
     276                 :            :         ATK_ROLE_UNKNOWN,       // PAGE - registered below
     277                 :            :         ATK_ROLE_RULER,
     278                 :            :         ATK_ROLE_UNKNOWN,       // SECTION - registered below
     279                 :            :         ATK_ROLE_UNKNOWN,       // TREE_ITEM - registered below
     280                 :            :         ATK_ROLE_TREE_TABLE,
     281                 :            :         ATK_ROLE_SCROLL_PANE,   // COMMENT - mapped to atk_role_scroll_pane
     282                 :            :         ATK_ROLE_UNKNOWN        // COMMENT_END - mapped to atk_role_unknown
     283                 :            :     };
     284                 :            : 
     285                 :            :     static bool initialized = false;
     286                 :            : 
     287                 :          0 :     if( ! initialized )
     288                 :            :     {
     289                 :            :         // re-use strings from ATK library
     290                 :          0 :         roleMap[accessibility::AccessibleRole::EDIT_BAR] = registerRole("edit bar");
     291                 :          0 :         roleMap[accessibility::AccessibleRole::EMBEDDED_OBJECT] = registerRole("embedded component");
     292                 :          0 :         roleMap[accessibility::AccessibleRole::CHART] = registerRole("chart");
     293                 :          0 :         roleMap[accessibility::AccessibleRole::CAPTION] = registerRole("caption");
     294                 :          0 :         roleMap[accessibility::AccessibleRole::DOCUMENT] = registerRole("document frame");
     295                 :          0 :         roleMap[accessibility::AccessibleRole::HEADING] = registerRole("heading");
     296                 :          0 :         roleMap[accessibility::AccessibleRole::PAGE] = registerRole("page");
     297                 :          0 :         roleMap[accessibility::AccessibleRole::SECTION] = registerRole("section");
     298                 :          0 :         roleMap[accessibility::AccessibleRole::FORM] = registerRole("form");
     299                 :            : 
     300                 :            :         // these don't exist in ATK yet
     301                 :          0 :         roleMap[accessibility::AccessibleRole::END_NOTE] = registerRole("end note");
     302                 :          0 :         roleMap[accessibility::AccessibleRole::FOOTNOTE] = registerRole("foot note");
     303                 :          0 :         roleMap[accessibility::AccessibleRole::GROUP_BOX] = registerRole("group box");
     304                 :          0 :         roleMap[accessibility::AccessibleRole::HYPER_LINK] = registerRole("hyper link");
     305                 :          0 :         roleMap[accessibility::AccessibleRole::SHAPE] = registerRole("shape");
     306                 :          0 :         roleMap[accessibility::AccessibleRole::TEXT_FRAME] = registerRole("text frame");
     307                 :          0 :         roleMap[accessibility::AccessibleRole::IMAGE_MAP] = registerRole("image map");
     308                 :          0 :         roleMap[accessibility::AccessibleRole::NOTE] = registerRole("note");
     309                 :          0 :         roleMap[accessibility::AccessibleRole::TREE_ITEM] = registerRole("tree item");
     310                 :            : 
     311                 :          0 :         initialized = true;
     312                 :            :     }
     313                 :            : 
     314                 :            :     static const sal_Int32 nMapSize = SAL_N_ELEMENTS(roleMap);
     315                 :          0 :     if( 0 <= nRole &&  nMapSize > nRole )
     316                 :          0 :         role = roleMap[nRole];
     317                 :            : 
     318                 :          0 :     return role;
     319                 :            : }
     320                 :            : 
     321                 :            : 
     322                 :            : /*****************************************************************************/
     323                 :            : 
     324                 :            : extern "C" {
     325                 :            : 
     326                 :            : /*****************************************************************************/
     327                 :            : 
     328                 :            : static G_CONST_RETURN gchar*
     329                 :          0 : wrapper_get_name( AtkObject *atk_obj )
     330                 :            : {
     331                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     332                 :            : 
     333                 :          0 :     if( obj->mpContext )
     334                 :            :     {
     335                 :            :         try {
     336                 :            :             rtl::OString aName =
     337                 :            :                 rtl::OUStringToOString(
     338                 :          0 :                     obj->mpContext->getAccessibleName(),
     339                 :          0 :                     RTL_TEXTENCODING_UTF8);
     340                 :            : 
     341                 :          0 :             int nCmp = atk_obj->name ? rtl_str_compare( atk_obj->name, aName.getStr() ) : -1;
     342                 :          0 :             if( nCmp != 0 )
     343                 :            :             {
     344                 :          0 :                 if( atk_obj->name )
     345                 :          0 :                     g_free(atk_obj->name);
     346                 :          0 :                 atk_obj->name = g_strdup(aName.getStr());
     347                 :          0 :             }
     348                 :            :         }
     349                 :          0 :         catch(const uno::Exception& e) {
     350                 :          0 :             g_warning( "Exception in getAccessibleName()" );
     351                 :            :         }
     352                 :            :     }
     353                 :            : 
     354                 :          0 :     return ATK_OBJECT_CLASS (parent_class)->get_name(atk_obj);
     355                 :            : }
     356                 :            : 
     357                 :            : /*****************************************************************************/
     358                 :            : 
     359                 :            : static G_CONST_RETURN gchar*
     360                 :          0 : wrapper_get_description( AtkObject *atk_obj )
     361                 :            : {
     362                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     363                 :            : 
     364                 :          0 :     if( obj->mpContext )
     365                 :            :     {
     366                 :            :         try {
     367                 :            :             rtl::OString aDescription =
     368                 :            :                 rtl::OUStringToOString(
     369                 :          0 :                     obj->mpContext->getAccessibleDescription(),
     370                 :          0 :                     RTL_TEXTENCODING_UTF8);
     371                 :            : 
     372                 :          0 :             g_free(atk_obj->description);
     373                 :          0 :             atk_obj->description = g_strdup(aDescription.getStr());
     374                 :            :         }
     375                 :          0 :         catch(const uno::Exception& e) {
     376                 :          0 :             g_warning( "Exception in getAccessibleDescription()" );
     377                 :            :         }
     378                 :            :     }
     379                 :            : 
     380                 :          0 :     return ATK_OBJECT_CLASS (parent_class)->get_description(atk_obj);
     381                 :            : 
     382                 :            : }
     383                 :            : 
     384                 :            : /*****************************************************************************/
     385                 :            : 
     386                 :            : static gint
     387                 :          0 : wrapper_get_n_children( AtkObject *atk_obj )
     388                 :            : {
     389                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     390                 :          0 :     gint n = 0;
     391                 :            : 
     392                 :          0 :     if( obj->mpContext )
     393                 :            :     {
     394                 :            :         try {
     395                 :          0 :             n = obj->mpContext->getAccessibleChildCount();
     396                 :            :         }
     397                 :          0 :         catch(const uno::Exception& e) {
     398                 :            :             OSL_FAIL("Exception in getAccessibleChildCount()" );
     399                 :            :         }
     400                 :            :     }
     401                 :            : 
     402                 :          0 :     return n;
     403                 :            : }
     404                 :            : 
     405                 :            : /*****************************************************************************/
     406                 :            : 
     407                 :            : static AtkObject *
     408                 :          0 : wrapper_ref_child( AtkObject *atk_obj,
     409                 :            :                    gint       i )
     410                 :            : {
     411                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     412                 :          0 :     AtkObject* child = NULL;
     413                 :            : 
     414                 :            :     // see comments above atk_object_wrapper_remove_child
     415                 :          0 :     if( -1 < i && obj->index_of_child_about_to_be_removed == i )
     416                 :            :     {
     417                 :          0 :         g_object_ref( obj->child_about_to_be_removed );
     418                 :          0 :         return obj->child_about_to_be_removed;
     419                 :            :     }
     420                 :            : 
     421                 :          0 :     if( obj->mpContext )
     422                 :            :     {
     423                 :            :         try {
     424                 :            :             uno::Reference< accessibility::XAccessible > xAccessible =
     425                 :          0 :                 obj->mpContext->getAccessibleChild( i );
     426                 :            : 
     427                 :          0 :             child = atk_object_wrapper_ref( xAccessible );
     428                 :            :         }
     429                 :          0 :         catch(const uno::Exception& e) {
     430                 :            :             OSL_FAIL("Exception in getAccessibleChild");
     431                 :            :         }
     432                 :            :     }
     433                 :            : 
     434                 :          0 :     return child;
     435                 :            : }
     436                 :            : 
     437                 :            : /*****************************************************************************/
     438                 :            : 
     439                 :            : static gint
     440                 :          0 : wrapper_get_index_in_parent( AtkObject *atk_obj )
     441                 :            : {
     442                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     443                 :          0 :     gint i = -1;
     444                 :            : 
     445                 :          0 :     if( obj->mpContext )
     446                 :            :     {
     447                 :            :         try {
     448                 :          0 :             i = obj->mpContext->getAccessibleIndexInParent();
     449                 :            : 
     450                 :            : #ifdef ENABLE_TRACING
     451                 :            :             fprintf(stderr, "%p->getAccessibleIndexInParent() returned: %u\n",
     452                 :            :                 obj->mpAccessible, i);
     453                 :            : #endif
     454                 :            :         }
     455                 :          0 :         catch(const uno::Exception& e) {
     456                 :          0 :             g_warning( "Exception in getAccessibleIndexInParent()" );
     457                 :            :         }
     458                 :            :     }
     459                 :          0 :     return i;
     460                 :            : }
     461                 :            : 
     462                 :            : /*****************************************************************************/
     463                 :            : 
     464                 :            : static AtkRelationSet *
     465                 :          0 : wrapper_ref_relation_set( AtkObject *atk_obj )
     466                 :            : {
     467                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     468                 :          0 :     AtkRelationSet *pSet = atk_relation_set_new();
     469                 :            : 
     470                 :          0 :     if( obj->mpContext )
     471                 :            :     {
     472                 :            :         try {
     473                 :            :             uno::Reference< accessibility::XAccessibleRelationSet > xRelationSet(
     474                 :          0 :                     obj->mpContext->getAccessibleRelationSet()
     475                 :          0 :             );
     476                 :            : 
     477                 :          0 :             sal_Int32 nRelations = xRelationSet.is() ? xRelationSet->getRelationCount() : 0;
     478                 :          0 :             for( sal_Int32 n = 0; n < nRelations; n++ )
     479                 :            :             {
     480                 :          0 :                 accessibility::AccessibleRelation aRelation = xRelationSet->getRelation( n );
     481                 :          0 :                 sal_uInt32 nTargetCount = aRelation.TargetSet.getLength();
     482                 :          0 :                 AtkObject **pTargets = (AtkObject **) alloca( nTargetCount * sizeof(AtkObject *) );
     483                 :            : 
     484                 :          0 :                 for( sal_uInt32 i = 0; i < nTargetCount; i++ )
     485                 :            :                 {
     486                 :            :                     uno::Reference< accessibility::XAccessible > xAccessible(
     487                 :          0 :                             aRelation.TargetSet[i], uno::UNO_QUERY );
     488                 :          0 :                     pTargets[i] = atk_object_wrapper_ref( xAccessible );
     489                 :          0 :                 }
     490                 :            : 
     491                 :            :                 AtkRelation *pRel =
     492                 :            :                     atk_relation_new(
     493                 :            :                         pTargets, nTargetCount,
     494                 :            :                         mapRelationType( aRelation.RelationType )
     495                 :          0 :                     );
     496                 :          0 :                 atk_relation_set_add( pSet, pRel );
     497                 :          0 :                 g_object_unref( G_OBJECT( pRel ) );
     498                 :          0 :             }
     499                 :            :         }
     500                 :          0 :         catch(const uno::Exception &e) {
     501                 :          0 :             g_object_unref( G_OBJECT( pSet ) );
     502                 :          0 :             pSet = NULL;
     503                 :            :         }
     504                 :            :     }
     505                 :            : 
     506                 :          0 :     return pSet;
     507                 :            : }
     508                 :            : 
     509                 :            : static AtkStateSet *
     510                 :          0 : wrapper_ref_state_set( AtkObject *atk_obj )
     511                 :            : {
     512                 :          0 :     AtkObjectWrapper *obj = ATK_OBJECT_WRAPPER (atk_obj);
     513                 :          0 :     AtkStateSet *pSet = atk_state_set_new();
     514                 :            : 
     515                 :          0 :     if( obj->mpContext )
     516                 :            :     {
     517                 :            :         try {
     518                 :            :             uno::Reference< accessibility::XAccessibleStateSet > xStateSet(
     519                 :          0 :                 obj->mpContext->getAccessibleStateSet());
     520                 :            : 
     521                 :          0 :             if( xStateSet.is() )
     522                 :            :             {
     523                 :          0 :                 uno::Sequence< sal_Int16 > aStates = xStateSet->getStates();
     524                 :            : 
     525                 :          0 :                 for( sal_Int32 n = 0; n < aStates.getLength(); n++ )
     526                 :          0 :                     atk_state_set_add_state( pSet, mapAtkState( aStates[n] ) );
     527                 :            : 
     528                 :            :                 // We need to emulate FOCUS state for menus, menu-items etc.
     529                 :          0 :                 if( atk_obj == atk_get_focus_object() )
     530                 :          0 :                     atk_state_set_add_state( pSet, ATK_STATE_FOCUSED );
     531                 :            : /* FIXME - should we do this ?
     532                 :            :                 else
     533                 :            :                     atk_state_set_remove_state( pSet, ATK_STATE_FOCUSED );
     534                 :            : */
     535                 :          0 :             }
     536                 :            :         }
     537                 :            : 
     538                 :          0 :         catch(const uno::Exception &e) {
     539                 :          0 :             g_warning( "Exception in wrapper_ref_state_set" );
     540                 :          0 :             atk_state_set_add_state( pSet, ATK_STATE_DEFUNCT );
     541                 :            :         }
     542                 :            :     }
     543                 :            :     else
     544                 :          0 :         atk_state_set_add_state( pSet, ATK_STATE_DEFUNCT );
     545                 :            : 
     546                 :          0 :     return pSet;
     547                 :            : }
     548                 :            : 
     549                 :            : /*****************************************************************************/
     550                 :            : 
     551                 :            : 
     552                 :            : static void
     553                 :          0 : atk_object_wrapper_finalize (GObject *obj)
     554                 :            : {
     555                 :          0 :     AtkObjectWrapper *pWrap = ATK_OBJECT_WRAPPER (obj);
     556                 :            : 
     557                 :          0 :     if( pWrap->mpAccessible )
     558                 :            :     {
     559                 :          0 :         ooo_wrapper_registry_remove( pWrap->mpAccessible );
     560                 :          0 :         pWrap->mpAccessible->release();
     561                 :          0 :         pWrap->mpAccessible = NULL;
     562                 :            :     }
     563                 :            : 
     564                 :          0 :     atk_object_wrapper_dispose( pWrap );
     565                 :            : 
     566                 :          0 :     parent_class->finalize( obj );
     567                 :          0 : }
     568                 :            : 
     569                 :            : static void
     570                 :          0 : atk_object_wrapper_class_init (AtkObjectWrapperClass *klass)
     571                 :            : {
     572                 :          0 :   GObjectClass *gobject_class = G_OBJECT_CLASS( klass );
     573                 :          0 :   AtkObjectClass *atk_class = ATK_OBJECT_CLASS( klass );
     574                 :            : 
     575                 :          0 :   parent_class = (GObjectClass *) g_type_class_peek_parent (klass);
     576                 :            : 
     577                 :            :   // GObject methods
     578                 :          0 :   gobject_class->finalize = atk_object_wrapper_finalize;
     579                 :            : 
     580                 :            :   // AtkObject methods
     581                 :          0 :   atk_class->get_name = wrapper_get_name;
     582                 :          0 :   atk_class->get_description = wrapper_get_description;
     583                 :          0 :   atk_class->get_n_children = wrapper_get_n_children;
     584                 :          0 :   atk_class->ref_child = wrapper_ref_child;
     585                 :          0 :   atk_class->get_index_in_parent = wrapper_get_index_in_parent;
     586                 :          0 :   atk_class->ref_relation_set = wrapper_ref_relation_set;
     587                 :          0 :   atk_class->ref_state_set = wrapper_ref_state_set;
     588                 :          0 : }
     589                 :            : 
     590                 :            : static void
     591                 :          0 : atk_object_wrapper_init (AtkObjectWrapper      *wrapper,
     592                 :            :                          AtkObjectWrapperClass)
     593                 :            : {
     594                 :          0 :    wrapper->mpAction = NULL;
     595                 :          0 :    wrapper->mpComponent = NULL;
     596                 :          0 :    wrapper->mpEditableText = NULL;
     597                 :          0 :    wrapper->mpHypertext = NULL;
     598                 :          0 :    wrapper->mpImage = NULL;
     599                 :          0 :    wrapper->mpSelection = NULL;
     600                 :          0 :    wrapper->mpTable = NULL;
     601                 :          0 :    wrapper->mpText = NULL;
     602                 :          0 :    wrapper->mpValue = NULL;
     603                 :          0 : }
     604                 :            : 
     605                 :            : } // extern "C"
     606                 :            : 
     607                 :            : GType
     608                 :          0 : atk_object_wrapper_get_type (void)
     609                 :            : {
     610                 :            :   static GType type = 0;
     611                 :            : 
     612                 :          0 :   if (!type)
     613                 :            :     {
     614                 :            :       static const GTypeInfo typeInfo =
     615                 :            :       {
     616                 :            :         sizeof (AtkObjectWrapperClass),
     617                 :            :         (GBaseInitFunc) NULL,
     618                 :            :         (GBaseFinalizeFunc) NULL,
     619                 :            :         (GClassInitFunc) atk_object_wrapper_class_init,
     620                 :            :         (GClassFinalizeFunc) NULL,
     621                 :            :         NULL,
     622                 :            :         sizeof (AtkObjectWrapper),
     623                 :            :         0,
     624                 :            :         (GInstanceInitFunc) atk_object_wrapper_init,
     625                 :            :         NULL
     626                 :            :       } ;
     627                 :            :       type = g_type_register_static (ATK_TYPE_OBJECT,
     628                 :            :                                      "OOoAtkObj",
     629                 :          0 :                                      &typeInfo, (GTypeFlags)0) ;
     630                 :            :     }
     631                 :          0 :   return type;
     632                 :            : }
     633                 :            : 
     634                 :            : static bool
     635                 :          0 : isOfType( uno::XInterface *pInterface, const uno::Type & rType )
     636                 :            : {
     637                 :          0 :     g_return_val_if_fail( pInterface != NULL, false );
     638                 :            : 
     639                 :          0 :     bool bIs = false;
     640                 :            :     try {
     641                 :          0 :         uno::Any aRet = pInterface->queryInterface( rType );
     642                 :            : 
     643                 :            :         bIs = ( ( typelib_TypeClass_INTERFACE == aRet.pType->eTypeClass ) &&
     644                 :          0 :                 ( aRet.pReserved != NULL ) );
     645                 :          0 :     } catch( const uno::Exception &e) { }
     646                 :            : 
     647                 :          0 :     return bIs;
     648                 :            : }
     649                 :            : 
     650                 :            : extern "C" {
     651                 :            : typedef  GType (* GetGIfaceType ) (void);
     652                 :            : }
     653                 :            : const struct {
     654                 :            :         const char          *name;
     655                 :            :         GInterfaceInitFunc   aInit;
     656                 :            :         GetGIfaceType        aGetGIfaceType;
     657                 :            :         const uno::Type &  (*aGetUnoType) (void *);
     658                 :            : } aTypeTable[] = {
     659                 :            : // re-location heaven:
     660                 :            :     {
     661                 :            :         "Comp", (GInterfaceInitFunc) componentIfaceInit,
     662                 :            :         atk_component_get_type,
     663                 :            :         accessibility::XAccessibleComponent::static_type
     664                 :            :     },
     665                 :            :     {
     666                 :            :         "Act",  (GInterfaceInitFunc) actionIfaceInit,
     667                 :            :         atk_action_get_type,
     668                 :            :         accessibility::XAccessibleAction::static_type
     669                 :            :     },
     670                 :            :     {
     671                 :            :         "Txt",  (GInterfaceInitFunc) textIfaceInit,
     672                 :            :         atk_text_get_type,
     673                 :            :         accessibility::XAccessibleText::static_type
     674                 :            :     },
     675                 :            :     {
     676                 :            :         "Val",  (GInterfaceInitFunc) valueIfaceInit,
     677                 :            :         atk_value_get_type,
     678                 :            :         accessibility::XAccessibleValue::static_type
     679                 :            :     },
     680                 :            :     {
     681                 :            :         "Tab",  (GInterfaceInitFunc) tableIfaceInit,
     682                 :            :         atk_table_get_type,
     683                 :            :         accessibility::XAccessibleTable::static_type
     684                 :            :     },
     685                 :            :     {
     686                 :            :         "Edt",  (GInterfaceInitFunc) editableTextIfaceInit,
     687                 :            :         atk_editable_text_get_type,
     688                 :            :         accessibility::XAccessibleEditableText::static_type
     689                 :            :     },
     690                 :            :     {
     691                 :            :         "Img",  (GInterfaceInitFunc) imageIfaceInit,
     692                 :            :         atk_image_get_type,
     693                 :            :         accessibility::XAccessibleImage::static_type
     694                 :            :     },
     695                 :            :     {
     696                 :            :         "Hyp",  (GInterfaceInitFunc) hypertextIfaceInit,
     697                 :            :         atk_hypertext_get_type,
     698                 :            :         accessibility::XAccessibleHypertext::static_type
     699                 :            :     },
     700                 :            :     {
     701                 :            :         "Sel",  (GInterfaceInitFunc) selectionIfaceInit,
     702                 :            :         atk_selection_get_type,
     703                 :            :         accessibility::XAccessibleSelection::static_type
     704                 :            :     }
     705                 :            :     // AtkDocument is a nastily broken interface (so far)
     706                 :            :     //  we could impl. get_document_type perhaps though.
     707                 :            : };
     708                 :            : 
     709                 :            : const int aTypeTableSize = G_N_ELEMENTS( aTypeTable );
     710                 :            : 
     711                 :            : static GType
     712                 :          0 : ensureTypeFor( uno::XInterface *pAccessible )
     713                 :            : {
     714                 :            :     int i;
     715                 :          0 :     int bTypes[ aTypeTableSize ] = { 0, };
     716                 :          0 :     rtl::OString aTypeName( "OOoAtkObj" );
     717                 :            : 
     718                 :          0 :     for( i = 0; i < aTypeTableSize; i++ )
     719                 :            :     {
     720                 :          0 :         if( isOfType( pAccessible, aTypeTable[i].aGetUnoType(0) ) )
     721                 :            :         {
     722                 :          0 :             aTypeName += aTypeTable[i].name;
     723                 :          0 :             bTypes[i] = TRUE;
     724                 :            :         }
     725                 :            :     }
     726                 :            : 
     727                 :          0 :     GType nType = g_type_from_name( aTypeName.getStr() );
     728                 :          0 :     if( nType == G_TYPE_INVALID )
     729                 :            :     {
     730                 :            :         GTypeInfo aTypeInfo = {
     731                 :            :             sizeof( AtkObjectWrapperClass ),
     732                 :            :             NULL, NULL, NULL, NULL, NULL,
     733                 :            :             sizeof( AtkObjectWrapper ),
     734                 :            :             0, NULL, NULL
     735                 :          0 :         } ;
     736                 :            :         nType = g_type_register_static( ATK_TYPE_OBJECT_WRAPPER,
     737                 :            :                                         aTypeName.getStr(), &aTypeInfo,
     738                 :          0 :                                         (GTypeFlags)0 ) ;
     739                 :            : 
     740                 :          0 :         for( int j = 0; j < aTypeTableSize; j++ )
     741                 :          0 :             if( bTypes[j] )
     742                 :            :             {
     743                 :          0 :                 GInterfaceInfo aIfaceInfo = { NULL, NULL, NULL };
     744                 :          0 :                 aIfaceInfo.interface_init = aTypeTable[j].aInit;
     745                 :            :                 g_type_add_interface_static (nType, aTypeTable[j].aGetGIfaceType(),
     746                 :          0 :                                              &aIfaceInfo);
     747                 :            :             }
     748                 :            :     }
     749                 :          0 :     return nType;
     750                 :            : }
     751                 :            : 
     752                 :            : AtkObject *
     753                 :          0 : atk_object_wrapper_ref( const uno::Reference< accessibility::XAccessible > &rxAccessible, bool create )
     754                 :            : {
     755                 :          0 :     g_return_val_if_fail( rxAccessible.get() != NULL, NULL );
     756                 :            : 
     757                 :          0 :     AtkObject *obj = ooo_wrapper_registry_get(rxAccessible);
     758                 :          0 :     if( obj )
     759                 :            :     {
     760                 :          0 :         g_object_ref( obj );
     761                 :          0 :         return obj;
     762                 :            :     }
     763                 :            : 
     764                 :          0 :     if( create )
     765                 :          0 :         return atk_object_wrapper_new( rxAccessible );
     766                 :            : 
     767                 :          0 :     return NULL;
     768                 :            : }
     769                 :            : 
     770                 :            : 
     771                 :            : AtkObject *
     772                 :          0 : atk_object_wrapper_new( const ::com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible >& rxAccessible,
     773                 :            :                         AtkObject* parent )
     774                 :            : {
     775                 :          0 :     g_return_val_if_fail( rxAccessible.get() != NULL, NULL );
     776                 :            : 
     777                 :          0 :     AtkObjectWrapper *pWrap = NULL;
     778                 :            : 
     779                 :            :     try {
     780                 :          0 :         uno::Reference< accessibility::XAccessibleContext > xContext(rxAccessible->getAccessibleContext());
     781                 :            : 
     782                 :          0 :         g_return_val_if_fail( xContext.get() != NULL, NULL );
     783                 :            : 
     784                 :          0 :         GType nType = ensureTypeFor( xContext.get() );
     785                 :          0 :         gpointer obj = g_object_new( nType, NULL);
     786                 :            : 
     787                 :          0 :         pWrap = ATK_OBJECT_WRAPPER( obj );
     788                 :          0 :         pWrap->mpAccessible = rxAccessible.get();
     789                 :          0 :         rxAccessible->acquire();
     790                 :            : 
     791                 :          0 :         pWrap->index_of_child_about_to_be_removed = -1;
     792                 :          0 :         pWrap->child_about_to_be_removed = NULL;
     793                 :            : 
     794                 :          0 :         xContext->acquire();
     795                 :          0 :         pWrap->mpContext = xContext.get();
     796                 :            : 
     797                 :          0 :         AtkObject* atk_obj = ATK_OBJECT(pWrap);
     798                 :          0 :         atk_obj->role = mapToAtkRole( xContext->getAccessibleRole() );
     799                 :          0 :         atk_obj->accessible_parent = parent;
     800                 :            : 
     801                 :          0 :         ooo_wrapper_registry_add( rxAccessible, atk_obj );
     802                 :            : 
     803                 :          0 :         if( parent )
     804                 :          0 :             g_object_ref( atk_obj->accessible_parent );
     805                 :            :         else
     806                 :            :         {
     807                 :            :             /* gail_focus_tracker remembers the focused object at the first
     808                 :            :              * parent in the hierachy that is a Gtk+ widget, but at the time the
     809                 :            :              * event gets processed (at idle), it may be too late to create the
     810                 :            :              * hierachy, so doing it now ..
     811                 :            :              */
     812                 :          0 :             uno::Reference< accessibility::XAccessible > xParent( xContext->getAccessibleParent() );
     813                 :            : 
     814                 :            :             /* The top-level objects should never be of this class */
     815                 :            :             OSL_ASSERT( xParent.is() );
     816                 :            : 
     817                 :          0 :             if( xParent.is() )
     818                 :          0 :                 atk_obj->accessible_parent = atk_object_wrapper_ref( xParent );
     819                 :            :         }
     820                 :            : 
     821                 :            :         // Attach a listener to the UNO object if it's not TRANSIENT
     822                 :          0 :         uno::Reference< accessibility::XAccessibleStateSet > xStateSet( xContext->getAccessibleStateSet() );
     823                 :          0 :         if( xStateSet.is() && ! xStateSet->contains( accessibility::AccessibleStateType::TRANSIENT ) )
     824                 :            :         {
     825                 :          0 :             uno::Reference< accessibility::XAccessibleEventBroadcaster > xBroadcaster(xContext, uno::UNO_QUERY);
     826                 :          0 :             if( xBroadcaster.is() )
     827                 :          0 :                 xBroadcaster->addEventListener( static_cast< accessibility::XAccessibleEventListener * > ( new AtkListener(pWrap) ) );
     828                 :            :         else
     829                 :          0 :                 OSL_ASSERT( false );
     830                 :            :         }
     831                 :            : 
     832                 :          0 :         return ATK_OBJECT( pWrap );
     833                 :            :     }
     834                 :          0 :     catch (const uno::Exception &e)
     835                 :            :     {
     836                 :          0 :         if( pWrap )
     837                 :          0 :             g_object_unref( pWrap );
     838                 :            : 
     839                 :          0 :         return NULL;
     840                 :            :     }
     841                 :            : }
     842                 :            : 
     843                 :            : 
     844                 :            : /*****************************************************************************/
     845                 :            : 
     846                 :          0 : void atk_object_wrapper_add_child(AtkObjectWrapper* wrapper, AtkObject *child, gint index)
     847                 :            : {
     848                 :          0 :     AtkObject *atk_obj = ATK_OBJECT( wrapper );
     849                 :            : 
     850                 :          0 :     atk_object_set_parent( child, atk_obj );
     851                 :          0 :     g_signal_emit_by_name( atk_obj, "children_changed::add", index, child, NULL );
     852                 :          0 : }
     853                 :            : 
     854                 :            : /*****************************************************************************/
     855                 :            : 
     856                 :          0 : void atk_object_wrapper_remove_child(AtkObjectWrapper* wrapper, AtkObject *child, gint index)
     857                 :            : {
     858                 :            :     /*
     859                 :            :      * the atk-bridge GTK+ module get's back to the event source to ref the child just
     860                 :            :      * vanishing, so we keep this reference because the semantic on OOo side is different.
     861                 :            :      */
     862                 :          0 :     wrapper->child_about_to_be_removed = child;
     863                 :          0 :     wrapper->index_of_child_about_to_be_removed = index;
     864                 :            : 
     865                 :          0 :     g_signal_emit_by_name( ATK_OBJECT( wrapper ), "children_changed::remove", index, child, NULL );
     866                 :            : 
     867                 :          0 :     wrapper->index_of_child_about_to_be_removed = -1;
     868                 :          0 :     wrapper->child_about_to_be_removed = NULL;
     869                 :          0 : }
     870                 :            : 
     871                 :            : /*****************************************************************************/
     872                 :            : 
     873                 :            : #define RELEASE(i) if( i ) { i->release(); i = NULL; }
     874                 :            : 
     875                 :          0 : void atk_object_wrapper_dispose(AtkObjectWrapper* wrapper)
     876                 :            : {
     877                 :          0 :     RELEASE( wrapper->mpContext )
     878                 :          0 :     RELEASE( wrapper->mpAction )
     879                 :          0 :     RELEASE( wrapper->mpComponent )
     880                 :          0 :     RELEASE( wrapper->mpEditableText )
     881                 :          0 :     RELEASE( wrapper->mpHypertext )
     882                 :          0 :     RELEASE( wrapper->mpImage )
     883                 :          0 :     RELEASE( wrapper->mpSelection )
     884                 :          0 :     RELEASE( wrapper->mpMultiLineText )
     885                 :          0 :     RELEASE( wrapper->mpTable )
     886                 :          0 :     RELEASE( wrapper->mpText )
     887                 :          0 :     RELEASE( wrapper->mpTextMarkup )
     888                 :          0 :     RELEASE( wrapper->mpTextAttributes )
     889                 :          0 :     RELEASE( wrapper->mpValue )
     890                 :          0 : }
     891                 :            : 
     892                 :            : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10