Commit 784612d0 authored by jhoneycutt@apple.com's avatar jhoneycutt@apple.com

WebCore:

2009-08-13  Jon Honeycutt  <jhoneycutt@apple.com>

        Part of <rdar://problem/6218721> No MSAA focus events fired for Webkit
        nightly (20866)

        https://bugs.webkit.org/show_bug.cgi?id=20866

        Reviewed by Oliver Hunt.

        * accessibility/AXObjectCache.cpp:
        (WebCore::AXObjectCache::AXObjectCache):
        Changed to take a pointer to its owner document. This is used by
        AXObjectCache::handleFocusedUIElementChanged().
        (WebCore::AXObjectCache::focusedUIElementForPage):
        Code moved from AccessibilityRenderObject::focusedUIElement(). Modified
        to be a static function and to take a pointer to a Page.
        (WebCore::AXObjectCache::platformGenerateAXID):
        Moved the code to generate the next AXID from getAXID() to here. Added
        a #if to make this non-WIN only, because Windows has its own
        implementation.
        (WebCore::AXObjectCache::getAXID):
        Ensure that we generate a positive AXID, ranging from 1 to LONG_MAX.

        * accessibility/AXObjectCache.h:
        Add a declaration for Document and Page. Removed the declaration of
        AccessibilityObject, because we include the header. Reordered the
        declaration of Node alphabetically. Moved the typedef for AXID to
        AccessibilityObject. Removed some trailing whitespace. Added a member
        variable to hold a pointer to the owner Document.
        (WebCore::AXObjectCache::AXObjectCache):
        Changed to take a pointer to its owner Document.
        (WebCore::AXObjectCache::focusedUIElementForPage):
        Added; code moved from AccessiblityRenderObject::focusedUIElement().
        Returns the focused element with respect to accessibility.
        (WebCore::AXObjectCache::platformGenerateAXID):
        Declare a function to generate an AXID.
        (WebCore::AXObjectCache::objectFromAXID):
        Return the AccessibilityObject with the given AXID.

        * accessibility/AccessibilityObject.h:
        Moved the typedef for AXID from AXObjectCache to here. Made the m_id
        member use the typedef.
        (WebCore::AccessibilityObject::axObjectID):
        Changed the return type to use the typedef.
        (WebCore::AccessibilityObject::setAXObjectID):
        Changed the argument type to use the typedef.

        * accessibility/AccessibilityRenderObject.cpp:
        Removed some unneeded #includes.
        (WebCore::AccessibilityRenderObject::focusedUIElement):
        Moved the code to AXObjectCache::focusedUIElementForPage(), which we now
        call.

        * accessibility/win/AXObjectCacheWin.cpp:
        (WebCore::AXObjectCache::platformGenerateAXID):
        Ensure that we generate an AXID that is in the range 1 to LONG_MAX.
        (WebCore::AXObjectCache::handleFocusedUIElementChanged):
        If the Document has no Page, return. If the Page has not focused
        element (respecting accessibility), return. Assert that the
        accessibility of the focused element is not ignored, and that the
        object's AXID will be negative and fit into a LONG when negated.
        Broadcast a focus event for the object.

        * dom/Document.cpp:
        (WebCore::Document::axObjectCache):
        Pass this when creating the AXObjectCache.
        (WebCore::Document::setFocusedNode):
        Call AXObjectCache::handleFocusedUIElementChanged() on Windows.

WebKit/win:

2009-08-13  Jon Honeycutt  <jhoneycutt@apple.com>

        Part of <rdar://problem/6218721> No MSAA focus events fired for Webkit
        nightly (20866)

        https://bugs.webkit.org/show_bug.cgi?id=20866

        Reviewed by Oliver Hunt.

        * AccessibleBase.cpp:
        (AccessibleBase::getAccessibilityObjectForChild):
        If the child ID is negative, negate it and treat it as an AXID.

git-svn-id: http://svn.webkit.org/repository/webkit/trunk@47311 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent 2e861b43
2009-08-13 Jon Honeycutt <jhoneycutt@apple.com>
Part of <rdar://problem/6218721> No MSAA focus events fired for Webkit
nightly (20866)
https://bugs.webkit.org/show_bug.cgi?id=20866
Reviewed by Oliver Hunt.
* accessibility/AXObjectCache.cpp:
(WebCore::AXObjectCache::AXObjectCache):
Changed to take a pointer to its owner document. This is used by
AXObjectCache::handleFocusedUIElementChanged().
(WebCore::AXObjectCache::focusedUIElementForPage):
Code moved from AccessibilityRenderObject::focusedUIElement(). Modified
to be a static function and to take a pointer to a Page.
(WebCore::AXObjectCache::platformGenerateAXID):
Moved the code to generate the next AXID from getAXID() to here. Added
a #if to make this non-WIN only, because Windows has its own
implementation.
(WebCore::AXObjectCache::getAXID):
Ensure that we generate a positive AXID, ranging from 1 to LONG_MAX.
* accessibility/AXObjectCache.h:
Add a declaration for Document and Page. Removed the declaration of
AccessibilityObject, because we include the header. Reordered the
declaration of Node alphabetically. Moved the typedef for AXID to
AccessibilityObject. Removed some trailing whitespace. Added a member
variable to hold a pointer to the owner Document.
(WebCore::AXObjectCache::AXObjectCache):
Changed to take a pointer to its owner Document.
(WebCore::AXObjectCache::focusedUIElementForPage):
Added; code moved from AccessiblityRenderObject::focusedUIElement().
Returns the focused element with respect to accessibility.
(WebCore::AXObjectCache::platformGenerateAXID):
Declare a function to generate an AXID.
(WebCore::AXObjectCache::objectFromAXID):
Return the AccessibilityObject with the given AXID.
* accessibility/AccessibilityObject.h:
Moved the typedef for AXID from AXObjectCache to here. Made the m_id
member use the typedef.
(WebCore::AccessibilityObject::axObjectID):
Changed the return type to use the typedef.
(WebCore::AccessibilityObject::setAXObjectID):
Changed the argument type to use the typedef.
* accessibility/AccessibilityRenderObject.cpp:
Removed some unneeded #includes.
(WebCore::AccessibilityRenderObject::focusedUIElement):
Moved the code to AXObjectCache::focusedUIElementForPage(), which we now
call.
* accessibility/win/AXObjectCacheWin.cpp:
(WebCore::AXObjectCache::platformGenerateAXID):
Ensure that we generate an AXID that is in the range 1 to LONG_MAX.
(WebCore::AXObjectCache::handleFocusedUIElementChanged):
If the Document has no Page, return. If the Page has not focused
element (respecting accessibility), return. Assert that the
accessibility of the focused element is not ignored, and that the
object's AXID will be negative and fit into a LONG when negated.
Broadcast a focus event for the object.
* dom/Document.cpp:
(WebCore::Document::axObjectCache):
Pass this when creating the AXObjectCache.
(WebCore::Document::setFocusedNode):
Call AXObjectCache::handleFocusedUIElementChanged() on Windows.
2009-08-14 Jiahua Huang <jhuangjiahua@gmail.com>
Reviewed by Jan Alonzo.
......@@ -43,8 +43,11 @@
#include "AccessibilityTableColumn.h"
#include "AccessibilityTableHeaderContainer.h"
#include "AccessibilityTableRow.h"
#include "InputElement.h"
#include "FocusController.h"
#include "Frame.h"
#include "HTMLNames.h"
#include "InputElement.h"
#include "Page.h"
#include "RenderObject.h"
#include "RenderView.h"
......@@ -57,8 +60,9 @@ using namespace HTMLNames;
bool AXObjectCache::gAccessibilityEnabled = false;
bool AXObjectCache::gAccessibilityEnhancedUserInterfaceEnabled = false;
AXObjectCache::AXObjectCache()
AXObjectCache::AXObjectCache(const Document* document)
: m_notificationPostTimer(this, &AXObjectCache::notificationPostTimerFired)
, m_document(document)
{
}
......@@ -73,6 +77,32 @@ AXObjectCache::~AXObjectCache()
}
}
AccessibilityObject* AXObjectCache::focusedUIElementForPage(const Page* page)
{
// get the focused node in the page
Document* focusedDocument = page->focusController()->focusedOrMainFrame()->document();
Node* focusedNode = focusedDocument->focusedNode();
if (!focusedNode)
focusedNode = focusedDocument;
RenderObject* focusedNodeRenderer = focusedNode->renderer();
if (!focusedNodeRenderer)
return 0;
AccessibilityObject* obj = focusedNodeRenderer->document()->axObjectCache()->getOrCreate(focusedNodeRenderer);
if (obj->shouldFocusActiveDescendant()) {
if (AccessibilityObject* descendant = obj->activeDescendant())
obj = descendant;
}
// the HTML element, for example, is focusable but has an AX object that is ignored
if (obj->accessibilityIsIgnored())
obj = obj->parentObjectUnignored();
return obj;
}
AccessibilityObject* AXObjectCache::get(RenderObject* renderer)
{
if (!renderer)
......@@ -213,6 +243,23 @@ void AXObjectCache::remove(RenderObject* renderer)
m_renderObjectMapping.remove(renderer);
}
#if !PLATFORM(WIN)
AXID AXObjectCache::platformGenerateAXID() const
{
static AXID lastUsedID = 0;
// Generate a new ID.
AXID objID = lastUsedID;
do {
++objID;
} while (objID == 0 || HashTraits<AXID>::isDeletedValue(objID) || m_idsInUse.contains(objID));
lastUsedID = objID;
return objID;
}
#endif
AXID AXObjectCache::getAXID(AccessibilityObject* obj)
{
// check for already-assigned ID
......@@ -221,15 +268,10 @@ AXID AXObjectCache::getAXID(AccessibilityObject* obj)
ASSERT(m_idsInUse.contains(objID));
return objID;
}
// generate a new ID
static AXID lastUsedID = 0;
objID = lastUsedID;
do
++objID;
while (objID == 0 || HashTraits<AXID>::isDeletedValue(objID) || m_idsInUse.contains(objID));
objID = platformGenerateAXID();
m_idsInUse.add(objID);
lastUsedID = objID;
obj->setAXObjectID(objID);
return objID;
......
......@@ -42,13 +42,12 @@ class WebCoreTextMarker;
namespace WebCore {
class Document;
class Node;
class Page;
class RenderObject;
class String;
class VisiblePosition;
class AccessibilityObject;
class Node;
typedef unsigned AXID;
struct TextMarkerData {
AXID axID;
......@@ -59,9 +58,11 @@ namespace WebCore {
class AXObjectCache {
public:
AXObjectCache();
AXObjectCache(const Document*);
~AXObjectCache();
static AccessibilityObject* focusedUIElementForPage(const Page*);
// to be used with render objects
AccessibilityObject* getOrCreate(RenderObject*);
......@@ -94,11 +95,13 @@ namespace WebCore {
void removeAXID(AccessibilityObject*);
bool isIDinUse(AXID id) const { return m_idsInUse.contains(id); }
AXID platformGenerateAXID() const;
AccessibilityObject* objectFromAXID(AXID id) const { return m_objects.get(id).get(); }
// Text marker utilities.
static void textMarkerDataForVisiblePosition(TextMarkerData&, const VisiblePosition&);
static VisiblePosition visiblePositionForTextMarkerData(TextMarkerData&);
private:
HashMap<AXID, RefPtr<AccessibilityObject> > m_objects;
HashMap<RenderObject*, AXID> m_renderObjectMapping;
......@@ -113,6 +116,8 @@ namespace WebCore {
AXID getAXID(AccessibilityObject*);
bool nodeIsAriaType(Node* node, String role);
const Document* m_document;
};
#if !HAVE(ACCESSIBILITY)
......
......@@ -91,6 +91,8 @@ class VisibleSelection;
class String;
class Widget;
typedef unsigned AXID;
enum AccessibilityRole {
UnknownRole = 1,
ButtonRole,
......@@ -305,8 +307,8 @@ public:
virtual PassRefPtr<Range> ariaSelectedTextDOMRange() const { return 0; }
virtual AXObjectCache* axObjectCache() const { return 0; }
unsigned axObjectID() const { return m_id; }
void setAXObjectID(unsigned axObjectID) { m_id = axObjectID; }
AXID axObjectID() const { return m_id; }
void setAXObjectID(AXID axObjectID) { m_id = axObjectID; }
static AccessibilityObject* anchorElementForNode(Node*);
virtual Element* anchorElement() const { return 0; }
......@@ -438,7 +440,7 @@ public:
virtual void updateBackingStore() { }
protected:
unsigned m_id;
AXID m_id;
AccessibilityChildrenVector m_children;
mutable bool m_haveChildren;
AccessibilityRole m_role;
......
......@@ -35,7 +35,6 @@
#include "CharacterNames.h"
#include "EventNames.h"
#include "FloatRect.h"
#include "FocusController.h"
#include "Frame.h"
#include "FrameLoader.h"
#include "HTMLAreaElement.h"
......@@ -54,7 +53,6 @@
#include "HitTestResult.h"
#include "LocalizedStrings.h"
#include "NodeList.h"
#include "Page.h"
#include "RenderButton.h"
#include "RenderFieldset.h"
#include "RenderFileUploadControl.h"
......@@ -2102,32 +2100,11 @@ AccessibilityObject* AccessibilityRenderObject::doAccessibilityHitTest(const Int
AccessibilityObject* AccessibilityRenderObject::focusedUIElement() const
{
// get the focused node in the page
Page* page = m_renderer->document()->page();
if (!page)
return 0;
Document* focusedDocument = page->focusController()->focusedOrMainFrame()->document();
Node* focusedNode = focusedDocument->focusedNode();
if (!focusedNode)
focusedNode = focusedDocument;
RenderObject* focusedNodeRenderer = focusedNode->renderer();
if (!focusedNodeRenderer)
return 0;
AccessibilityObject* obj = focusedNodeRenderer->document()->axObjectCache()->getOrCreate(focusedNodeRenderer);
if (obj->shouldFocusActiveDescendant()) {
if (AccessibilityObject* descendant = obj->activeDescendant())
obj = descendant;
}
// the HTML element, for example, is focusable but has an AX object that is ignored
if (obj->accessibilityIsIgnored())
obj = obj->parentObjectUnignored();
return obj;
return AXObjectCache::focusedUIElementForPage(page);
}
bool AccessibilityRenderObject::shouldFocusActiveDescendant() const
......
......@@ -28,6 +28,10 @@
#include "AXObjectCache.h"
#include "AccessibilityObject.h"
#include "Document.h"
#include "Page.h"
using namespace std;
namespace WebCore {
......@@ -50,8 +54,43 @@ void AXObjectCache::postPlatformNotification(AccessibilityObject*, const String&
{
}
AXID AXObjectCache::platformGenerateAXID() const
{
static AXID lastUsedID = 0;
// Generate a new ID. Windows accessibility relies on a positive AXID,
// ranging from 1 to LONG_MAX.
AXID objID = lastUsedID;
do {
++objID;
objID %= std::numeric_limits<LONG>::max();
} while (objID == 0 || HashTraits<AXID>::isDeletedValue(objID) || m_idsInUse.contains(objID));
ASSERT(objID >= 1 && objID <= std::numeric_limits<LONG>::max());
lastUsedID = objID;
return objID;
}
void AXObjectCache::handleFocusedUIElementChanged()
{
Page* page = m_document->page();
if (!page || !page->chrome()->platformWindow())
return;
AccessibilityObject* focusedObject = focusedUIElementForPage(page);
if (!focusedObject)
return;
ASSERT(!focusedObject->accessibilityIsIgnored());
ASSERT(focusedObject->axObjectID() >= 1 && focusedObject->axObjectID() <= numeric_limits<LONG>::max());
// Windows will end up calling get_accChild() on the root accessible
// object for the WebView, passing the child ID that we specify below. We
// negate the AXID so we know that the caller is passing the ID of an
// element, not the index of a child element.
NotifyWinEvent(EVENT_OBJECT_FOCUS, page->chrome()->platformWindow(), OBJID_CLIENT, -static_cast<LONG>(focusedObject->axObjectID()));
}
} // namespace WebCore
......@@ -1467,7 +1467,7 @@ AXObjectCache* Document::axObjectCache() const
return doc->axObjectCache();
// this is the top-level document, so install a new cache
m_axObjectCache = new AXObjectCache;
m_axObjectCache = new AXObjectCache(this);
return m_axObjectCache;
}
......@@ -2622,7 +2622,7 @@ bool Document::setFocusedNode(PassRefPtr<Node> newFocusedNode)
}
}
#if PLATFORM(MAC) && !PLATFORM(CHROMIUM)
#if (PLATFORM(MAC) || PLATFORM(WIN)) && !PLATFORM(CHROMIUM)
if (!focusChangeBlocked && m_focusedNode && AXObjectCache::accessibilityEnabled())
axObjectCache()->handleFocusedUIElementChanged();
#elif PLATFORM(GTK)
......
......@@ -592,7 +592,15 @@ HRESULT AccessibleBase::getAccessibilityObjectForChild(VARIANT vChild, Accessibi
if (vChild.lVal == CHILDID_SELF)
childObj = m_object;
else {
else if (vChild.lVal < 0) {
// When broadcasting MSAA events, we negate the AXID and pass it as the
// child ID.
Document* document = m_object->document();
if (!document)
return E_FAIL;
childObj = document->axObjectCache()->objectFromAXID(-vChild.lVal);
} else {
size_t childIndex = static_cast<size_t>(vChild.lVal - 1);
if (childIndex >= m_object->children().size())
......
2009-08-13 Jon Honeycutt <jhoneycutt@apple.com>
Part of <rdar://problem/6218721> No MSAA focus events fired for Webkit
nightly (20866)
https://bugs.webkit.org/show_bug.cgi?id=20866
Reviewed by Oliver Hunt.
* AccessibleBase.cpp:
(AccessibleBase::getAccessibilityObjectForChild):
If the child ID is negative, negate it and treat it as an AXID.
2009-08-12 Brian Weinstein <bweinstein@apple.com>
Reviewed by Adam Roben.
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment