Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(292)

Unified Diff: Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.cpp

Issue 13726025: Remove GTK AX support, we've never used it (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.h ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.cpp
diff --git a/Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.cpp b/Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.cpp
deleted file mode 100644
index f0284af683413bb71952e4fd46c0e868825349c5..0000000000000000000000000000000000000000
--- a/Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.cpp
+++ /dev/null
@@ -1,1200 +0,0 @@
-/*
- * Copyright (C) 2008 Nuanti Ltd.
- * Copyright (C) 2009 Jan Alonzo
- * Copyright (C) 2009, 2010, 2011, 2012 Igalia S.L.
- * Copyright (C) 2013 Samsung Electronics
- *
- * Portions from Mozilla a11y, copyright as follows:
- *
- * The Original Code is mozilla.org code.
- *
- * The Initial Developer of the Original Code is
- * Sun Microsystems, Inc.
- * Portions created by the Initial Developer are Copyright (C) 2002
- * the Initial Developer. All Rights Reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#include "config.h"
-#include "WebKitAccessibleWrapperAtk.h"
-
-#if HAVE(ACCESSIBILITY)
-
-#include "AXObjectCache.h"
-#include "Document.h"
-#include "Frame.h"
-#include "FrameView.h"
-#include "HTMLNames.h"
-#include "HTMLTableElement.h"
-#include "HostWindow.h"
-#include "RenderObject.h"
-#include "Settings.h"
-#include "TextIterator.h"
-#include "VisibleUnits.h"
-#include "WebKitAccessibleHyperlink.h"
-#include "WebKitAccessibleInterfaceAction.h"
-#include "WebKitAccessibleInterfaceComponent.h"
-#include "WebKitAccessibleInterfaceDocument.h"
-#include "WebKitAccessibleInterfaceEditableText.h"
-#include "WebKitAccessibleInterfaceHyperlinkImpl.h"
-#include "WebKitAccessibleInterfaceHypertext.h"
-#include "WebKitAccessibleInterfaceImage.h"
-#include "WebKitAccessibleInterfaceSelection.h"
-#include "WebKitAccessibleInterfaceTable.h"
-#include "WebKitAccessibleInterfaceText.h"
-#include "WebKitAccessibleInterfaceValue.h"
-#include "WebKitAccessibleUtil.h"
-#include "htmlediting.h"
-#include <glib/gprintf.h>
-
-#if PLATFORM(GTK)
-#include <gtk/gtk.h>
-#endif
-
-using namespace WebCore;
-
-struct _WebKitAccessiblePrivate {
- // Cached data for AtkObject.
- CString accessibleName;
- CString accessibleDescription;
-
- // Cached data for AtkAction.
- CString actionName;
- CString actionKeyBinding;
-
- // Cached data for AtkDocument.
- CString documentLocale;
- CString documentType;
- CString documentEncoding;
- CString documentURI;
-
- // Cached data for AtkImage.
- CString imageDescription;
-};
-
-#define WEBKIT_ACCESSIBLE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), WEBKIT_TYPE_ACCESSIBLE, WebKitAccessiblePrivate))
-
-static AccessibilityObject* fallbackObject()
-{
- // FIXME: An AXObjectCache with a Document is meaningless.
- static AXObjectCache* fallbackCache = new AXObjectCache(0);
- static AccessibilityObject* object = 0;
- if (!object) {
- // FIXME: using fallbackCache->getOrCreate(ListBoxOptionRole) is a hack
- object = fallbackCache->getOrCreate(ListBoxOptionRole);
- object->ref();
- }
-
- return object;
-}
-
-static AccessibilityObject* core(WebKitAccessible* accessible)
-{
- if (!accessible)
- return 0;
-
- return accessible->m_object;
-}
-
-static AccessibilityObject* core(AtkObject* object)
-{
- if (!WEBKIT_IS_ACCESSIBLE(object))
- return 0;
-
- return core(WEBKIT_ACCESSIBLE(object));
-}
-
-static const gchar* webkitAccessibleGetName(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
- if (!coreObject->isAccessibilityRenderObject())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, coreObject->stringValue());
-
- if (coreObject->isFieldset()) {
- AccessibilityObject* label = coreObject->titleUIElement();
- if (label) {
- AtkObject* atkObject = label->wrapper();
- if (ATK_IS_TEXT(atkObject))
- return atk_text_get_text(ATK_TEXT(atkObject), 0, -1);
- }
- }
-
- if (coreObject->isControl()) {
- AccessibilityObject* label = coreObject->correspondingLabelForControlElement();
- if (label) {
- AtkObject* atkObject = label->wrapper();
- if (ATK_IS_TEXT(atkObject))
- return atk_text_get_text(ATK_TEXT(atkObject), 0, -1);
- }
-
- // Try text under the node.
- String textUnder = coreObject->textUnderElement();
- if (textUnder.length())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, textUnder);
- }
-
- if (coreObject->isImage() || coreObject->isInputImage()) {
- Node* node = coreObject->node();
- if (node && node->isHTMLElement()) {
- // Get the attribute rather than altText String so as not to fall back on title.
- String alt = toHTMLElement(node)->getAttribute(HTMLNames::altAttr);
- if (!alt.isEmpty())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, alt);
- }
- }
-
- // Fallback for the webArea object: just return the document's title.
- if (coreObject->isWebArea()) {
- Document* document = coreObject->document();
- if (document)
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, document->title());
- }
-
- // Nothing worked so far, try with the AccessibilityObject's
- // title() before going ahead with stringValue().
- String axTitle = accessibilityTitle(coreObject);
- if (!axTitle.isEmpty())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, axTitle);
-
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleName, coreObject->stringValue());
-}
-
-static const gchar* webkitAccessibleGetDescription(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
- Node* node = 0;
- if (coreObject->isAccessibilityRenderObject())
- node = coreObject->node();
- if (!node || !node->isHTMLElement() || coreObject->ariaRoleAttribute() != UnknownRole)
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleDescription, accessibilityDescription(coreObject));
-
- // atk_table_get_summary returns an AtkObject. We have no summary object, so expose summary here.
- if (coreObject->roleValue() == TableRole) {
- String summary = static_cast<HTMLTableElement*>(node)->summary();
- if (!summary.isEmpty())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleDescription, summary);
- }
-
- // The title attribute should be reliably available as the object's descripton.
- // We do not want to fall back on other attributes in its absence. See bug 25524.
- String title = toHTMLElement(node)->title();
- if (!title.isEmpty())
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleDescription, title);
-
- return cacheAndReturnAtkProperty(object, AtkCachedAccessibleDescription, accessibilityDescription(coreObject));
-}
-
-static void setAtkRelationSetFromCoreObject(AccessibilityObject* coreObject, AtkRelationSet* relationSet)
-{
- if (coreObject->isFieldset()) {
- AccessibilityObject* label = coreObject->titleUIElement();
- if (label)
- atk_relation_set_add_relation_by_type(relationSet, ATK_RELATION_LABELLED_BY, label->wrapper());
- return;
- }
-
- if (coreObject->roleValue() == LegendRole) {
- for (AccessibilityObject* parent = coreObject->parentObjectUnignored(); parent; parent = parent->parentObjectUnignored()) {
- if (parent->isFieldset()) {
- atk_relation_set_add_relation_by_type(relationSet, ATK_RELATION_LABEL_FOR, parent->wrapper());
- break;
- }
- }
- return;
- }
-
- if (coreObject->isControl()) {
- AccessibilityObject* label = coreObject->correspondingLabelForControlElement();
- if (label)
- atk_relation_set_add_relation_by_type(relationSet, ATK_RELATION_LABELLED_BY, label->wrapper());
- } else {
- AccessibilityObject* control = coreObject->correspondingControlForLabelElement();
- if (control)
- atk_relation_set_add_relation_by_type(relationSet, ATK_RELATION_LABEL_FOR, control->wrapper());
- }
-}
-
-static gpointer webkitAccessibleParentClass = 0;
-
-static bool isRootObject(AccessibilityObject* coreObject)
-{
- // The root accessible object in WebCore is always an object with
- // the ScrolledArea role with one child with the WebArea role.
- if (!coreObject || !coreObject->isScrollView())
- return false;
-
- AccessibilityObject* firstChild = coreObject->firstChild();
- if (!firstChild || !firstChild->isWebArea())
- return false;
-
- return true;
-}
-
-static AtkObject* atkParentOfRootObject(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
- AccessibilityObject* coreParent = coreObject->parentObjectUnignored();
-
- // The top level object claims to not have a parent. This makes it
- // impossible for assistive technologies to ascend the accessible
- // hierarchy all the way to the application. (Bug 30489)
- if (!coreParent && isRootObject(coreObject)) {
- Document* document = coreObject->document();
- if (!document)
- return 0;
-
-#if PLATFORM(GTK)
- HostWindow* hostWindow = document->view()->hostWindow();
- if (hostWindow) {
- PlatformPageClient scrollView = hostWindow->platformPageClient();
- if (scrollView) {
- GtkWidget* scrollViewParent = gtk_widget_get_parent(scrollView);
- if (scrollViewParent)
- return gtk_widget_get_accessible(scrollViewParent);
- }
- }
-#endif // PLATFORM(GTK)
- }
-
- if (!coreParent)
- return 0;
-
- return coreParent->wrapper();
-}
-
-static AtkObject* webkitAccessibleGetParent(AtkObject* object)
-{
- // Check first if the parent has been already set.
- AtkObject* accessibleParent = ATK_OBJECT_CLASS(webkitAccessibleParentClass)->get_parent(object);
- if (accessibleParent)
- return accessibleParent;
-
- // Parent not set yet, so try to find it in the hierarchy.
- AccessibilityObject* coreObject = core(object);
- if (!coreObject)
- return 0;
-
- AccessibilityObject* coreParent = coreObject->parentObjectUnignored();
-
- if (!coreParent && isRootObject(coreObject))
- return atkParentOfRootObject(object);
-
- if (!coreParent)
- return 0;
-
- // We don't expose table rows to Assistive technologies, but we
- // need to have them anyway in the hierarchy from WebCore to
- // properly perform coordinates calculations when requested.
- if (coreParent->isTableRow() && coreObject->isTableCell())
- coreParent = coreParent->parentObjectUnignored();
-
- return coreParent->wrapper();
-}
-
-static gint getNChildrenForTable(AccessibilityObject* coreObject)
-{
- AccessibilityObject::AccessibilityChildrenVector tableChildren = coreObject->children();
- size_t tableChildrenCount = tableChildren.size();
- size_t cellsCount = 0;
-
- // Look for the actual index of the cell inside the table.
- for (unsigned i = 0; i < tableChildrenCount; ++i) {
- if (tableChildren[i]->isTableRow()) {
- AccessibilityObject::AccessibilityChildrenVector rowChildren = tableChildren[i]->children();
- cellsCount += rowChildren.size();
- } else
- cellsCount++;
- }
-
- return cellsCount;
-}
-
-static gint webkitAccessibleGetNChildren(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
-
- // Tables should be treated in a different way because rows should
- // be bypassed when exposing the accessible hierarchy.
- if (coreObject->isAccessibilityTable())
- return getNChildrenForTable(coreObject);
-
- return coreObject->children().size();
-}
-
-static AccessibilityObject* getChildForTable(AccessibilityObject* coreObject, gint index)
-{
- AccessibilityObject::AccessibilityChildrenVector tableChildren = coreObject->children();
- size_t tableChildrenCount = tableChildren.size();
- size_t cellsCount = 0;
-
- // Look for the actual index of the cell inside the table.
- size_t current = static_cast<size_t>(index);
- for (unsigned i = 0; i < tableChildrenCount; ++i) {
- if (tableChildren[i]->isTableRow()) {
- AccessibilityObject::AccessibilityChildrenVector rowChildren = tableChildren[i]->children();
- size_t rowChildrenCount = rowChildren.size();
- if (current < cellsCount + rowChildrenCount)
- return rowChildren.at(current - cellsCount).get();
- cellsCount += rowChildrenCount;
- } else if (cellsCount == current)
- return tableChildren[i].get();
- else
- cellsCount++;
- }
-
- // Shouldn't reach if the child was found.
- return 0;
-}
-
-static AtkObject* webkitAccessibleRefChild(AtkObject* object, gint index)
-{
- if (index < 0)
- return 0;
-
- AccessibilityObject* coreObject = core(object);
- AccessibilityObject* coreChild = 0;
-
- // Tables are special cases because rows should be bypassed, but
- // still taking their cells into account.
- if (coreObject->isAccessibilityTable())
- coreChild = getChildForTable(coreObject, index);
- else {
- AccessibilityObject::AccessibilityChildrenVector children = coreObject->children();
- if (static_cast<unsigned>(index) >= children.size())
- return 0;
- coreChild = children.at(index).get();
- }
-
- if (!coreChild)
- return 0;
-
- AtkObject* child = coreChild->wrapper();
- atk_object_set_parent(child, object);
- g_object_ref(child);
-
- return child;
-}
-
-static gint getIndexInParentForCellInRow(AccessibilityObject* coreObject)
-{
- AccessibilityObject* parent = coreObject->parentObjectUnignored();
- if (!parent)
- return -1;
-
- AccessibilityObject* grandParent = parent->parentObjectUnignored();
- if (!grandParent)
- return -1;
-
- AccessibilityObject::AccessibilityChildrenVector rows = grandParent->children();
- size_t rowsCount = rows.size();
- size_t previousCellsCount = 0;
-
- // Look for the actual index of the cell inside the table.
- for (unsigned i = 0; i < rowsCount; ++i) {
- if (!rows[i]->isTableRow())
- continue;
-
- AccessibilityObject::AccessibilityChildrenVector cells = rows[i]->children();
- size_t cellsCount = cells.size();
-
- if (rows[i] == parent) {
- for (unsigned j = 0; j < cellsCount; ++j) {
- if (cells[j] == coreObject)
- return previousCellsCount + j;
- }
- }
-
- previousCellsCount += cellsCount;
- }
-
- return -1;
-}
-
-static gint webkitAccessibleGetIndexInParent(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
- AccessibilityObject* parent = coreObject->parentObjectUnignored();
-
- if (!parent && isRootObject(coreObject)) {
- AtkObject* atkParent = atkParentOfRootObject(object);
- if (!atkParent)
- return -1;
-
- unsigned count = atk_object_get_n_accessible_children(atkParent);
- for (unsigned i = 0; i < count; ++i) {
- AtkObject* child = atk_object_ref_accessible_child(atkParent, i);
- bool childIsObject = child == object;
- g_object_unref(child);
- if (childIsObject)
- return i;
- }
- }
-
- // Need to calculate the index of the cell in the table, as
- // rows won't be exposed to assistive technologies.
- if (parent && parent->isTableRow() && coreObject->isTableCell())
- return getIndexInParentForCellInRow(coreObject);
-
- if (!parent)
- return -1;
-
- size_t index = parent->children().find(coreObject);
- return (index == WTF::notFound) ? -1 : index;
-}
-
-static AtkAttributeSet* webkitAccessibleGetAttributes(AtkObject* object)
-{
- AtkAttributeSet* attributeSet = 0;
-#if PLATFORM(GTK)
- attributeSet = addToAtkAttributeSet(attributeSet, "toolkit", "WebKitGtk");
-#endif
-
- AccessibilityObject* coreObject = core(object);
- if (!coreObject)
- return attributeSet;
-
- // Hack needed for WebKit2 tests because obtaining an element by its ID
- // cannot be done from the UIProcess. Assistive technologies have no need
- // for this information.
- Node* node = coreObject->node();
- if (node && node->isElementNode()) {
- String id = toElement(node)->getIdAttribute().string();
- if (!id.isEmpty())
- attributeSet = addToAtkAttributeSet(attributeSet, "html-id", id.utf8().data());
- }
-
- int headingLevel = coreObject->headingLevel();
- if (headingLevel) {
- String value = String::number(headingLevel);
- attributeSet = addToAtkAttributeSet(attributeSet, "level", value.utf8().data());
- }
-
- // Set the 'layout-guess' attribute to help Assistive
- // Technologies know when an exposed table is not data table.
- if (coreObject->isAccessibilityTable() && !coreObject->isDataTable())
- attributeSet = addToAtkAttributeSet(attributeSet, "layout-guess", "true");
-
- String placeholder = coreObject->placeholderValue();
- if (!placeholder.isEmpty())
- attributeSet = addToAtkAttributeSet(attributeSet, "placeholder-text", placeholder.utf8().data());
-
- return attributeSet;
-}
-
-static AtkRole atkRole(AccessibilityRole role)
-{
- switch (role) {
- case UnknownRole:
- return ATK_ROLE_UNKNOWN;
- case ButtonRole:
- return ATK_ROLE_PUSH_BUTTON;
- case ToggleButtonRole:
- return ATK_ROLE_TOGGLE_BUTTON;
- case RadioButtonRole:
- return ATK_ROLE_RADIO_BUTTON;
- case CheckBoxRole:
- return ATK_ROLE_CHECK_BOX;
- case SliderRole:
- return ATK_ROLE_SLIDER;
- case TabGroupRole:
- case TabListRole:
- return ATK_ROLE_PAGE_TAB_LIST;
- case TextFieldRole:
- case TextAreaRole:
- return ATK_ROLE_ENTRY;
- case StaticTextRole:
- return ATK_ROLE_TEXT;
- case OutlineRole:
- return ATK_ROLE_TREE;
- case MenuBarRole:
- return ATK_ROLE_MENU_BAR;
- case MenuListPopupRole:
- case MenuRole:
- return ATK_ROLE_MENU;
- case MenuListOptionRole:
- case MenuItemRole:
- return ATK_ROLE_MENU_ITEM;
- case ColumnRole:
- // return ATK_ROLE_TABLE_COLUMN_HEADER; // Is this right?
- return ATK_ROLE_UNKNOWN; // Matches Mozilla
- case RowRole:
- // return ATK_ROLE_TABLE_ROW_HEADER; // Is this right?
- return ATK_ROLE_LIST_ITEM; // Matches Mozilla
- case ToolbarRole:
- return ATK_ROLE_TOOL_BAR;
- case BusyIndicatorRole:
- return ATK_ROLE_PROGRESS_BAR; // Is this right?
- case ProgressIndicatorRole:
- // return ATK_ROLE_SPIN_BUTTON; // Some confusion about this role in AccessibilityRenderObject.cpp
- return ATK_ROLE_PROGRESS_BAR;
- case WindowRole:
- return ATK_ROLE_WINDOW;
- case PopUpButtonRole:
- case ComboBoxRole:
- return ATK_ROLE_COMBO_BOX;
- case SplitGroupRole:
- return ATK_ROLE_SPLIT_PANE;
- case SplitterRole:
- return ATK_ROLE_UNKNOWN;
- case ColorWellRole:
- return ATK_ROLE_COLOR_CHOOSER;
- case ListRole:
- return ATK_ROLE_LIST;
- case ScrollBarRole:
- return ATK_ROLE_SCROLL_BAR;
- case ScrollAreaRole:
- return ATK_ROLE_SCROLL_PANE;
- case GridRole: // Is this right?
- case TableRole:
- return ATK_ROLE_TABLE;
- case ApplicationRole:
- return ATK_ROLE_APPLICATION;
- case GroupRole:
- case RadioGroupRole:
- case TabPanelRole:
- return ATK_ROLE_PANEL;
- case RowHeaderRole: // Row headers are cells after all.
- case ColumnHeaderRole: // Column headers are cells after all.
- case CellRole:
- return ATK_ROLE_TABLE_CELL;
- case LinkRole:
- case WebCoreLinkRole:
- case ImageMapLinkRole:
- return ATK_ROLE_LINK;
- case ImageMapRole:
- case ImageRole:
- return ATK_ROLE_IMAGE;
- case ListMarkerRole:
- return ATK_ROLE_TEXT;
- case WebAreaRole:
- // return ATK_ROLE_HTML_CONTAINER; // Is this right?
- return ATK_ROLE_DOCUMENT_FRAME;
- case HeadingRole:
- return ATK_ROLE_HEADING;
- case ListBoxRole:
- return ATK_ROLE_LIST;
- case ListItemRole:
- case ListBoxOptionRole:
- return ATK_ROLE_LIST_ITEM;
- case ParagraphRole:
- return ATK_ROLE_PARAGRAPH;
- case LabelRole:
- case LegendRole:
- return ATK_ROLE_LABEL;
- case DivRole:
- return ATK_ROLE_SECTION;
- case FormRole:
- return ATK_ROLE_FORM;
- case CanvasRole:
- return ATK_ROLE_CANVAS;
- case HorizontalRuleRole:
- return ATK_ROLE_SEPARATOR;
- case SpinButtonRole:
- return ATK_ROLE_SPIN_BUTTON;
- case TabRole:
- return ATK_ROLE_PAGE_TAB;
- default:
- return ATK_ROLE_UNKNOWN;
- }
-}
-
-static AtkRole webkitAccessibleGetRole(AtkObject* object)
-{
- AccessibilityObject* coreObject = core(object);
-
- if (!coreObject)
- return ATK_ROLE_UNKNOWN;
-
- // Note: Why doesn't WebCore have a password field for this
- if (coreObject->isPasswordField())
- return ATK_ROLE_PASSWORD_TEXT;
-
- return atkRole(coreObject->roleValue());
-}
-
-static bool isTextWithCaret(AccessibilityObject* coreObject)
-{
- if (!coreObject || !coreObject->isAccessibilityRenderObject())
- return false;
-
- Document* document = coreObject->document();
- if (!document)
- return false;
-
- Frame* frame = document->frame();
- if (!frame)
- return false;
-
- Settings* settings = frame->settings();
- if (!settings || !settings->caretBrowsingEnabled())
- return false;
-
- // Check text objects and paragraphs only.
- AtkObject* axObject = coreObject->wrapper();
- AtkRole role = axObject ? atk_object_get_role(axObject) : ATK_ROLE_INVALID;
- if (role != ATK_ROLE_TEXT && role != ATK_ROLE_PARAGRAPH)
- return false;
-
- // Finally, check whether the caret is set in the current object.
- VisibleSelection selection = coreObject->selection();
- if (!selection.isCaret())
- return false;
-
- return selectionBelongsToObject(coreObject, selection);
-}
-
-static void setAtkStateSetFromCoreObject(AccessibilityObject* coreObject, AtkStateSet* stateSet)
-{
- AccessibilityObject* parent = coreObject->parentObject();
- bool isListBoxOption = parent && parent->isListBox();
-
- // Please keep the state list in alphabetical order
- if (coreObject->isChecked())
- atk_state_set_add_state(stateSet, ATK_STATE_CHECKED);
-
- // FIXME: isReadOnly does not seem to do the right thing for
- // controls, so check explicitly for them. In addition, because
- // isReadOnly is false for listBoxOptions, we need to add one
- // more check so that we do not present them as being "editable".
- if ((!coreObject->isReadOnly()
- || (coreObject->isControl() && coreObject->canSetValueAttribute()))
- && !isListBoxOption)
- atk_state_set_add_state(stateSet, ATK_STATE_EDITABLE);
-
- // FIXME: Put both ENABLED and SENSITIVE together here for now
- if (coreObject->isEnabled()) {
- atk_state_set_add_state(stateSet, ATK_STATE_ENABLED);
- atk_state_set_add_state(stateSet, ATK_STATE_SENSITIVE);
- }
-
- if (coreObject->canSetExpandedAttribute())
- atk_state_set_add_state(stateSet, ATK_STATE_EXPANDABLE);
-
- if (coreObject->isExpanded())
- atk_state_set_add_state(stateSet, ATK_STATE_EXPANDED);
-
- if (coreObject->canSetFocusAttribute())
- atk_state_set_add_state(stateSet, ATK_STATE_FOCUSABLE);
-
- if (coreObject->isFocused() || isTextWithCaret(coreObject))
- atk_state_set_add_state(stateSet, ATK_STATE_FOCUSED);
-
- if (coreObject->orientation() == AccessibilityOrientationHorizontal)
- atk_state_set_add_state(stateSet, ATK_STATE_HORIZONTAL);
- else if (coreObject->orientation() == AccessibilityOrientationVertical)
- atk_state_set_add_state(stateSet, ATK_STATE_VERTICAL);
-
- if (coreObject->isIndeterminate())
- atk_state_set_add_state(stateSet, ATK_STATE_INDETERMINATE);
-
- if (coreObject->isMultiSelectable())
- atk_state_set_add_state(stateSet, ATK_STATE_MULTISELECTABLE);
-
- // TODO: ATK_STATE_OPAQUE
-
- if (coreObject->isPressed())
- atk_state_set_add_state(stateSet, ATK_STATE_PRESSED);
-
- // TODO: ATK_STATE_SELECTABLE_TEXT
-
- if (coreObject->canSetSelectedAttribute()) {
- atk_state_set_add_state(stateSet, ATK_STATE_SELECTABLE);
- // Items in focusable lists have both STATE_SELECT{ABLE,ED}
- // and STATE_FOCUS{ABLE,ED}. We'll fake the latter based on
- // the former.
- if (isListBoxOption)
- atk_state_set_add_state(stateSet, ATK_STATE_FOCUSABLE);
- }
-
- if (coreObject->isSelected()) {
- atk_state_set_add_state(stateSet, ATK_STATE_SELECTED);
- // Items in focusable lists have both STATE_SELECT{ABLE,ED}
- // and STATE_FOCUS{ABLE,ED}. We'll fake the latter based on the
- // former.
- if (isListBoxOption)
- atk_state_set_add_state(stateSet, ATK_STATE_FOCUSED);
- }
-
- // FIXME: Group both SHOWING and VISIBLE here for now
- // Not sure how to handle this in WebKit, see bug
- // http://bugzilla.gnome.org/show_bug.cgi?id=509650 for other
- // issues with SHOWING vs VISIBLE.
- if (!coreObject->isOffScreen()) {
- atk_state_set_add_state(stateSet, ATK_STATE_SHOWING);
- atk_state_set_add_state(stateSet, ATK_STATE_VISIBLE);
- }
-
- // Mutually exclusive, so we group these two
- if (coreObject->roleValue() == TextFieldRole)
- atk_state_set_add_state(stateSet, ATK_STATE_SINGLE_LINE);
- else if (coreObject->roleValue() == TextAreaRole)
- atk_state_set_add_state(stateSet, ATK_STATE_MULTI_LINE);
-
- // TODO: ATK_STATE_SENSITIVE
-
- if (coreObject->isVisited())
- atk_state_set_add_state(stateSet, ATK_STATE_VISITED);
-}
-
-static AtkStateSet* webkitAccessibleRefStateSet(AtkObject* object)
-{
- AtkStateSet* stateSet = ATK_OBJECT_CLASS(webkitAccessibleParentClass)->ref_state_set(object);
- AccessibilityObject* coreObject = core(object);
-
- if (coreObject == fallbackObject()) {
- atk_state_set_add_state(stateSet, ATK_STATE_DEFUNCT);
- return stateSet;
- }
-
- // Text objects must be focusable.
- AtkRole role = atk_object_get_role(object);
- if (role == ATK_ROLE_TEXT || role == ATK_ROLE_PARAGRAPH)
- atk_state_set_add_state(stateSet, ATK_STATE_FOCUSABLE);
-
- setAtkStateSetFromCoreObject(coreObject, stateSet);
- return stateSet;
-}
-
-static AtkRelationSet* webkitAccessibleRefRelationSet(AtkObject* object)
-{
- AtkRelationSet* relationSet = ATK_OBJECT_CLASS(webkitAccessibleParentClass)->ref_relation_set(object);
- AccessibilityObject* coreObject = core(object);
-
- setAtkRelationSetFromCoreObject(coreObject, relationSet);
-
- return relationSet;
-}
-
-static void webkitAccessibleInit(AtkObject* object, gpointer data)
-{
- if (ATK_OBJECT_CLASS(webkitAccessibleParentClass)->initialize)
- ATK_OBJECT_CLASS(webkitAccessibleParentClass)->initialize(object, data);
-
- WebKitAccessible* accessible = WEBKIT_ACCESSIBLE(object);
- accessible->m_object = reinterpret_cast<AccessibilityObject*>(data);
- accessible->priv = WEBKIT_ACCESSIBLE_GET_PRIVATE(accessible);
-}
-
-static void webkitAccessibleFinalize(GObject* object)
-{
- G_OBJECT_CLASS(webkitAccessibleParentClass)->finalize(object);
-}
-
-static void webkitAccessibleClassInit(AtkObjectClass* klass)
-{
- GObjectClass* gobjectClass = G_OBJECT_CLASS(klass);
-
- webkitAccessibleParentClass = g_type_class_peek_parent(klass);
-
- gobjectClass->finalize = webkitAccessibleFinalize;
-
- klass->initialize = webkitAccessibleInit;
- klass->get_name = webkitAccessibleGetName;
- klass->get_description = webkitAccessibleGetDescription;
- klass->get_parent = webkitAccessibleGetParent;
- klass->get_n_children = webkitAccessibleGetNChildren;
- klass->ref_child = webkitAccessibleRefChild;
- klass->get_role = webkitAccessibleGetRole;
- klass->ref_state_set = webkitAccessibleRefStateSet;
- klass->get_index_in_parent = webkitAccessibleGetIndexInParent;
- klass->get_attributes = webkitAccessibleGetAttributes;
- klass->ref_relation_set = webkitAccessibleRefRelationSet;
-
- g_type_class_add_private(klass, sizeof(WebKitAccessiblePrivate));
-}
-
-GType
-webkitAccessibleGetType(void)
-{
- static volatile gsize typeVolatile = 0;
-
- if (g_once_init_enter(&typeVolatile)) {
- static const GTypeInfo tinfo = {
- sizeof(WebKitAccessibleClass),
- (GBaseInitFunc) 0,
- (GBaseFinalizeFunc) 0,
- (GClassInitFunc) webkitAccessibleClassInit,
- (GClassFinalizeFunc) 0,
- 0, /* class data */
- sizeof(WebKitAccessible), /* instance size */
- 0, /* nb preallocs */
- (GInstanceInitFunc) 0,
- 0 /* value table */
- };
-
- GType type = g_type_register_static(ATK_TYPE_OBJECT, "WebKitAccessible", &tinfo, GTypeFlags(0));
- g_once_init_leave(&typeVolatile, type);
- }
-
- return typeVolatile;
-}
-
-static const GInterfaceInfo AtkInterfacesInitFunctions[] = {
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleActionInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleSelectionInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleEditableTextInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleTextInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleComponentInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleImageInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleTableInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleHypertextInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleHyperlinkImplInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleDocumentInterfaceInit), 0, 0},
- {reinterpret_cast<GInterfaceInitFunc>(webkitAccessibleValueInterfaceInit), 0, 0}
-};
-
-enum WAIType {
- WAI_ACTION,
- WAI_SELECTION,
- WAI_EDITABLE_TEXT,
- WAI_TEXT,
- WAI_COMPONENT,
- WAI_IMAGE,
- WAI_TABLE,
- WAI_HYPERTEXT,
- WAI_HYPERLINK,
- WAI_DOCUMENT,
- WAI_VALUE,
-};
-
-static GType GetAtkInterfaceTypeFromWAIType(WAIType type)
-{
- switch (type) {
- case WAI_ACTION:
- return ATK_TYPE_ACTION;
- case WAI_SELECTION:
- return ATK_TYPE_SELECTION;
- case WAI_EDITABLE_TEXT:
- return ATK_TYPE_EDITABLE_TEXT;
- case WAI_TEXT:
- return ATK_TYPE_TEXT;
- case WAI_COMPONENT:
- return ATK_TYPE_COMPONENT;
- case WAI_IMAGE:
- return ATK_TYPE_IMAGE;
- case WAI_TABLE:
- return ATK_TYPE_TABLE;
- case WAI_HYPERTEXT:
- return ATK_TYPE_HYPERTEXT;
- case WAI_HYPERLINK:
- return ATK_TYPE_HYPERLINK_IMPL;
- case WAI_DOCUMENT:
- return ATK_TYPE_DOCUMENT;
- case WAI_VALUE:
- return ATK_TYPE_VALUE;
- }
-
- return G_TYPE_INVALID;
-}
-
-static bool roleIsTextType(AccessibilityRole role)
-{
- return role == ParagraphRole || role == HeadingRole || role == DivRole || role == CellRole || role == ListItemRole;
-}
-
-static guint16 getInterfaceMaskFromObject(AccessibilityObject* coreObject)
-{
- guint16 interfaceMask = 0;
-
- // Component interface is always supported
- interfaceMask |= 1 << WAI_COMPONENT;
-
- AccessibilityRole role = coreObject->roleValue();
-
- // Action
- // As the implementation of the AtkAction interface is a very
- // basic one (just relays in executing the default action for each
- // object, and only supports having one action per object), it is
- // better just to implement this interface for every instance of
- // the WebKitAccessible class and let WebCore decide what to do.
- interfaceMask |= 1 << WAI_ACTION;
-
- // Selection
- if (coreObject->isListBox() || coreObject->isMenuList())
- interfaceMask |= 1 << WAI_SELECTION;
-
- // Get renderer if available.
- RenderObject* renderer = 0;
- if (coreObject->isAccessibilityRenderObject())
- renderer = coreObject->renderer();
-
- // Hyperlink (links and embedded objects).
- if (coreObject->isLink() || (renderer && renderer->isReplaced()))
- interfaceMask |= 1 << WAI_HYPERLINK;
-
- // Text & Editable Text
- if (role == StaticTextRole || coreObject->isMenuListOption())
- interfaceMask |= 1 << WAI_TEXT;
- else {
- if (coreObject->isTextControl()) {
- interfaceMask |= 1 << WAI_TEXT;
- if (!coreObject->isReadOnly())
- interfaceMask |= 1 << WAI_EDITABLE_TEXT;
- } else {
- if (role != TableRole) {
- interfaceMask |= 1 << WAI_HYPERTEXT;
- if ((renderer && renderer->childrenInline()) || roleIsTextType(role))
- interfaceMask |= 1 << WAI_TEXT;
- }
-
- // Add the TEXT interface for list items whose
- // first accessible child has a text renderer
- if (role == ListItemRole) {
- AccessibilityObject::AccessibilityChildrenVector children = coreObject->children();
- if (children.size()) {
- AccessibilityObject* axRenderChild = children.at(0).get();
- interfaceMask |= getInterfaceMaskFromObject(axRenderChild);
- }
- }
- }
- }
-
- // Image
- if (coreObject->isImage())
- interfaceMask |= 1 << WAI_IMAGE;
-
- // Table
- if (role == TableRole)
- interfaceMask |= 1 << WAI_TABLE;
-
- // Document
- if (role == WebAreaRole)
- interfaceMask |= 1 << WAI_DOCUMENT;
-
- // Value
- if (role == SliderRole || role == SpinButtonRole || role == ScrollBarRole)
- interfaceMask |= 1 << WAI_VALUE;
-
- return interfaceMask;
-}
-
-static const char* getUniqueAccessibilityTypeName(guint16 interfaceMask)
-{
-#define WAI_TYPE_NAME_LEN (30) /* Enough for prefix + 5 hex characters (max) */
- static char name[WAI_TYPE_NAME_LEN + 1];
-
- g_sprintf(name, "WAIType%x", interfaceMask);
- name[WAI_TYPE_NAME_LEN] = '\0';
-
- return name;
-}
-
-static GType getAccessibilityTypeFromObject(AccessibilityObject* coreObject)
-{
- static const GTypeInfo typeInfo = {
- sizeof(WebKitAccessibleClass),
- (GBaseInitFunc) 0,
- (GBaseFinalizeFunc) 0,
- (GClassInitFunc) 0,
- (GClassFinalizeFunc) 0,
- 0, /* class data */
- sizeof(WebKitAccessible), /* instance size */
- 0, /* nb preallocs */
- (GInstanceInitFunc) 0,
- 0 /* value table */
- };
-
- guint16 interfaceMask = getInterfaceMaskFromObject(coreObject);
- const char* atkTypeName = getUniqueAccessibilityTypeName(interfaceMask);
- GType type = g_type_from_name(atkTypeName);
- if (type)
- return type;
-
- type = g_type_register_static(WEBKIT_TYPE_ACCESSIBLE, atkTypeName, &typeInfo, GTypeFlags(0));
- for (guint i = 0; i < G_N_ELEMENTS(AtkInterfacesInitFunctions); i++) {
- if (interfaceMask & (1 << i))
- g_type_add_interface_static(type,
- GetAtkInterfaceTypeFromWAIType(static_cast<WAIType>(i)),
- &AtkInterfacesInitFunctions[i]);
- }
-
- return type;
-}
-
-WebKitAccessible* webkitAccessibleNew(AccessibilityObject* coreObject)
-{
- GType type = getAccessibilityTypeFromObject(coreObject);
- AtkObject* object = static_cast<AtkObject*>(g_object_new(type, 0));
-
- atk_object_initialize(object, coreObject);
-
- return WEBKIT_ACCESSIBLE(object);
-}
-
-AccessibilityObject* webkitAccessibleGetAccessibilityObject(WebKitAccessible* accessible)
-{
- return accessible->m_object;
-}
-
-void webkitAccessibleDetach(WebKitAccessible* accessible)
-{
- ASSERT(accessible->m_object);
-
- if (core(accessible)->roleValue() == WebAreaRole)
- g_signal_emit_by_name(accessible, "state-change", "defunct", true);
-
- // We replace the WebCore AccessibilityObject with a fallback object that
- // provides default implementations to avoid repetitive null-checking after
- // detachment.
- accessible->m_object = fallbackObject();
-}
-
-AtkObject* webkitAccessibleGetFocusedElement(WebKitAccessible* accessible)
-{
- if (!accessible->m_object)
- return 0;
-
- RefPtr<AccessibilityObject> focusedObj = accessible->m_object->focusedUIElement();
- if (!focusedObj)
- return 0;
-
- return focusedObj->wrapper();
-}
-
-AccessibilityObject* objectFocusedAndCaretOffsetUnignored(AccessibilityObject* referenceObject, int& offset)
-{
- // Indication that something bogus has transpired.
- offset = -1;
-
- Document* document = referenceObject->document();
- if (!document)
- return 0;
-
- Node* focusedNode = referenceObject->selection().end().containerNode();
- if (!focusedNode)
- return 0;
-
- RenderObject* focusedRenderer = focusedNode->renderer();
- if (!focusedRenderer)
- return 0;
-
- AccessibilityObject* focusedObject = document->axObjectCache()->getOrCreate(focusedRenderer);
- if (!focusedObject)
- return 0;
-
- // Look for the actual (not ignoring accessibility) selected object.
- AccessibilityObject* firstUnignoredParent = focusedObject;
- if (firstUnignoredParent->accessibilityIsIgnored())
- firstUnignoredParent = firstUnignoredParent->parentObjectUnignored();
- if (!firstUnignoredParent)
- return 0;
-
- // Don't ignore links if the offset is being requested for a link.
- if (!referenceObject->isLink() && firstUnignoredParent->isLink())
- firstUnignoredParent = firstUnignoredParent->parentObjectUnignored();
- if (!firstUnignoredParent)
- return 0;
-
- // The reference object must either coincide with the focused
- // object being considered, or be a descendant of it.
- if (referenceObject->isDescendantOfObject(firstUnignoredParent))
- referenceObject = firstUnignoredParent;
-
- Node* startNode = 0;
- if (firstUnignoredParent != referenceObject || firstUnignoredParent->isTextControl()) {
- // We need to use the first child's node of the reference
- // object as the start point to calculate the caret offset
- // because we want it to be relative to the object of
- // reference, not just to the focused object (which could have
- // previous siblings which should be taken into account too).
- AccessibilityObject* axFirstChild = referenceObject->firstChild();
- if (axFirstChild)
- startNode = axFirstChild->node();
- }
- // Getting the Position of a PseudoElement now triggers an assertion.
- // This can occur when clicking on empty space in a render block.
- if (!startNode || startNode->isPseudoElement())
- startNode = firstUnignoredParent->node();
-
- // Check if the node for the first parent object not ignoring
- // accessibility is null again before using it. This might happen
- // with certain kind of accessibility objects, such as the root
- // one (the scroller containing the webArea object).
- if (!startNode)
- return 0;
-
- VisiblePosition startPosition = VisiblePosition(positionBeforeNode(startNode), DOWNSTREAM);
- VisiblePosition endPosition = firstUnignoredParent->selection().visibleEnd();
-
- if (startPosition == endPosition)
- offset = 0;
- else if (!isStartOfLine(endPosition)) {
- RefPtr<Range> range = makeRange(startPosition, endPosition.previous());
- offset = TextIterator::rangeLength(range.get(), true) + 1;
- } else {
- RefPtr<Range> range = makeRange(startPosition, endPosition);
- offset = TextIterator::rangeLength(range.get(), true);
- }
-
- return firstUnignoredParent;
-}
-
-const char* cacheAndReturnAtkProperty(AtkObject* object, AtkCachedProperty property, String value)
-{
- WebKitAccessiblePrivate* priv = WEBKIT_ACCESSIBLE(object)->priv;
- CString* propertyPtr = 0;
-
- switch (property) {
- case AtkCachedAccessibleName:
- propertyPtr = &priv->accessibleName;
- break;
-
- case AtkCachedAccessibleDescription:
- propertyPtr = &priv->accessibleDescription;
- break;
-
- case AtkCachedActionName:
- propertyPtr = &priv->actionName;
- break;
-
- case AtkCachedActionKeyBinding:
- propertyPtr = &priv->actionKeyBinding;
- break;
-
- case AtkCachedDocumentLocale:
- propertyPtr = &priv->documentLocale;
- break;
-
- case AtkCachedDocumentType:
- propertyPtr = &priv->documentType;
- break;
-
- case AtkCachedDocumentEncoding:
- propertyPtr = &priv->documentEncoding;
- break;
-
- case AtkCachedDocumentURI:
- propertyPtr = &priv->documentURI;
- break;
-
- case AtkCachedImageDescription:
- propertyPtr = &priv->imageDescription;
- break;
-
- default:
- ASSERT_NOT_REACHED();
- }
-
- // Don't invalidate old memory if not stricly needed, since other
- // callers might be still holding on to it.
- if (*propertyPtr != value.utf8())
- *propertyPtr = value.utf8();
-
- return (*propertyPtr).data();
-}
-
-#endif // HAVE(ACCESSIBILITY)
« no previous file with comments | « Source/WebCore/accessibility/atk/WebKitAccessibleWrapperAtk.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698