Bug 278034. Reconstruct both HTML and XUL combobox accessibles

This commit is contained in:
aaronleventhal%moonset.net 2007-01-11 20:07:36 +00:00
Родитель 821f6c70bc
Коммит 57bf2986f3
11 изменённых файлов: 273 добавлений и 382 удалений

Просмотреть файл

@ -45,7 +45,7 @@ interface nsIFrame;
interface nsObjectFrame;
interface nsIContent;
[scriptable, uuid(7b2dc92f-bd14-4f0c-bdff-1caa0621fea5)]
[scriptable, uuid(e4cdb7c5-d029-4bee-bff5-99455c6e0057)]
interface nsIAccessibilityService : nsIAccessibleRetrieval
{
nsIAccessible createOuterDocAccessible(in nsIDOMNode aNode);
@ -75,10 +75,6 @@ interface nsIAccessibilityService : nsIAccessibleRetrieval
nsIAccessible createHTMLTextAccessible(in nsISupports aFrame);
nsIAccessible createHTMLTextFieldAccessible(in nsISupports aFrame);
// XXX: It seems these methods aren't used.
nsIAccessible createXULSelectOptionAccessible(in nsIDOMNode aNode);
nsIAccessible createXULSelectListAccessible(in nsIDOMNode aNode);
[noscript] nsIAccessible getAccessible(in nsIDOMNode aNode, in nsIPresShell aPresShell,
in nsIWeakReference aWeakShell,
inout nsIFrame frameHint, out boolean aIsHidden);

Просмотреть файл

@ -488,7 +488,9 @@ interface nsIAccessible : nsISupports
const unsigned long ROLE_APP_ROOT = 111;
const unsigned long ROLE_PARENT_MENUITEM = 112;
const unsigned long ROLE_CALENDAR = 113;
const unsigned long ROLE_LAST_ENTRY = 114; // Important -- helps ensure nsRoleMap's are synchronized
const unsigned long ROLE_COMBOBOX_LIST = 114;
const unsigned long ROLE_COMBOBOX_LISTITEM = 115;
const unsigned long ROLE_LAST_ENTRY = 116; // Important -- helps ensure nsRoleMap's are synchronized
// MSAA relationship extensions to accNavigate
const unsigned long NAVRELATION_CONTROLLED_BY = 0x1000;

Просмотреть файл

@ -160,6 +160,8 @@ PRUint32 atkRoleMap[] = {
ATK_ROLE_APPLICATION, // nsIAccessible::ROLE_APP_ROOT 111
ATK_ROLE_MENU, // nsIAccessible::ROLE_PARENT_MENUITEM 112
ATK_ROLE_CALENDAR, // nsIAccessible::ROLE_CALENDAR 113
ATK_ROLE_MENU, // nsIAccessible::ROLE_COMBOBOX_LIST 114
ATK_ROLE_MENU_ITEM, // nsIAccessible::ROLE_COMBOBOX_LISTITEM 115
kROLE_ATK_LAST_ENTRY // nsIAccessible::ROLE_LAST_ENTRY
};

Просмотреть файл

@ -893,42 +893,6 @@ nsAccessibilityService::CreateHTMLBRAccessible(nsISupports *aFrame, nsIAccessibl
return NS_OK;
}
NS_IMETHODIMP
nsAccessibilityService::CreateXULSelectListAccessible(nsIDOMNode *aNode, nsIAccessible **_retval)
{
#ifdef MOZ_XUL
nsCOMPtr<nsIWeakReference> weakShell;
GetShellFromNode(aNode, getter_AddRefs(weakShell));
*_retval = new nsXULSelectListAccessible(aNode, weakShell);
if (! *_retval)
return NS_ERROR_OUT_OF_MEMORY;
NS_ADDREF(*_retval);
#else
*_retval = nsnull;
#endif // MOZ_XUL
return NS_OK;
}
NS_IMETHODIMP
nsAccessibilityService::CreateXULSelectOptionAccessible(nsIDOMNode *aNode, nsIAccessible **_retval)
{
#ifdef MOZ_XUL
nsCOMPtr<nsIWeakReference> weakShell;
GetShellFromNode(aNode, getter_AddRefs(weakShell));
*_retval = new nsXULSelectOptionAccessible(aNode, weakShell);
if (! *_retval)
return NS_ERROR_OUT_OF_MEMORY;
NS_ADDREF(*_retval);
#else
*_retval = nsnull;
#endif // MOZ_XUL
return NS_OK;
}
NS_IMETHODIMP nsAccessibilityService::GetCachedAccessible(nsIDOMNode *aNode,
nsIWeakReference *aWeakShell,
nsIAccessible **aAccessible)

Просмотреть файл

@ -61,12 +61,17 @@
*
* Comboboxes:
* - nsHTMLComboboxAccessible
* - nsHTMLComboboxTextFieldAccessible
* - nsHTMLComboboxButtonAccessible
* - nsHTMLComboboxListAccessible [ inserted in accessible tree ]
* - nsHTMLComboboxTextFieldAccessible (#ifdef COMBO_BOX_WITH_THREE_CHILDREN)
* - nsHTMLComboboxButtonAccessible (#ifdef COMBO_BOX_WITH_THREE_CHILDREN)
* - nsHTMLComboboxListAccessible [ inserted in accessible tree ]
* - nsHTMLSelectOptionAccessible(s)
*
* XXX COMBO_BOX_WITH_THREE_CHILDREN is not currently defined.
* If we start using it again, we should pass the correct frame into those accessibles.
* They share a DOM node with the parent combobox.
*/
/** ------------------------------------------------------ */
/** Impl. of nsHTMLSelectableAccessible */
/** ------------------------------------------------------ */
@ -334,9 +339,14 @@ NS_IMETHODIMP nsHTMLSelectListAccessible::GetState(PRUint32 *_retval)
return NS_OK;
}
NS_IMETHODIMP nsHTMLSelectListAccessible::GetRole(PRUint32 *_retval)
NS_IMETHODIMP nsHTMLSelectListAccessible::GetRole(PRUint32 *aRole)
{
*_retval = ROLE_LIST;
if (mParent && Role(mParent) == ROLE_COMBOBOX) {
*aRole = ROLE_COMBOBOX_LIST;
}
else {
*aRole = ROLE_LIST;
}
return NS_OK;
}
@ -464,7 +474,12 @@ nsHyperTextAccessible(aDOMNode, aShell)
/** We are a ListItem */
NS_IMETHODIMP nsHTMLSelectOptionAccessible::GetRole(PRUint32 *aRole)
{
*aRole = ROLE_LISTITEM;
if (mParent && Role(mParent) == ROLE_COMBOBOX_LIST) {
*aRole = ROLE_COMBOBOX_LISTITEM;
}
else {
*aRole = ROLE_COMBOBOX_LISTITEM;
}
return NS_OK;
}
@ -701,12 +716,9 @@ nsresult nsHTMLSelectOptionAccessible::GetFocusedOptionNode(nsIDOMNode *aListNod
rv = selectElement->GetSelectedIndex(&focusedOptionIndex);
}
// Either use options and focused index, or default to list node itself
if (NS_SUCCEEDED(rv) && options && focusedOptionIndex >= 0) // Something is focused
// Either use options and focused index, or default return null
if (NS_SUCCEEDED(rv) && options && focusedOptionIndex >= 0) { // Something is focused
rv = options->Item(focusedOptionIndex, aFocusedOptionNode);
else { // If no options in list or focusedOptionIndex <0, then we are not focused on an item
NS_ADDREF(*aFocusedOptionNode = aListNode); // return normal target content
rv = NS_OK;
}
return rv;
@ -800,40 +812,72 @@ NS_IMETHODIMP nsHTMLComboboxAccessible::GetRole(PRUint32 *_retval)
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxAccessible::Shutdown()
void nsHTMLComboboxAccessible::CacheChildren()
{
nsHTMLSelectableAccessible::Shutdown();
mComboboxTextFieldAccessible = nsnull;
mComboboxButtonAccessible = nsnull;
mComboboxListAccessible = nsnull;
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxAccessible::Init()
{
// Hold references
GetFirstChild(getter_AddRefs(mComboboxTextFieldAccessible));
if (mComboboxTextFieldAccessible) {
mComboboxTextFieldAccessible->GetNextSibling(getter_AddRefs(mComboboxButtonAccessible));
}
if (mComboboxButtonAccessible) {
mComboboxButtonAccessible->GetNextSibling(getter_AddRefs(mComboboxListAccessible));
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
nsHTMLSelectableAccessible::Init();
if (mAccChildCount == eChildCountUninitialized) {
mAccChildCount = 0;
#ifdef COMBO_BOX_WITH_THREE_CHILDREN
// We no longer create textfield and button accessible, in order to have
// harmonization between IAccessible2, ATK/AT-SPI and OS X
nsHTMLComboboxTextFieldAccessible* textFieldAccessible =
new nsHTMLComboboxTextFieldAccessible(this, mDOMNode, mWeakShell);
SetFirstChild(textFieldAccessible);
if (!textFieldAccessible) {
return;
}
textFieldAccessible->SetParent(this);
textFieldAccessible->Init();
mAccChildCount = 1; // Textfield accessible child successfully added
return NS_OK;
}
nsHTMLComboboxButtonAccessible* buttonAccessible =
new nsHTMLComboboxButtonAccessible(mParent, mDOMNode, mWeakShell);
textFieldAccessible->SetNextSibling(buttonAccessible);
if (!buttonAccessible) {
return;
}
/**
* We always have 3 children: TextField, Button, Window. In that order
*/
NS_IMETHODIMP nsHTMLComboboxAccessible::GetChildCount(PRInt32 *_retval)
{
*_retval = 3;
return NS_OK;
buttonAccessible->SetParent(this);
buttonAccessible->Init();
mAccChildCount = 2; // Button accessible child successfully added
#endif
nsIFrame *frame = GetFrame();
if (!frame) {
return;
}
nsIComboboxControlFrame *comboFrame = nsnull;
frame->QueryInterface(NS_GET_IID(nsIComboboxControlFrame), (void**)&comboFrame);
if (!comboFrame) {
return;
}
nsIFrame *listFrame = comboFrame->GetDropDown();
if (!listFrame) {
return;
}
nsHTMLComboboxListAccessible* listAccessible =
new nsHTMLComboboxListAccessible(mParent, mDOMNode, listFrame, mWeakShell);
#ifdef COMBO_BOX_WITH_THREE_CHILDREN
buttonAccessible->SetNextSibling(listAccessible);
#else
SetFirstChild(listAccessible);
#endif
if (!listAccessible) {
return;
}
listAccessible->SetParent(this);
listAccessible->SetNextSibling(nsnull);
listAccessible->Init();
++ mAccChildCount; // List accessible child successfully added
}
}
/**
@ -864,44 +908,18 @@ NS_IMETHODIMP nsHTMLComboboxAccessible::GetState(PRUint32 *_retval)
return NS_OK;
}
/**
* Our last child is an nsHTMLComboboxListAccessible object, is also the third child
*/
NS_IMETHODIMP nsHTMLComboboxAccessible::GetLastChild(nsIAccessible **aLastChild)
{
// It goes: textfield, button, list. We're returning the list.
return GetChildAt(2, aLastChild);
}
/**
* Our first child is an nsHTMLComboboxTextFieldAccessible object
*/
NS_IMETHODIMP nsHTMLComboboxAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
if (mFirstChild) {
*aFirstChild = mFirstChild;
}
else {
nsHTMLComboboxTextFieldAccessible* accessible =
new nsHTMLComboboxTextFieldAccessible(this, mDOMNode, mWeakShell);
*aFirstChild = accessible;
if (! *aFirstChild)
return NS_ERROR_FAILURE;
accessible->Init();
SetFirstChild(*aFirstChild);
}
NS_ADDREF(*aFirstChild);
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxAccessible::GetDescription(nsAString& aDescription)
{
// Use description of currently focused option
aDescription.Truncate();
// First check to see if combo box itself has a description, perhaps through
// tooltip (title attribute) or via aaa:describedby
nsAccessible::GetDescription(aDescription);
if (!aDescription.IsEmpty()) {
return NS_OK;
}
// Use description of currently focused option
nsCOMPtr<nsIAccessible> optionAccessible = GetFocusedOptionAccessible();
NS_ENSURE_TRUE(optionAccessible, NS_ERROR_FAILURE);
return optionAccessible->GetDescription(aDescription);
return optionAccessible ? optionAccessible->GetDescription(aDescription) : NS_OK;
}
already_AddRefed<nsIAccessible>
@ -910,19 +928,9 @@ nsHTMLComboboxAccessible::GetFocusedOptionAccessible()
if (!mWeakShell) {
return nsnull; // Shut down
}
nsCOMPtr<nsIComboboxControlFrame> cbxFrame = do_QueryInterface(GetFrame());
if (!cbxFrame) {
return nsnull;
}
nsIFrame *listFrame = cbxFrame->GetDropDown();
if (!listFrame) {
return nsnull;
}
nsCOMPtr<nsIDOMNode> listNode = do_QueryInterface(listFrame->GetContent());
nsCOMPtr<nsIDOMNode> focusedOptionNode;
nsHTMLSelectOptionAccessible::GetFocusedOptionNode(listNode, getter_AddRefs(focusedOptionNode));
nsCOMPtr<nsIAccessibilityService> accService =
do_GetService("@mozilla.org/accessibilityService;1");
nsHTMLSelectOptionAccessible::GetFocusedOptionNode(mDOMNode, getter_AddRefs(focusedOptionNode));
nsIAccessibilityService *accService = GetAccService();
if (!focusedOptionNode || !accService) {
return nsnull;
}
@ -946,6 +954,66 @@ NS_IMETHODIMP nsHTMLComboboxAccessible::GetValue(nsAString& aValue)
return optionAccessible->GetName(aValue);
}
/** Just one action ( click ). */
NS_IMETHODIMP nsHTMLComboboxAccessible::GetNumActions(PRUint8 *aNumActions)
{
*aNumActions = 1;
return NS_OK;
}
/**
* Programmaticaly toggle the combo box
*/
NS_IMETHODIMP nsHTMLComboboxAccessible::DoAction(PRUint8 aIndex)
{
if (aIndex != nsHTMLComboboxAccessible::eAction_Click) {
return NS_ERROR_INVALID_ARG;
}
nsIFrame *frame = GetFrame();
if (!frame) {
return NS_ERROR_FAILURE;
}
nsIComboboxControlFrame *comboFrame = nsnull;
frame->QueryInterface(NS_GET_IID(nsIComboboxControlFrame), (void**)&comboFrame);
if (!comboFrame) {
return NS_ERROR_FAILURE;
}
// Reverse whether it's dropped down or not
comboFrame->ShowDropDown(!comboFrame->IsDroppedDown());
return NS_OK;
}
/**
* Our action name is the reverse of our state:
* if we are closed -> open is our name.
* if we are open -> closed is our name.
* Uses the frame to get the state, updated on every click
*/
NS_IMETHODIMP nsHTMLComboboxAccessible::GetActionName(PRUint8 aIndex, nsAString& aActionName)
{
if (aIndex != nsHTMLComboboxAccessible::eAction_Click) {
return NS_ERROR_INVALID_ARG;
}
nsIFrame *frame = GetFrame();
if (!frame) {
return NS_ERROR_FAILURE;
}
nsIComboboxControlFrame *comboFrame = nsnull;
frame->QueryInterface(NS_GET_IID(nsIComboboxControlFrame), (void**)&comboFrame);
if (!comboFrame) {
return NS_ERROR_FAILURE;
}
if (comboFrame->IsDroppedDown())
nsAccessible::GetTranslatedString(NS_LITERAL_STRING("close"), aActionName);
else
nsAccessible::GetTranslatedString(NS_LITERAL_STRING("open"), aActionName);
return NS_OK;
}
#ifdef COMBO_BOX_WITH_THREE_CHILDREN
/** ----- nsHTMLComboboxTextFieldAccessible ----- */
/** Constructor */
@ -954,32 +1022,8 @@ nsHTMLComboboxTextFieldAccessible::nsHTMLComboboxTextFieldAccessible(nsIAccessib
nsIWeakReference* aShell):
nsHTMLTextFieldAccessible(aDOMNode, aShell)
{
// There is no cache entry for this item.
// It's generated and ref'd by nsHTMLComboboxAccessible
SetParent(aParent);
}
/**
* Our next sibling is an nsHTMLComboboxButtonAccessible object
*/
NS_IMETHODIMP nsHTMLComboboxTextFieldAccessible::GetNextSibling(nsIAccessible **aNextSibling)
{
if (mNextSibling) {
*aNextSibling = mNextSibling;
}
else {
nsHTMLComboboxButtonAccessible* accessible =
new nsHTMLComboboxButtonAccessible(mParent, mDOMNode, mWeakShell);
*aNextSibling = accessible;
if (!*aNextSibling)
return NS_ERROR_FAILURE;
accessible->Init();
mNextSibling = accessible;
}
NS_ADDREF(*aNextSibling);
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxTextFieldAccessible::GetUniqueID(void **aUniqueID)
{
// Since mDOMNode is same as for our parent, use |this| pointer as the unique Id
@ -1033,15 +1077,6 @@ void nsHTMLComboboxTextFieldAccessible::CacheChildren()
}
}
/**
* We are the first child of our parent, no previous sibling
*/
NS_IMETHODIMP nsHTMLComboboxTextFieldAccessible::GetPreviousSibling(nsIAccessible **_retval)
{
*_retval = nsnull;
return NS_OK;
}
/** -----ComboboxButtonAccessible ----- */
/** Constructor -- cache our parent */
@ -1050,9 +1085,6 @@ nsHTMLComboboxButtonAccessible::nsHTMLComboboxButtonAccessible(nsIAccessible* aP
nsIWeakReference* aShell):
nsLeafAccessible(aDOMNode, aShell)
{
// There is no cache entry for this item.
// It's generated and ref'd by nsHTMLComboboxAccessible
SetParent(aParent);
}
/** Just one action ( click ). */
@ -1183,47 +1215,21 @@ NS_IMETHODIMP nsHTMLComboboxButtonAccessible::GetState(PRUint32 *_retval)
return NS_OK;
}
/**
* Our next sibling is an nsHTMLComboboxListAccessible object
*/
NS_IMETHODIMP nsHTMLComboboxButtonAccessible::GetNextSibling(nsIAccessible **aNextSibling)
{
if (mNextSibling) {
*aNextSibling = mNextSibling;
}
else {
nsHTMLComboboxListAccessible* accessible =
new nsHTMLComboboxListAccessible(mParent, mDOMNode, mWeakShell);
*aNextSibling = accessible;
if (!*aNextSibling)
return NS_ERROR_OUT_OF_MEMORY;
accessible->Init();
mNextSibling = accessible;
}
NS_ADDREF(*aNextSibling);
return NS_OK;
}
/**
* Our prev sibling is an nsHTMLComboboxTextFieldAccessible object
*/
NS_IMETHODIMP nsHTMLComboboxButtonAccessible::GetPreviousSibling(nsIAccessible **aAccPrevSibling)
{
return mParent->GetFirstChild(aAccPrevSibling);
}
#endif
/** ----- nsHTMLComboboxListAccessible ----- */
nsHTMLComboboxListAccessible::nsHTMLComboboxListAccessible(nsIAccessible *aParent,
nsIDOMNode* aDOMNode,
nsIDOMNode* aDOMNode,
nsIFrame *aListFrame,
nsIWeakReference* aShell):
nsHTMLSelectListAccessible(aDOMNode, aShell)
nsHTMLSelectListAccessible(aDOMNode, aShell), mListFrame(aListFrame)
{
// There is no cache entry for this item.
// It's generated and ref'd by nsHTMLComboboxAccessible
SetParent(aParent);
}
nsIFrame *nsHTMLComboboxListAccessible::GetFrame()
{
return mListFrame;
}
/**
@ -1259,11 +1265,6 @@ NS_IMETHODIMP nsHTMLComboboxListAccessible::GetParent(nsIAccessible **aParent)
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxListAccessible::GetPreviousSibling(nsIAccessible **aAccPrevSibling)
{
return mParent->GetChildAt(1, aAccPrevSibling);
}
NS_IMETHODIMP nsHTMLComboboxListAccessible::GetUniqueID(void **aUniqueID)
{
// Since mDOMNode is same for all tree item, use |this| pointer as the unique Id

Просмотреть файл

@ -196,32 +196,27 @@ public:
class nsHTMLComboboxAccessible : public nsHTMLSelectableAccessible
{
public:
enum { eAction_Click = 0 };
nsHTMLComboboxAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell);
virtual ~nsHTMLComboboxAccessible() {}
/* ----- nsIAccessible ----- */
NS_IMETHOD GetRole(PRUint32 *_retval);
NS_IMETHOD GetChildCount(PRInt32 *_retval);
NS_IMETHOD GetState(PRUint32 *_retval);
NS_IMETHOD GetLastChild(nsIAccessible **_retval);
NS_IMETHOD GetFirstChild(nsIAccessible **_retval);
NS_IMETHOD GetValue(nsAString& _retval);
NS_IMETHOD GetDescription(nsAString& aDescription);
NS_IMETHOD Shutdown();
NS_IMETHOD Init();
NS_IMETHOD DoAction(PRUint8 index);
NS_IMETHOD GetNumActions(PRUint8 *aNumActions);
NS_IMETHOD GetActionName(PRUint8 index, nsAString& aActionName);
void CacheChildren();
protected:
already_AddRefed<nsIAccessible> GetFocusedOptionAccessible();
// Hold references to our generated children
// So that we can shut them down when we need to
nsCOMPtr<nsIAccessible> mComboboxTextFieldAccessible;
nsCOMPtr<nsIAccessible> mComboboxButtonAccessible;
nsCOMPtr<nsIAccessible> mComboboxListAccessible;
};
#ifdef COMBO_BOX_WITH_THREE_CHILDREN
/*
* A class the represents the text field in the Select to the left
* of the drop down button
@ -234,8 +229,6 @@ public:
virtual ~nsHTMLComboboxTextFieldAccessible() {}
/* ----- nsIAccessible ----- */
NS_IMETHOD GetNextSibling(nsIAccessible **_retval);
NS_IMETHOD GetPreviousSibling(nsIAccessible **_retval);
NS_IMETHOD GetUniqueID(void **aUniqueID);
virtual void GetBoundsRect(nsRect& aBounds, nsIFrame** aBoundingFrame);
@ -261,8 +254,6 @@ public:
NS_IMETHOD GetNumActions(PRUint8 *_retval);
NS_IMETHOD GetActionName(PRUint8 index, nsAString& _retval);
NS_IMETHOD GetParent(nsIAccessible **_retval);
NS_IMETHOD GetNextSibling(nsIAccessible **_retval);
NS_IMETHOD GetPreviousSibling(nsIAccessible **_retval);
NS_IMETHOD GetName(nsAString& _retval);
NS_IMETHOD GetRole(PRUint32 *_retval);
NS_IMETHOD GetState(PRUint32 *_retval);
@ -270,6 +261,7 @@ public:
virtual void GetBoundsRect(nsRect& aBounds, nsIFrame** aBoundingFrame);
};
#endif
/*
* A class that represents the window that lives to the right
@ -281,17 +273,23 @@ class nsHTMLComboboxListAccessible : public nsHTMLSelectListAccessible
public:
nsHTMLComboboxListAccessible(nsIAccessible *aParent,
nsIDOMNode* aDOMNode,
nsIWeakReference* aShell);
nsIDOMNode* aDOMNode,
nsIFrame *aListFrame,
nsIWeakReference* aShell);
virtual ~nsHTMLComboboxListAccessible() {}
/* ----- nsIAccessible ----- */
NS_IMETHOD GetState(PRUint32 *aState);
NS_IMETHOD GetParent(nsIAccessible **aParent);
NS_IMETHOD GetUniqueID(void **aUniqueID);
NS_IMETHOD GetPreviousSibling(nsIAccessible **aAccPrevSibling);
// nsPIAccessNode
NS_IMETHOD_(nsIFrame *) GetFrame(void);
virtual void GetBoundsRect(nsRect& aBounds, nsIFrame** aBoundingFrame);
protected:
nsIFrame *mListFrame;
};
#endif

Просмотреть файл

@ -156,5 +156,7 @@ static const NSString* AXRoles [] = {
NSAccessibilityUnknownRole, // ROLE_APP_ROOT. unused on OS X
NSAccessibilityMenuItemRole, // ROLE_PARENT_MENUITEM
NSAccessibilityGroupRole, // ROLE_CALENDAR
NSAccessibilityMenuRole, // ROLE_COMBOBOX_LIST
NSAccessibilityMenuItemRole, // ROLE_COMBOBOX_LISTITEM
@"ROLE_LAST_ENTRY" // ROLE_LAST_ENTRY. bogus role that will never be shown (just marks the end of this array)!
};

Просмотреть файл

@ -173,6 +173,8 @@ PRUint32 msaaRoleMap[] = {
ROLE_SYSTEM_APPLICATION, // nsIAccessible::ROLE_APP_ROOT
ROLE_SYSTEM_MENUITEM, // nsIAccessible::ROLE_PARENT_MENUITEM
ROLE_SYSTEM_CLIENT, // nsIAccessible::ROLE_CALENDAR
ROLE_SYSTEM_LIST, // nsIAccessible::ROLE_COMBOBOX_LIST
ROLE_SYSTEM_LISTITEM, // nsIAccessible::ROLE_COMBOBOX_LISTITEM
ROLE_MSAA_LAST_ENTRY // nsIAccessible::ROLE_LAST_ENTRY
};

Просмотреть файл

@ -192,6 +192,10 @@ NS_IMETHODIMP nsXULMenuitemAccessible::GetKeyBinding(nsAString& _retval)
NS_IMETHODIMP nsXULMenuitemAccessible::GetRole(PRUint32 *aRole)
{
*aRole = ROLE_MENUITEM;
if (mParent && Role(mParent) == ROLE_COMBOBOX_LIST) {
*aRole = ROLE_COMBOBOX_LISTITEM;
return NS_OK;
}
nsCOMPtr<nsIDOMElement> element(do_QueryInterface(mDOMNode));
if (!element)
return NS_ERROR_FAILURE;
@ -381,9 +385,14 @@ NS_IMETHODIMP nsXULMenupopupAccessible::GetName(nsAString& _retval)
return NS_ERROR_FAILURE;
}
NS_IMETHODIMP nsXULMenupopupAccessible::GetRole(PRUint32 *_retval)
NS_IMETHODIMP nsXULMenupopupAccessible::GetRole(PRUint32 *aRole)
{
*_retval = ROLE_MENUPOPUP;
if (mParent && Role(mParent) == ROLE_COMBOBOX) {
*aRole = ROLE_COMBOBOX_LIST;
}
else {
*aRole = ROLE_MENUPOPUP;
}
return NS_OK;
}

Просмотреть файл

@ -58,16 +58,13 @@
* nsXULSelectableAccessible so that it supports nsIAccessibleSelectable)
*
* Listbox:
* - nsXULListboxAccessible
* - nsXULSelectListAccessible
* - nsXULSelectOptionAccessible
* - nsXULListboxAccessible <richlistbox/>
* - nsXULSelectOptionAccessible <richlistitem/>
*
* Comboboxes:
* - nsXULComboboxAccessible
* - nsHTMLTextFieldAccessible (editable) or nsTextAccessible (readonly)
* - nsXULComboboxButtonAccessible
* - nsXULSelectListAccessible
* - nsXULSelectOptionAccessible
* - nsXULComboboxAccessible <menulist/>
* - nsXULMenuAccessible <menupopup/>
* - nsXULMenuitemAccessible <menuitem/>
*/
/** ------------------------------------------------------ */
@ -258,106 +255,6 @@ NS_IMETHODIMP nsXULSelectableAccessible::SelectAllSelection(PRBool *_retval)
return NS_OK;
}
/** ------------------------------------------------------ */
/** First, the common widgets */
/** ------------------------------------------------------ */
/** ----- nsXULSelectListAccessible ----- */
/** Default Constructor */
nsXULSelectListAccessible::nsXULSelectListAccessible(nsIDOMNode* aDOMNode,
nsIWeakReference* aShell)
:nsAccessibleWrap(aDOMNode, aShell)
{
}
NS_IMETHODIMP nsXULSelectListAccessible::GetRole(PRUint32 *_retval)
{
*_retval = ROLE_LIST;
return NS_OK;
}
/**
* As a nsXULSelectListAccessible we can have the following states:
* STATE_MULTISELECTABLE
* STATE_EXTSELECTABLE
*/
NS_IMETHODIMP nsXULSelectListAccessible::GetState(PRUint32 *_retval)
{
*_retval = 0;
nsAutoString selectionTypeString;
nsCOMPtr<nsIDOMElement> element(do_QueryInterface(mDOMNode));
NS_ASSERTION(element, "No nsIDOMElement for caption node!");
element->GetAttribute(NS_LITERAL_STRING("seltype"), selectionTypeString) ;
if (selectionTypeString.LowerCaseEqualsLiteral("multiple"))
*_retval |= STATE_MULTISELECTABLE | STATE_EXTSELECTABLE;
return NS_OK;
}
/** ----- nsXULSelectOptionAccessible ----- */
/** Default Constructor */
nsXULSelectOptionAccessible::nsXULSelectOptionAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell):
nsXULMenuitemAccessible(aDOMNode, aShell)
{
}
NS_IMETHODIMP nsXULSelectOptionAccessible::GetRole(PRUint32 *_retval)
{
*_retval = ROLE_LISTITEM;
return NS_OK;
}
/**
* As a nsXULSelectOptionAccessible we can have the following states:
* STATE_SELECTABLE
* STATE_SELECTED
* STATE_FOCUSED
* STATE_FOCUSABLE
*/
NS_IMETHODIMP nsXULSelectOptionAccessible::GetState(PRUint32 *_retval)
{
nsXULMenuitemAccessible::GetState(_retval);
nsCOMPtr<nsIDOMXULSelectControlItemElement> item(do_QueryInterface(mDOMNode));
PRBool isSelected = PR_FALSE;
item->GetSelected(&isSelected);
if (isSelected)
*_retval |= STATE_SELECTED;
return NS_OK;
}
nsIFrame* nsXULSelectOptionAccessible::GetBoundsFrame()
{
nsCOMPtr<nsIContent> menuListContent(do_QueryInterface(mDOMNode));
while (menuListContent) {
nsCOMPtr<nsIDOMXULMenuListElement> menuListControl =
do_QueryInterface(menuListContent);
if (menuListControl) {
PRBool isOpen;
menuListControl->GetOpen(&isOpen);
if (!isOpen) {
nsCOMPtr<nsIPresShell> presShell(GetPresShell());
if (!presShell) {
return nsnull;
}
return presShell->GetPrimaryFrameFor(menuListContent);
}
break;
}
menuListContent = menuListContent->GetParent();
}
return nsXULMenuitemAccessible::GetBoundsFrame();
}
/** ------------------------------------------------------ */
/** Secondly, the Listbox widget */
/** ------------------------------------------------------ */
/** ----- nsXULListboxAccessible ----- */
/** Constructor */
@ -454,35 +351,35 @@ NS_IMETHODIMP nsXULListitemAccessible::GetName(nsAString& _retval)
/**
*
*/
NS_IMETHODIMP nsXULListitemAccessible::GetRole(PRUint32 *_retval)
NS_IMETHODIMP nsXULListitemAccessible::GetRole(PRUint32 *aRole)
{
if (mIsCheckbox)
*_retval = ROLE_CHECKBUTTON;
*aRole = ROLE_CHECKBUTTON;
else
*_retval = ROLE_LISTITEM;
*aRole = ROLE_LISTITEM;
return NS_OK;
}
/**
*
*/
NS_IMETHODIMP nsXULListitemAccessible::GetState(PRUint32 *_retval)
NS_IMETHODIMP nsXULListitemAccessible::GetState(PRUint32 *aState)
{
if (mIsCheckbox) {
nsXULMenuitemAccessible::GetState(_retval);
nsXULMenuitemAccessible::GetState(aState);
return NS_OK;
}
*_retval = STATE_FOCUSABLE | STATE_SELECTABLE;
*aState = STATE_FOCUSABLE | STATE_SELECTABLE;
nsCOMPtr<nsIDOMXULSelectControlItemElement> listItem (do_QueryInterface(mDOMNode));
if (listItem) {
PRBool isSelected;
listItem->GetSelected(&isSelected);
if (isSelected)
*_retval |= STATE_SELECTED;
*aState |= STATE_SELECTED;
if (gLastFocusedNode == mDOMNode) {
*_retval |= STATE_FOCUSED;
*aState |= STATE_FOCUSED;
}
}
@ -491,7 +388,7 @@ NS_IMETHODIMP nsXULListitemAccessible::GetState(PRUint32 *_retval)
NS_IMETHODIMP nsXULListitemAccessible::GetActionName(PRUint8 index, nsAString& _retval)
{
if (index == eAction_Click) {
if (index == eAction_Click && mIsCheckbox) {
// check or uncheck
PRUint32 state;
GetState(&state);
@ -660,3 +557,54 @@ nsXULComboboxAccessible::GetAllowsAnonChildAccessibles(PRBool *aAllowsAnonChildr
return NS_OK;
}
/** Just one action ( click ). */
NS_IMETHODIMP nsXULComboboxAccessible::GetNumActions(PRUint8 *aNumActions)
{
*aNumActions = 1;
return NS_OK;
}
/**
* Programmaticaly toggle the combo box
*/
NS_IMETHODIMP nsXULComboboxAccessible::DoAction(PRUint8 aIndex)
{
if (aIndex != nsXULComboboxAccessible::eAction_Click) {
return NS_ERROR_INVALID_ARG;
}
nsCOMPtr<nsIDOMXULMenuListElement> menuList(do_QueryInterface(mDOMNode));
if (!menuList) {
return NS_ERROR_FAILURE;
}
PRBool isDroppedDown;
menuList->GetOpen(&isDroppedDown);
return menuList->SetOpen(!isDroppedDown);
}
/**
* Our action name is the reverse of our state:
* if we are closed -> open is our name.
* if we are open -> closed is our name.
* Uses the frame to get the state, updated on every click
*/
NS_IMETHODIMP nsXULComboboxAccessible::GetActionName(PRUint8 aIndex, nsAString& aActionName)
{
if (aIndex != nsXULComboboxAccessible::eAction_Click) {
return NS_ERROR_INVALID_ARG;
}
nsCOMPtr<nsIDOMXULMenuListElement> menuList(do_QueryInterface(mDOMNode));
if (!menuList) {
return NS_ERROR_FAILURE;
}
PRBool isDroppedDown;
menuList->GetOpen(&isDroppedDown);
if (isDroppedDown)
nsAccessible::GetTranslatedString(NS_LITERAL_STRING("close"), aActionName);
else
nsAccessible::GetTranslatedString(NS_LITERAL_STRING("open"), aActionName);
return NS_OK;
}

Просмотреть файл

@ -51,15 +51,12 @@ class nsIWeakReference;
*
* Listbox:
* - nsXULListboxAccessible
* - nsXULSelectListAccessible
* - nsXULSelectOptionAccessible
* - nsXULSelectOptionAccessible
*
* Comboboxes:
* - nsXULComboboxAccessible <menulist />
* - nsHTMLTextFieldAccessible
* - nsXULComboboxButtonAccessible
* - nsXULSelectListAccessible <menupopup />
* - nsXULSelectOptionAccessible(s) <menuitem />
* - nsXULMenuAccessible <menupopup />
* - nsXULMenuitemAccessible(s) <menuitem />
*/
/** ------------------------------------------------------ */
@ -86,39 +83,6 @@ protected:
{ return NS_ERROR_FAILURE; } // Overrides base impl in nsAccessible
};
/*
* The list that contains all the options in the select.
*/
class nsXULSelectListAccessible : public nsAccessibleWrap
{
public:
nsXULSelectListAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell);
virtual ~nsXULSelectListAccessible() {}
/* ----- nsIAccessible ----- */
NS_IMETHOD GetRole(PRUint32 *_retval);
NS_IMETHOD GetState(PRUint32 *_retval);
};
/*
* Options inside the select, contained within the list
*/
class nsXULSelectOptionAccessible : public nsXULMenuitemAccessible
{
public:
nsXULSelectOptionAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell);
virtual ~nsXULSelectOptionAccessible() {}
/* ----- nsIAccessible ----- */
NS_IMETHOD GetRole(PRUint32 *_retval);
NS_IMETHOD GetState(PRUint32 *_retval);
// Don't use XUL menuitems's description attribute
NS_IMETHOD GetDescription(nsAString& aDesc) { return nsAccessibleWrap::GetDescription(aDesc); }
nsIFrame* GetBoundsFrame();
};
/** ------------------------------------------------------ */
/** Secondly, the Listbox widget */
/** ------------------------------------------------------ */
@ -176,6 +140,7 @@ private:
class nsXULComboboxAccessible : public nsXULSelectableAccessible
{
public:
enum { eAction_Click = 0 };
nsXULComboboxAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell);
virtual ~nsXULComboboxAccessible() {}
@ -184,10 +149,12 @@ public:
void CacheChildren();
NS_IMETHOD GetRole(PRUint32 *_retval);
NS_IMETHOD GetState(PRUint32 *_retval);
NS_IMETHOD GetValue(nsAString& _retval);
NS_IMETHOD GetDescription(nsAString& aDescription);
NS_IMETHOD GetAllowsAnonChildAccessibles(PRBool *aAllowsAnonChildren);
NS_IMETHOD DoAction(PRUint8 index);
NS_IMETHOD GetNumActions(PRUint8 *aNumActions);
NS_IMETHOD GetActionName(PRUint8 index, nsAString& aActionName);
};
#endif