Merge mozilla-central into electrolysis. One code change was required: in nsDocShell::CreateStaticClone I replaced EnsureDocShell with MaybeCreateDocShell.

This commit is contained in:
Benjamin Smedberg 2009-12-12 13:38:25 -05:00
commit 636d74b114
489 changed files with 15995 additions and 8110 deletions

View file

@ -46,7 +46,7 @@ interface nsObjectFrame;
interface nsIContent;
interface nsITimer;
[uuid(29384ba1-f9ce-425d-afb5-54e2ee949d87)]
[uuid(61098f48-4fcc-4b05-9cf3-c11b8efbe682)]
interface nsIAccessibilityService : nsIAccessibleRetrieval
{
nsIAccessible createOuterDocAccessible(in nsIDOMNode aNode);
@ -76,9 +76,18 @@ interface nsIAccessibilityService : nsIAccessibleRetrieval
nsIAccessible createHTMLTextFieldAccessible(in nsIFrame aFrame);
nsIAccessible createHTMLCaptionAccessible(in nsIFrame aFrame);
nsIAccessible getAccessible(in nsIDOMNode aNode, in nsIPresShell aPresShell,
in nsIWeakReference aWeakShell,
inout nsIFrame frameHint, out boolean aIsHidden);
/**
* Return an accessible for the given DOM node.
*
* @param aNode [in] the given node
* @param aPresShell [in] the pres shell of the node
* @param aWeakShell [in] the weak shell for the pres shell
* @param aFrameHint [in] the frame of the given node
* @param aIsHidden [out] indicates whether the node's frame is hidden
*/
nsIAccessible getAccessible(in nsIDOMNode aNode, in nsIPresShell aPresShell,
in nsIWeakReference aWeakShell,
in nsIFrame aFrameHint, out boolean aIsHidden);
// For gtk+ native window accessible
nsIAccessible addNativeRootAccessible(in voidPtr aAtkAccessible);

View file

@ -647,8 +647,7 @@ nsApplicationAccessibleWrap::AddRootAccessible(nsIAccessible *aRootAccWrap)
AtkObject *atkAccessible = nsAccessibleWrap::GetAtkObject(aRootAccWrap);
atk_object_set_parent(atkAccessible, mAtkObject);
PRUint32 count = 0;
mChildren->GetLength(&count);
PRUint32 count = mChildren.Count();
g_signal_emit_by_name(mAtkObject, "children_changed::add", count - 1,
atkAccessible, NULL);
@ -670,36 +669,27 @@ nsApplicationAccessibleWrap::RemoveRootAccessible(nsIAccessible *aRootAccWrap)
{
NS_ENSURE_ARG_POINTER(aRootAccWrap);
PRUint32 index = 0;
nsresult rv = NS_ERROR_FAILURE;
// we must use weak ref to get the index
nsCOMPtr<nsIWeakReference> weakPtr = do_GetWeakReference(aRootAccWrap);
rv = mChildren->IndexOf(0, weakPtr, &index);
PRInt32 index = mChildren.IndexOf(aRootAccWrap);
AtkObject *atkAccessible = nsAccessibleWrap::GetAtkObject(aRootAccWrap);
atk_object_set_parent(atkAccessible, NULL);
g_signal_emit_by_name(mAtkObject, "children_changed::remove", index,
atkAccessible, NULL);
nsresult rv = nsApplicationAccessible::RemoveRootAccessible(aRootAccWrap);
#ifdef MAI_LOGGING
PRUint32 count = 0;
mChildren->GetLength(&count);
PRUint32 count = mChildren.Count();
if (NS_SUCCEEDED(rv)) {
rv = mChildren->RemoveElementAt(index);
MAI_LOG_DEBUG(("\nRemove RootAcc=%p, count=%d\n",
(void*)aRootAccWrap, (count-1)));
}
else
MAI_LOG_DEBUG(("\nFail to Remove RootAcc=%p, count=%d\n",
(void*)aRootAccWrap, count));
#else
NS_ENSURE_SUCCESS(rv, rv);
rv = mChildren->RemoveElementAt(index);
#endif
InvalidateChildren();
return rv;
}

View file

@ -502,6 +502,46 @@ nsAccUtils::GetARIATreeItemParent(nsIAccessible *aStartTreeItem,
}
}
already_AddRefed<nsIAccessible>
nsAccUtils::GetSelectableContainer(nsIAccessible *aAccessible, PRUint32 aState)
{
if (!aAccessible)
return nsnull;
if (!(aState & nsIAccessibleStates::STATE_SELECTABLE))
return nsnull;
nsCOMPtr<nsIAccessibleSelectable> container;
nsCOMPtr<nsIAccessible> parent, accessible(aAccessible);
while (!container) {
accessible->GetParent(getter_AddRefs(parent));
if (!parent || Role(parent) == nsIAccessibleRole::ROLE_PANE)
return nsnull;
container = do_QueryInterface(parent);
parent.swap(accessible);
}
return accessible.forget();
}
already_AddRefed<nsIAccessible>
nsAccUtils::GetMultiSelectableContainer(nsIDOMNode *aNode)
{
nsCOMPtr<nsIAccessible> accessible;
nsAccessNode::GetAccService()->GetAccessibleFor(aNode,
getter_AddRefs(accessible));
nsCOMPtr<nsIAccessible> container =
GetSelectableContainer(accessible, State(accessible));
if (State(container) & nsIAccessibleStates::STATE_MULTISELECTABLE)
return container.forget();
return nsnull;
}
PRBool
nsAccUtils::IsARIASelected(nsIAccessible *aAccessible)
{
@ -927,37 +967,6 @@ nsAccUtils::IsNodeRelevant(nsIDOMNode *aNode)
return aNode == relevantNode;
}
already_AddRefed<nsIAccessible>
nsAccUtils::GetMultiSelectFor(nsIDOMNode *aNode)
{
if (!aNode)
return nsnull;
nsCOMPtr<nsIAccessible> accessible;
nsAccessNode::GetAccService()->GetAccessibleFor(aNode,
getter_AddRefs(accessible));
if (!accessible)
return nsnull;
PRUint32 state = State(accessible);
if (0 == (state & nsIAccessibleStates::STATE_SELECTABLE))
return nsnull;
while (0 == (state & nsIAccessibleStates::STATE_MULTISELECTABLE)) {
nsIAccessible *current = accessible;
current->GetParent(getter_AddRefs(accessible));
if (!accessible ||
nsAccUtils::Role(accessible) == nsIAccessibleRole::ROLE_PANE) {
return nsnull;
}
state = State(accessible);
}
nsIAccessible *returnAccessible = nsnull;
accessible.swap(returnAccessible);
return returnAccessible;
}
nsresult
nsAccUtils::GetHeaderCellsFor(nsIAccessibleTable *aTable,
nsIAccessibleTableCell *aCell,

View file

@ -179,6 +179,21 @@ public:
nsIContent *aStartTreeItemContent,
nsIAccessible **aTreeItemParent);
/**
* Return single or multi selectable container for the given item.
*
* @param aAccessible [in] the item accessible
* @param aState [in] the state of the item accessible
*/
static already_AddRefed<nsIAccessible>
GetSelectableContainer(nsIAccessible *aAccessible, PRUint32 aState);
/**
* Return multi selectable container for the given item.
*/
static already_AddRefed<nsIAccessible>
GetMultiSelectableContainer(nsIDOMNode *aNode);
/**
* Return true if the DOM node of given accessible has aria-selected="true"
* attribute.
@ -467,11 +482,6 @@ public:
*/
static PRBool IsNodeRelevant(nsIDOMNode *aNode);
/**
* Return multiselectable parent for the given selectable accessible if any.
*/
static already_AddRefed<nsIAccessible> GetMultiSelectFor(nsIDOMNode *aNode);
/**
* Search hint enum constants. Used by GetHeaderCellsFor() method.
*/

View file

@ -1242,10 +1242,9 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessibleInShell(nsIDOMNode *aNode,
NS_ENSURE_ARG(aPresShell);
nsCOMPtr<nsIWeakReference> weakShell(do_GetWeakReference(aPresShell));
nsIFrame *outFrameUnused = NULL;
PRBool isHiddenUnused = false;
return GetAccessible(aNode, aPresShell, weakShell,
&outFrameUnused, &isHiddenUnused, aAccessible);
nsnull, &isHiddenUnused, aAccessible);
}
NS_IMETHODIMP nsAccessibilityService::GetAccessibleInWeakShell(nsIDOMNode *aNode,
@ -1259,10 +1258,9 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessibleInWeakShell(nsIDOMNode *aNode
NS_ENSURE_ARG(aWeakShell);
nsCOMPtr<nsIPresShell> presShell(do_QueryReferent(aWeakShell));
nsIFrame *outFrameUnused = NULL;
PRBool isHiddenUnused = false;
return GetAccessible(aNode, presShell, aWeakShell,
&outFrameUnused, &isHiddenUnused, aAccessible);
nsnull, &isHiddenUnused, aAccessible);
}
nsresult nsAccessibilityService::InitAccessible(nsIAccessible *aAccessibleIn,
@ -1315,13 +1313,13 @@ static PRBool HasRelatedContent(nsIContent *aContent)
NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
nsIPresShell *aPresShell,
nsIWeakReference *aWeakShell,
nsIFrame **aFrameHint,
nsIFrame *aFrameHint,
PRBool *aIsHidden,
nsIAccessible **aAccessible)
{
NS_ENSURE_ARG_POINTER(aAccessible);
NS_ENSURE_ARG_POINTER(aFrameHint);
*aAccessible = nsnull;
if (!aPresShell || !aWeakShell || gIsShutdown) {
return NS_ERROR_FAILURE;
}
@ -1334,7 +1332,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
// that can flush layout, either directly, or via DOM manipulation, or some
// CSS styles like :hover. We use the weak frame checks to avoid calling
// methods on a dead frame pointer.
nsWeakFrame weakFrame(*aFrameHint);
nsWeakFrame weakFrame(aFrameHint);
#ifdef DEBUG_A11Y
// Please leave this in for now, it's a convenient debugging method
@ -1391,7 +1389,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
CreateRootAccessible(aPresShell, nodeIsDoc, getter_AddRefs(newAcc)); // Does Init() for us
}
*aFrameHint = aPresShell->GetRootFrame();
NS_IF_ADDREF(*aAccessible = newAcc);
return NS_OK;
}
@ -1421,7 +1418,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
if (content->IsNodeOfType(nsINode::eTEXT)) {
++frameHintFailedForText;
}
frameHintNonexistant += !*aFrameHint;
frameHintNonexistant += !aFrameHint;
printf("Frame hint failures: %d / %d . Text fails = %d. No hint fails = %d \n", frameHintFailed, frameHintTried, frameHintFailedForText, frameHintNonexistant);
if (frameHintTried >= 354) {
printf("* "); // Aaron's break point
@ -1450,7 +1447,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
return NS_OK;
}
*aFrameHint = weakFrame.GetFrame();
}
}
@ -1460,10 +1456,8 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
*aIsHidden = PR_TRUE;
}
if (*aIsHidden) {
*aFrameHint = weakFrame.GetFrame();
if (*aIsHidden)
return NS_OK;
}
/**
* Attempt to create an accessible based on what we know
@ -1477,7 +1471,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
if (renderedWhitespace.IsEmpty()) {
// Really empty -- nothing is rendered
*aIsHidden = PR_TRUE;
*aFrameHint = weakFrame.GetFrame();
return NS_OK;
}
}
@ -1485,9 +1478,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
weakFrame.GetFrame()->GetAccessible(getter_AddRefs(newAcc));
}
nsresult rv = InitAccessible(newAcc, aAccessible, nsnull);
*aFrameHint = weakFrame.GetFrame();
return rv;
return InitAccessible(newAcc, aAccessible, nsnull);
}
PRBool isHTML = content->IsHTML();
@ -1504,16 +1495,12 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
content->GetAttr(kNameSpaceID_None, nsAccessibilityAtoms::name, name);
if (!name.IsEmpty()) {
*aIsHidden = PR_TRUE;
*aFrameHint = weakFrame.GetFrame();
return NS_OK;
}
nsresult rv =
CreateHyperTextAccessible(weakFrame.GetFrame(), getter_AddRefs(newAcc));
if (NS_FAILED(rv)) {
*aFrameHint = weakFrame.GetFrame();
return rv;
}
NS_ENSURE_SUCCESS(rv, rv);
}
nsRoleMapEntry *roleMapEntry = nsAccUtils::GetRoleMapEntry(aNode);
@ -1522,7 +1509,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
// Only create accessible for role of "presentation" if it is focusable --
// in that case we need an accessible in case it gets focused, we
// don't want focus ever to be 'lost'
*aFrameHint = weakFrame.GetFrame();
return NS_OK;
}
@ -1580,7 +1566,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
// presentation if they aren't focusable and have not explicit ARIA
// role (don't create accessibles for them unless they need to fire
// focus events).
*aFrameHint = weakFrame.GetFrame();
return NS_OK;
}
@ -1628,10 +1613,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
nsresult rv =
CreateHTMLAccessibleByMarkup(weakFrame.GetFrame(), aWeakShell, aNode,
getter_AddRefs(newAcc));
if (NS_FAILED(rv)) {
*aFrameHint = weakFrame.GetFrame();
return rv;
}
NS_ENSURE_SUCCESS(rv, rv);
if (!newAcc) {
// Do not create accessible object subtrees for non-rendered table
@ -1649,7 +1631,6 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
// XXX This is not the ideal place for this code, but right now there
// is no better place:
*aIsHidden = PR_TRUE;
*aFrameHint = weakFrame.GetFrame();
return NS_OK;
}
f->GetAccessible(getter_AddRefs(newAcc)); // Try using frame to do it
@ -1661,10 +1642,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
// Elements may implement nsIAccessibleProvider via XBL. This allows them to
// say what kind of accessible to create.
nsresult rv = GetAccessibleByType(aNode, getter_AddRefs(newAcc));
if (NS_FAILED(rv)) {
*aFrameHint = weakFrame.GetFrame();
return rv;
}
NS_ENSURE_SUCCESS(rv, rv);
}
if (!newAcc) {
@ -1707,9 +1685,7 @@ NS_IMETHODIMP nsAccessibilityService::GetAccessible(nsIDOMNode *aNode,
}
}
nsresult rv = InitAccessible(newAcc, aAccessible, roleMapEntry);
*aFrameHint = weakFrame.GetFrame();
return rv;
return InitAccessible(newAcc, aAccessible, roleMapEntry);
}
PRBool

View file

@ -149,14 +149,12 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(nsAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsAccessible, nsAccessNode)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mParent)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mFirstChild)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mNextSibling)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMARRAY(mChildren)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsAccessible, nsAccessNode)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mParent)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mFirstChild)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mNextSibling)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMARRAY(mChildren)
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_IMPL_ADDREF_INHERITED(nsAccessible, nsAccessNode)
@ -186,23 +184,19 @@ nsresult nsAccessible::QueryInterface(REFNSIID aIID, void** aInstancePtr)
}
if (aIID.Equals(NS_GET_IID(nsIAccessibleSelectable))) {
nsCOMPtr<nsIContent> content(do_QueryInterface(mDOMNode));
if (!content) {
return NS_ERROR_FAILURE; // This accessible has been shut down
}
if (content->HasAttr(kNameSpaceID_None, nsAccessibilityAtoms::role)) {
// If we have an XHTML role attribute present and the
// aria-multiselectable attribute is true, then we need
// to support nsIAccessibleSelectable
if (mRoleMapEntry &&
(mRoleMapEntry->attributeMap1 == eARIAMultiSelectable ||
mRoleMapEntry->attributeMap2 == eARIAMultiSelectable ||
mRoleMapEntry->attributeMap3 == eARIAMultiSelectable)) {
// If we have an ARIA role attribute present and the role allows multi
// selectable state, then we need to support nsIAccessibleSelectable.
// If either attribute (role or multiselectable) change, then we'll
// destroy this accessible so that we can follow COM identity rules.
nsAutoString multiselectable;
if (content->AttrValueIs(kNameSpaceID_None, nsAccessibilityAtoms::aria_multiselectable,
nsAccessibilityAtoms::_true, eCaseMatters)) {
*aInstancePtr = static_cast<nsIAccessibleSelectable*>(this);
NS_ADDREF_THIS();
return NS_OK;
}
*aInstancePtr = static_cast<nsIAccessibleSelectable*>(this);
NS_ADDREF_THIS();
return NS_OK;
}
}
@ -229,8 +223,8 @@ nsresult nsAccessible::QueryInterface(REFNSIID aIID, void** aInstancePtr)
}
nsAccessible::nsAccessible(nsIDOMNode* aNode, nsIWeakReference* aShell): nsAccessNodeWrap(aNode, aShell),
mParent(nsnull), mFirstChild(nsnull), mNextSibling(nsnull), mRoleMapEntry(nsnull),
mAccChildCount(eChildCountUninitialized)
mParent(nsnull), mRoleMapEntry(nsnull),
mAreChildrenInitialized(PR_FALSE)
{
#ifdef NS_DEBUG_X
{
@ -482,39 +476,9 @@ nsAccessible::GetKeyboardShortcut(nsAString& aAccessKey)
return NS_OK;
}
void
nsAccessible::SetParent(nsIAccessible *aParent)
{
if (mParent != aParent) {
// Adopt a child -- we allow this now. the new parent
// may be a dom node which wasn't previously accessible but now is.
// The old parent's children now need to be invalidated, since
// it no longer owns the child, the new parent does
nsRefPtr<nsAccessible> oldParent = nsAccUtils::QueryAccessible(mParent);
if (oldParent)
oldParent->InvalidateChildren();
}
mParent = aParent;
}
void
nsAccessible::SetFirstChild(nsIAccessible *aFirstChild)
{
mFirstChild = aFirstChild;
}
void
nsAccessible::SetNextSibling(nsIAccessible *aNextSibling)
{
mNextSibling = aNextSibling;
}
nsresult
nsAccessible::Shutdown()
{
mNextSibling = nsnull;
// Invalidate the child count and pointers to other accessibles, also make
// sure none of its children point to this parent
InvalidateChildren();
@ -527,198 +491,112 @@ nsAccessible::Shutdown()
return nsAccessNodeWrap::Shutdown();
}
void
nsAccessible::InvalidateChildren()
{
// Document has transformed, reset our invalid children and child count
// Reset the sibling pointers, they will be set up again the next time
// CacheChildren() is called.
// Note: we don't want to start creating accessibles at this point,
// so don't use GetNextSibling() here. (bug 387252)
nsRefPtr<nsAccessible> child = nsAccUtils::QueryAccessible(mFirstChild);
while (child) {
child->mParent = nsnull;
nsCOMPtr<nsIAccessible> next = child->mNextSibling;
child->mNextSibling = nsnull;
child = nsAccUtils::QueryAccessible(next);
}
mAccChildCount = eChildCountUninitialized;
mFirstChild = nsnull;
}
NS_IMETHODIMP
nsAccessible::GetParent(nsIAccessible **aParent)
{
if (IsDefunct())
return NS_ERROR_FAILURE;
NS_ENSURE_ARG_POINTER(aParent);
nsCOMPtr<nsIAccessible> cachedParent = GetCachedParent();
if (cachedParent) {
cachedParent.swap(*aParent);
return NS_OK;
}
nsCOMPtr<nsIAccessibleDocument> docAccessible(GetDocAccessible());
NS_ENSURE_TRUE(docAccessible, NS_ERROR_FAILURE);
return docAccessible->GetAccessibleInParentChain(mDOMNode, PR_TRUE, aParent);
}
already_AddRefed<nsIAccessible>
nsAccessible::GetCachedParent()
{
if (IsDefunct())
return nsnull;
nsCOMPtr<nsIAccessible> cachedParent = mParent;
return cachedParent.forget();
}
already_AddRefed<nsIAccessible>
nsAccessible::GetCachedFirstChild()
{
if (IsDefunct())
return nsnull;
nsCOMPtr<nsIAccessible> cachedFirstChild = mFirstChild;
return cachedFirstChild.forget();
NS_IF_ADDREF(*aParent = GetParent());
return *aParent ? NS_OK : NS_ERROR_FAILURE;
}
/* readonly attribute nsIAccessible nextSibling; */
NS_IMETHODIMP nsAccessible::GetNextSibling(nsIAccessible * *aNextSibling)
{
*aNextSibling = nsnull;
if (!mWeakShell) {
// This node has been shut down
return NS_ERROR_FAILURE;
}
if (!mParent) {
nsCOMPtr<nsIAccessible> parent(GetParent());
if (parent) {
PRInt32 numChildren;
parent->GetChildCount(&numChildren); // Make sure we cache all of the children
}
}
NS_IMETHODIMP
nsAccessible::GetNextSibling(nsIAccessible **aNextSibling)
{
NS_ENSURE_ARG_POINTER(aNextSibling);
if (mNextSibling || !mParent) {
// If no parent, don't try to calculate a new sibling
// It either means we're at the root or shutting down the parent
NS_IF_ADDREF(*aNextSibling = mNextSibling);
return NS_OK;
}
return NS_ERROR_FAILURE;
nsresult rv = NS_OK;
NS_IF_ADDREF(*aNextSibling = GetSiblingAtOffset(1, &rv));
return rv;
}
/* readonly attribute nsIAccessible previousSibling; */
NS_IMETHODIMP nsAccessible::GetPreviousSibling(nsIAccessible * *aPreviousSibling)
NS_IMETHODIMP
nsAccessible::GetPreviousSibling(nsIAccessible * *aPreviousSibling)
{
*aPreviousSibling = nsnull;
NS_ENSURE_ARG_POINTER(aPreviousSibling);
if (!mWeakShell) {
// This node has been shut down
return NS_ERROR_FAILURE;
}
nsCOMPtr<nsIAccessible> parent;
if (NS_FAILED(GetParent(getter_AddRefs(parent))) || !parent) {
return NS_ERROR_FAILURE;
}
nsCOMPtr<nsIAccessible> testAccessible, prevSibling;
parent->GetFirstChild(getter_AddRefs(testAccessible));
while (testAccessible && this != testAccessible) {
prevSibling = testAccessible;
prevSibling->GetNextSibling(getter_AddRefs(testAccessible));
}
if (!prevSibling) {
return NS_ERROR_FAILURE;
}
NS_ADDREF(*aPreviousSibling = prevSibling);
return NS_OK;
nsresult rv = NS_OK;
NS_IF_ADDREF(*aPreviousSibling = GetSiblingAtOffset(-1, &rv));
return rv;
}
/* readonly attribute nsIAccessible firstChild; */
NS_IMETHODIMP nsAccessible::GetFirstChild(nsIAccessible * *aFirstChild)
{
if (gIsCacheDisabled) {
NS_IMETHODIMP
nsAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
NS_ENSURE_ARG_POINTER(aFirstChild);
*aFirstChild = nsnull;
if (gIsCacheDisabled)
InvalidateChildren();
}
PRInt32 numChildren;
GetChildCount(&numChildren); // Make sure we cache all of the children
#ifdef DEBUG
nsRefPtr<nsAccessible> firstChild(nsAccUtils::QueryAccessible(mFirstChild));
if (firstChild) {
nsCOMPtr<nsIAccessible> realParent = firstChild->GetCachedParent();
NS_ASSERTION(!realParent || realParent == this,
"Two accessibles have the same first child accessible.");
}
#endif
PRInt32 childCount = GetChildCount();
NS_ENSURE_TRUE(childCount != -1, NS_ERROR_FAILURE);
NS_IF_ADDREF(*aFirstChild = mFirstChild);
if (childCount > 0)
NS_ADDREF(*aFirstChild = GetChildAt(0));
return NS_OK;
}
/* readonly attribute nsIAccessible lastChild; */
NS_IMETHODIMP nsAccessible::GetLastChild(nsIAccessible * *aLastChild)
{
GetChildAt(-1, aLastChild);
return NS_OK;
}
NS_IMETHODIMP nsAccessible::GetChildAt(PRInt32 aChildNum, nsIAccessible **aChild)
/* readonly attribute nsIAccessible lastChild; */
NS_IMETHODIMP
nsAccessible::GetLastChild(nsIAccessible **aLastChild)
{
// aChildNum is a zero-based index
NS_ENSURE_ARG_POINTER(aLastChild);
*aLastChild = nsnull;
PRInt32 numChildren;
GetChildCount(&numChildren);
PRInt32 childCount = GetChildCount();
NS_ENSURE_TRUE(childCount != -1, NS_ERROR_FAILURE);
// If no children or aChildNum is larger than numChildren, return null
if (aChildNum >= numChildren || numChildren == 0 || !mWeakShell) {
*aChild = nsnull;
return NS_ERROR_FAILURE;
// If aChildNum is less than zero, set aChild to last index
} else if (aChildNum < 0) {
aChildNum = numChildren - 1;
}
NS_IF_ADDREF(*aLastChild = GetChildAt(childCount - 1));
return NS_OK;
}
nsCOMPtr<nsIAccessible> current(mFirstChild), nextSibling;
PRInt32 index = 0;
NS_IMETHODIMP
nsAccessible::GetChildAt(PRInt32 aChildIndex, nsIAccessible **aChild)
{
NS_ENSURE_ARG_POINTER(aChild);
*aChild = nsnull;
while (current) {
nextSibling = current;
if (++index > aChildNum) {
break;
}
nextSibling->GetNextSibling(getter_AddRefs(current));
}
PRInt32 childCount = GetChildCount();
NS_ENSURE_TRUE(childCount != -1, NS_ERROR_FAILURE);
NS_IF_ADDREF(*aChild = nextSibling);
// If child index is negative, then return last child.
// XXX: do we really need this?
if (aChildIndex < 0)
aChildIndex = childCount - 1;
nsIAccessible* child = GetChildAt(aChildIndex);
if (!child)
return NS_ERROR_INVALID_ARG;
NS_ADDREF(*aChild = child);
return NS_OK;
}
// readonly attribute nsIArray children;
NS_IMETHODIMP nsAccessible::GetChildren(nsIArray **aOutChildren)
NS_IMETHODIMP
nsAccessible::GetChildren(nsIArray **aOutChildren)
{
NS_ENSURE_ARG_POINTER(aOutChildren);
*aOutChildren = nsnull;
nsCOMPtr<nsIMutableArray> children = do_CreateInstance(NS_ARRAY_CONTRACTID);
if (!children)
return NS_ERROR_FAILURE;
nsCOMPtr<nsIAccessible> curChild;
while (NextChild(curChild)) {
children->AppendElement(curChild, PR_FALSE);
PRInt32 childCount = GetChildCount();
NS_ENSURE_TRUE(childCount != -1, NS_ERROR_FAILURE);
nsresult rv = NS_OK;
nsCOMPtr<nsIMutableArray> children =
do_CreateInstance(NS_ARRAY_CONTRACTID, &rv);
NS_ENSURE_SUCCESS(rv, rv);
for (PRInt32 childIdx = 0; childIdx < childCount; childIdx++) {
nsIAccessible* child = GetChildAt(childIdx);
children->AppendElement(child, PR_FALSE);
}
NS_ADDREF(*aOutChildren = children);
return NS_OK;
}
@ -735,39 +613,6 @@ nsIAccessible *nsAccessible::NextChild(nsCOMPtr<nsIAccessible>& aAccessible)
return (aAccessible = nextChild);
}
void nsAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount == eChildCountUninitialized) {
mAccChildCount = 0;// Prevent reentry
PRBool allowsAnonChildren = GetAllowsAnonChildAccessibles();
nsAccessibleTreeWalker walker(mWeakShell, mDOMNode, allowsAnonChildren);
// Seed the frame hint early while we're still on a container node.
// This is better than doing the GetPrimaryFrameFor() later on
// a text node, because text nodes aren't in the frame map.
walker.mState.frame = GetFrame();
nsRefPtr<nsAccessible> prevAcc;
PRInt32 childCount = 0;
walker.GetFirstChild();
SetFirstChild(walker.mState.accessible);
while (walker.mState.accessible) {
++ childCount;
prevAcc = nsAccUtils::QueryAccessible(walker.mState.accessible);
prevAcc->SetParent(this);
walker.GetNextSibling();
prevAcc->SetNextSibling(walker.mState.accessible);
}
mAccChildCount = childCount;
}
}
PRBool
nsAccessible::GetAllowsAnonChildAccessibles()
{
@ -775,73 +620,23 @@ nsAccessible::GetAllowsAnonChildAccessibles()
}
/* readonly attribute long childCount; */
NS_IMETHODIMP nsAccessible::GetChildCount(PRInt32 *aAccChildCount)
NS_IMETHODIMP
nsAccessible::GetChildCount(PRInt32 *aChildCount)
{
CacheChildren();
*aAccChildCount = mAccChildCount;
return NS_OK;
NS_ENSURE_ARG_POINTER(aChildCount);
*aChildCount = GetChildCount();
return *aChildCount != -1 ? NS_OK : NS_ERROR_FAILURE;
}
/* readonly attribute long indexInParent; */
NS_IMETHODIMP nsAccessible::GetIndexInParent(PRInt32 *aIndexInParent)
NS_IMETHODIMP
nsAccessible::GetIndexInParent(PRInt32 *aIndexInParent)
{
*aIndexInParent = -1;
if (!mWeakShell) {
return NS_ERROR_FAILURE;
}
NS_ENSURE_ARG_POINTER(aIndexInParent);
nsCOMPtr<nsIAccessible> parent;
GetParent(getter_AddRefs(parent));
if (!parent) {
return NS_ERROR_FAILURE;
}
nsCOMPtr<nsIAccessible> sibling;
parent->GetFirstChild(getter_AddRefs(sibling));
if (!sibling) {
return NS_ERROR_FAILURE;
}
*aIndexInParent = 0;
while (sibling != this) {
NS_ASSERTION(sibling, "Never ran into the same child that we started from");
if (!sibling)
return NS_ERROR_FAILURE;
++*aIndexInParent;
nsCOMPtr<nsIAccessible> tempAccessible;
sibling->GetNextSibling(getter_AddRefs(tempAccessible));
sibling = tempAccessible;
}
return NS_OK;
}
void
nsAccessible::TestChildCache(nsIAccessible *aCachedChild)
{
#ifdef DEBUG_A11Y
// All cached accessible nodes should be in the parent
// It will assert if not all the children were created
// when they were first cached, and no invalidation
// ever corrected parent accessible's child cache.
if (mAccChildCount <= 0)
return;
nsCOMPtr<nsIAccessible> sibling = mFirstChild;
while (sibling != aCachedChild) {
NS_ASSERTION(sibling, "[TestChildCache] Never ran into the same child that we started from");
if (!sibling)
return;
nsCOMPtr<nsIAccessible> tempAccessible;
sibling->GetNextSibling(getter_AddRefs(tempAccessible));
sibling = tempAccessible;
}
#endif
*aIndexInParent = GetIndexInParent();
return *aIndexInParent != -1 ? NS_OK : NS_ERROR_FAILURE;
}
nsresult nsAccessible::GetTranslatedString(const nsAString& aKey, nsAString& aStringOut)
@ -1384,7 +1179,7 @@ NS_IMETHODIMP nsAccessible::SetSelected(PRBool aSelect)
PRUint32 state = nsAccUtils::State(this);
if (state & nsIAccessibleStates::STATE_SELECTABLE) {
nsCOMPtr<nsIAccessible> multiSelect =
nsAccUtils::GetMultiSelectFor(mDOMNode);
nsAccUtils::GetMultiSelectableContainer(mDOMNode);
if (!multiSelect) {
return aSelect ? TakeFocus() : NS_ERROR_FAILURE;
}
@ -1414,7 +1209,7 @@ NS_IMETHODIMP nsAccessible::TakeSelection()
PRUint32 state = nsAccUtils::State(this);
if (state & nsIAccessibleStates::STATE_SELECTABLE) {
nsCOMPtr<nsIAccessible> multiSelect =
nsAccUtils::GetMultiSelectFor(mDOMNode);
nsAccUtils::GetMultiSelectableContainer(mDOMNode);
if (multiSelect) {
nsCOMPtr<nsIAccessibleSelectable> selectable = do_QueryInterface(multiSelect);
selectable->ClearSelection();
@ -3113,8 +2908,247 @@ nsAccessible::GetNameInternal(nsAString& aName)
return NS_OK;
}
void
nsAccessible::SetParent(nsIAccessible *aParent)
{
NS_PRECONDITION(aParent, "This method isn't used to set null parent!");
if (mParent && mParent != aParent) {
// Adopt a child -- we allow this now. the new parent
// may be a dom node which wasn't previously accessible but now is.
// The old parent's children now need to be invalidated, since
// it no longer owns the child, the new parent does
NS_ASSERTION(PR_FALSE, "Adopting child!");
nsRefPtr<nsAccessible> oldParent = nsAccUtils::QueryAccessible(mParent);
if (oldParent)
oldParent->InvalidateChildren();
}
mParent = aParent;
}
void
nsAccessible::InvalidateChildren()
{
PRInt32 childCount = mChildren.Count();
for (PRInt32 childIdx = 0; childIdx < childCount; childIdx++) {
nsRefPtr<nsAccessible> child =
nsAccUtils::QueryObject<nsAccessible>(mChildren.ObjectAt(childIdx));
child->mParent = nsnull;
}
mChildren.Clear();
mAreChildrenInitialized = PR_FALSE;
}
nsIAccessible*
nsAccessible::GetParent()
{
if (IsDefunct())
return nsnull;
if (mParent)
return mParent;
nsCOMPtr<nsIAccessibleDocument> docAccessible(GetDocAccessible());
NS_ASSERTION(docAccessible, "No document accessible for valid accessible!");
if (!docAccessible)
return nsnull;
nsCOMPtr<nsIAccessible> parent;
docAccessible->GetAccessibleInParentChain(mDOMNode, PR_TRUE,
getter_AddRefs(parent));
#ifdef DEBUG
nsRefPtr<nsAccessible> parentAcc = nsAccUtils::QueryAccessible(parent);
NS_ASSERTION(!parentAcc->IsDefunct(), "Defunct parent!");
parentAcc->EnsureChildren();
if (parent != mParent)
NS_WARNING("Bad accessible tree!");
#endif
return parent;
}
nsIAccessible*
nsAccessible::GetChildAt(PRUint32 aIndex)
{
if (EnsureChildren())
return nsnull;
nsIAccessible *child = mChildren.SafeObjectAt(aIndex);
if (!child)
return nsnull;
#ifdef DEBUG
nsRefPtr<nsAccessible> childAcc = nsAccUtils::QueryAccessible(child);
nsCOMPtr<nsIAccessible> realParent = childAcc->mParent;
NS_ASSERTION(!realParent || realParent == this,
"Two accessibles have the same first child accessible!");
#endif
return child;
}
PRInt32
nsAccessible::GetChildCount()
{
return EnsureChildren() ? -1 : mChildren.Count();
}
PRInt32
nsAccessible::GetIndexOf(nsIAccessible *aChild)
{
return EnsureChildren() ? -1 : mChildren.IndexOf(aChild);
}
PRInt32
nsAccessible::GetIndexInParent()
{
nsIAccessible *parent = GetParent();
if (!parent)
return -1;
nsRefPtr<nsAccessible> parentAcc =
nsAccUtils::QueryObject<nsAccessible>(parent);
return parentAcc->GetIndexOf(this);
}
already_AddRefed<nsIAccessible>
nsAccessible::GetCachedParent()
{
if (IsDefunct())
return nsnull;
nsCOMPtr<nsIAccessible> cachedParent = mParent;
return cachedParent.forget();
}
already_AddRefed<nsIAccessible>
nsAccessible::GetCachedFirstChild()
{
if (IsDefunct())
return nsnull;
nsCOMPtr<nsIAccessible> cachedFirstChild = GetChildAt(0);
return cachedFirstChild.forget();
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessible private methods
// nsAccessible protected methods
void
nsAccessible::CacheChildren()
{
PRBool allowsAnonChildren = GetAllowsAnonChildAccessibles();
nsAccessibleTreeWalker walker(mWeakShell, mDOMNode, allowsAnonChildren);
// Seed the frame hint early while we're still on a container node.
// This is better than doing the GetPrimaryFrameFor() later on
// a text node, because text nodes aren't in the frame map.
walker.mState.frame = GetFrame();
walker.GetFirstChild();
while (walker.mState.accessible) {
mChildren.AppendObject(walker.mState.accessible);
nsRefPtr<nsAccessible> acc =
nsAccUtils::QueryObject<nsAccessible>(walker.mState.accessible);
acc->SetParent(this);
walker.GetNextSibling();
}
}
void
nsAccessible::TestChildCache(nsIAccessible *aCachedChild)
{
#ifdef DEBUG_A11Y
// All cached accessible nodes should be in the parent
// It will assert if not all the children were created
// when they were first cached, and no invalidation
// ever corrected parent accessible's child cache.
PRUint32 childCount = mChildren.Count();
if (childCount == 0) {
NS_ASSERTION(mAreChildrenInitialized,
"Children are stored but not initailzied!");
return;
}
for (PRInt32 childIdx = 0; childIdx < childCount; childIdx++) {
nsIAccessible *child = GetChildAt(childIdx);
if (child == aCachedChild)
break;
}
NS_ASSERTION(child == aCachedChild,
"[TestChildCache] cached accessible wasn't found. Wrong accessible tree!");
#endif
}
PRBool
nsAccessible::EnsureChildren()
{
if (IsDefunct()) {
mAreChildrenInitialized = PR_FALSE;
return PR_TRUE;
}
if (mAreChildrenInitialized)
return PR_FALSE;
mAreChildrenInitialized = PR_TRUE; // Prevent reentry
CacheChildren();
return PR_FALSE;
}
nsIAccessible*
nsAccessible::GetSiblingAtOffset(PRInt32 aOffset, nsresult* aError)
{
if (IsDefunct()) {
if (aError)
*aError = NS_ERROR_FAILURE;
return nsnull;
}
nsIAccessible *parent = GetParent();
if (!parent) {
if (aError)
*aError = NS_ERROR_UNEXPECTED;
return nsnull;
}
nsRefPtr<nsAccessible> parentAcc =
nsAccUtils::QueryObject<nsAccessible>(parent);
PRInt32 indexInParent = parentAcc->GetIndexOf(this);
if (indexInParent == -1) {
if (aError)
*aError = NS_ERROR_UNEXPECTED;
return nsnull;
}
if (aError) {
PRInt32 childCount = parentAcc->GetChildCount();
if (indexInParent + aOffset >= childCount) {
*aError = NS_OK; // fail peacefully
return nsnull;
}
}
nsIAccessible *child = parentAcc->GetChildAt(indexInParent + aOffset);
if (aError && !child)
*aError = NS_ERROR_UNEXPECTED;
return child;
}
already_AddRefed<nsIAccessible>
nsAccessible::GetFirstAvailableAccessible(nsIDOMNode *aStartNode)

View file

@ -103,11 +103,11 @@ private:
#define NS_ACCESSIBLE_IMPL_CID \
{ /* 53cfa871-be42-47fc-b416-0033653b3151 */ \
0x53cfa871, \
0xbe42, \
0x47fc, \
{ 0xb4, 0x16, 0x00, 0x33, 0x65, 0x3b, 0x31, 0x51 } \
{ /* 07c5a6d6-4e87-4b57-8613-4c39e1b5150a */ \
0x07c5a6d6, \
0x4e87, \
0x4b57, \
{ 0x86, 0x13, 0x4c, 0x39, 0xe1, 0xb5, 0x15, 0x0a } \
}
class nsAccessible : public nsAccessNodeWrap,
@ -199,22 +199,7 @@ public:
nsIAccessible **aChild);
//////////////////////////////////////////////////////////////////////////////
// Initializing and cache methods
/**
* Set accessible parent.
*/
void SetParent(nsIAccessible *aParent);
/**
* Set first accessible child.
*/
void SetFirstChild(nsIAccessible *aFirstChild);
/**
* Set next sibling accessible.
*/
void SetNextSibling(nsIAccessible *aNextSibling);
// Initializing methods
/**
* Set the ARIA role map entry for a new accessible.
@ -226,10 +211,45 @@ public:
virtual void SetRoleMapEntry(nsRoleMapEntry *aRoleMapEntry);
/**
* Set the child count to -1 (unknown) and null out cached child pointers
* Set accessible parent.
*/
void SetParent(nsIAccessible *aParent);
/**
* Set the child count to -1 (unknown) and null out cached child pointers.
* Should be called when accessible tree is changed because document has
* transformed.
*/
virtual void InvalidateChildren();
//////////////////////////////////////////////////////////////////////////////
// Accessible tree traverse methods
/**
* Return parent accessible.
*/
virtual nsIAccessible* GetParent();
/**
* Return child accessible at the given index.
*/
virtual nsIAccessible* GetChildAt(PRUint32 aIndex);
/**
* Return child accessible count.
*/
virtual PRInt32 GetChildCount();
/**
* Return index of the given child accessible.
*/
virtual PRInt32 GetIndexOf(nsIAccessible *aChild);
/**
* Return index in parent accessible.
*/
PRInt32 GetIndexInParent();
/**
* Return parent accessible only if cached.
*/
@ -240,13 +260,8 @@ public:
*/
already_AddRefed<nsIAccessible> GetCachedFirstChild();
/**
* Assert if child not in parent's cache.
*/
void TestChildCache(nsIAccessible *aCachedChild);
//////////////////////////////////////////////////////////////////////////////
// Miscellaneous methods.
// Miscellaneous methods
/**
* Fire accessible event.
@ -269,22 +284,41 @@ public:
virtual nsresult AppendTextTo(nsAString& aText, PRUint32 aStartOffset,
PRUint32 aLength);
//////////////////////////////////////////////////////////////////////////////
// Helper methods
already_AddRefed<nsIAccessible> GetParent() {
nsIAccessible *parent = nsnull;
GetParent(&parent);
return parent;
}
protected:
//////////////////////////////////////////////////////////////////////////////
// Initializing, cache and tree traverse methods
/**
* Cache accessible children.
*/
virtual void CacheChildren();
/**
* Assert if child not in parent's cache.
*/
void TestChildCache(nsIAccessible *aCachedChild);
/**
* Cache children if necessary. Return true if the accessible is defunct.
*/
PRBool EnsureChildren();
/**
* Return sibling accessible at the given offset.
*/
virtual nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError = nsnull);
//////////////////////////////////////////////////////////////////////////////
// Miscellaneous helpers
virtual nsIFrame* GetBoundsFrame();
virtual void GetBoundsRect(nsRect& aRect, nsIFrame** aRelativeFrame);
PRBool IsVisible(PRBool *aIsOffscreen);
//////////////////////////////////////////////////////////////////////////////
// Name helpers.
// Name helpers
/**
* Compute the name of HTML node.
@ -300,25 +334,6 @@ protected:
static nsresult GetFullKeyName(const nsAString& aModifierName, const nsAString& aKeyName, nsAString& aStringOut);
static nsresult GetTranslatedString(const nsAString& aKey, nsAString& aStringOut);
/**
* Walk into subtree and calculate the string which is used as the accessible
* name or description.
*
* @param aContent [in] traversed content
* @param aFlatString [in, out] result string
* @param aIsRootHidden [in] specifies whether root content (we started to
* traverse from) is hidden, in this case the result
* string is calculated from hidden children
* (this is used when hidden root content is explicitly
* specified as label or description by author)
*/
nsresult AppendFlatStringFromSubtreeRecurse(nsIContent *aContent,
nsAString *aFlatString,
PRBool aIsRootHidden);
// Helpers for dealing with children
virtual void CacheChildren();
// nsCOMPtr<>& is useful here, because getter_AddRefs() nulls the comptr's value, and NextChild
// depends on the passed-in comptr being null or already set to a child (finding the next sibling).
nsIAccessible *NextChild(nsCOMPtr<nsIAccessible>& aAccessible);
@ -436,11 +451,10 @@ protected:
// Data Members
nsCOMPtr<nsIAccessible> mParent;
nsCOMPtr<nsIAccessible> mFirstChild;
nsCOMPtr<nsIAccessible> mNextSibling;
nsCOMArray<nsIAccessible> mChildren;
PRBool mAreChildrenInitialized;
nsRoleMapEntry *mRoleMapEntry; // Non-null indicates author-supplied role; possibly state & value as well
PRInt32 mAccChildCount;
};
NS_DEFINE_STATIC_IID_ACCESSOR(nsAccessible,

View file

@ -77,7 +77,7 @@ void nsAccessibleTreeWalker::GetKids(nsIDOMNode *aParentNode)
mState.frame = nsnull; // Don't walk frames in non-HTML content, just walk the DOM.
}
UpdateFrame(PR_TRUE);
WalkFrames();
// Walk frames? UpdateFrame() sets this when it sees anonymous frames
if (mState.siblingIndex == eSiblingsWalkFrames) {
@ -160,20 +160,40 @@ NS_IMETHODIMP nsAccessibleTreeWalker::PushState()
void nsAccessibleTreeWalker::GetNextDOMNode()
{
// Get next DOM node
// Get next DOM node and its frame.
if (mState.parentContent) {
mState.domNode = do_QueryInterface(mState.parentContent->GetChildAt(++mState.siblingIndex));
}
else if (mState.siblingIndex == eSiblingsWalkFrames) {
if (mState.frame.GetFrame()) {
mState.domNode = do_QueryInterface(mState.frame.GetFrame()->GetContent());
} else {
mState.domNode = nsnull;
mState.domNode =
do_QueryInterface(mState.parentContent->GetChildAt(++mState.siblingIndex));
} else if (mState.siblingIndex == eSiblingsWalkFrames) {
if (mState.frame.IsAlive()) {
mState.frame = mState.frame.GetFrame()->GetNextSibling();
if (mState.frame.IsAlive()) {
mState.domNode = do_QueryInterface(mState.frame.GetFrame()->GetContent());
return;
}
}
mState.domNode = nsnull;
return;
} else {
mState.siblingList->Item(++mState.siblingIndex,
getter_AddRefs(mState.domNode));
}
else {
mState.siblingList->Item(++mState.siblingIndex, getter_AddRefs(mState.domNode));
}
// Update the frame.
nsCOMPtr<nsIPresShell> presShell(do_QueryReferent(mWeakShell));
NS_ASSERTION(presShell, "Huh? No presshell?");
if (!presShell)
return;
nsCOMPtr<nsIContent> content = do_QueryInterface(mState.domNode);
if (content)
mState.frame = presShell->GetRealPrimaryFrameFor(content);
else
mState.frame = presShell->GetRootFrame();
}
NS_IMETHODIMP nsAccessibleTreeWalker::GetNextSibling()
@ -185,7 +205,6 @@ NS_IMETHODIMP nsAccessibleTreeWalker::GetNextSibling()
while (PR_TRUE) {
// Get next frame
UpdateFrame(PR_FALSE);
GetNextDOMNode();
if (!mState.domNode) { // Done with current siblings
@ -219,7 +238,7 @@ NS_IMETHODIMP nsAccessibleTreeWalker::GetFirstChild()
while (mState.domNode) {
if ((mState.domNode != parent && GetAccessible()) || NS_SUCCEEDED(GetFirstChild()))
return NS_OK;
UpdateFrame(PR_FALSE);
GetNextDOMNode();
}
@ -227,50 +246,46 @@ NS_IMETHODIMP nsAccessibleTreeWalker::GetFirstChild()
return NS_ERROR_FAILURE;
}
void nsAccessibleTreeWalker::UpdateFrame(PRBool aTryFirstChild)
void
nsAccessibleTreeWalker::WalkFrames()
{
nsIFrame *curFrame = mState.frame.GetFrame();
if (!curFrame) {
return;
}
if (aTryFirstChild) {
// If the frame implements nsIAnonymousContentCreator interface then go down
// through the frames and obtain anonymous nodes for them.
nsIAnonymousContentCreator* creator = do_QueryFrame(curFrame);
nsIFrame *child = curFrame->GetFirstChild(nsnull);
mState.frame = child;
// If the frame implements nsIAnonymousContentCreator interface then go down
// through the frames and obtain anonymous nodes for them.
nsIAnonymousContentCreator* creator = do_QueryFrame(curFrame);
nsIFrame *child = curFrame->GetFirstChild(nsnull);
if (creator && child && mState.siblingIndex < 0) {
mState.domNode = do_QueryInterface(child->GetContent());
mState.siblingIndex = eSiblingsWalkFrames;
}
if (creator && child && mState.siblingIndex < 0) {
mState.frame = child;
mState.domNode = do_QueryInterface(child->GetContent());
mState.siblingIndex = eSiblingsWalkFrames;
}
// temporary workaround for Bug 359210. We never want to walk frames.
// Aaron Leventhal will refix :before and :after content later without walking frames.
#if 0
if (mState.frame && mState.siblingIndex < 0) {
// Container frames can contain generated content frames from
// :before and :after style rules, so we walk their frame trees
// instead of content trees
// XXX Walking the frame tree doesn't get us Aural CSS nodes, e.g.
// @media screen { display: none; }
// Asking the style system might be better (with ProbePseudoStyleFor(),
// except that we need to ask only for those display types that support
// :before and :after (which roughly means non-replaced elements)
// Here's some code to see if there is an :after rule for an element
// nsRefPtr<nsStyleContext> pseudoContext;
// nsStyleContext *styleContext = primaryFrame->GetStyleContext();
// if (aContent) {
// pseudoContext = presContext->StyleSet()->
// ProbePseudoStyleFor(content, nsAccessibilityAtoms::after, aStyleContext);
mState.domNode = do_QueryInterface(mState.frame->GetContent());
mState.siblingIndex = eSiblingsWalkFrames;
}
if (mState.frame && mState.siblingIndex < 0) {
// Container frames can contain generated content frames from
// :before and :after style rules, so we walk their frame trees
// instead of content trees
// XXX Walking the frame tree doesn't get us Aural CSS nodes, e.g.
// @media screen { display: none; }
// Asking the style system might be better (with ProbePseudoStyleFor(),
// except that we need to ask only for those display types that support
// :before and :after (which roughly means non-replaced elements)
// Here's some code to see if there is an :after rule for an element
// nsRefPtr<nsStyleContext> pseudoContext;
// nsStyleContext *styleContext = primaryFrame->GetStyleContext();
// if (aContent) {
// pseudoContext = presContext->StyleSet()->
// ProbePseudoStyleFor(content, nsAccessibilityAtoms::after, aStyleContext);
mState.domNode = do_QueryInterface(mState.frame->GetContent());
mState.siblingIndex = eSiblingsWalkFrames;
}
#endif
}
else {
mState.frame = curFrame->GetNextSibling();
}
}
/**
@ -286,11 +301,10 @@ PRBool nsAccessibleTreeWalker::GetAccessible()
mState.accessible = nsnull;
nsCOMPtr<nsIPresShell> presShell(do_QueryReferent(mWeakShell));
nsIFrame *frame = mState.frame.GetFrame();
mAccService->GetAccessible(mState.domNode, presShell, mWeakShell,
&frame, &mState.isHidden,
mState.frame.GetFrame(), &mState.isHidden,
getter_AddRefs(mState.accessible));
mState.frame = frame;
return mState.accessible ? PR_TRUE : PR_FALSE;
}

View file

@ -121,12 +121,9 @@ protected:
NS_IMETHOD PopState();
/**
* Change current state so that its frame is changed to next frame.
*
* @param aTryFirstChild [in] points whether we should move to child or
* sibling frame
* Make treewalker traverse by frame tree if necessary.
*/
void UpdateFrame(PRBool aTryFirstChild);
void WalkFrames();
/**
* Change current state so that its node is changed to next node.

View file

@ -42,64 +42,22 @@
#include "nsApplicationAccessible.h"
#include "nsAccessibilityService.h"
#include "nsIComponentManager.h"
#include "nsServiceManagerUtils.h"
nsApplicationAccessible::nsApplicationAccessible():
nsAccessibleWrap(nsnull, nsnull), mChildren(nsnull)
nsApplicationAccessible::nsApplicationAccessible() :
nsAccessibleWrap(nsnull, nsnull)
{
}
////////////////////////////////////////////////////////////////////////////////
// nsISupports
NS_IMPL_CYCLE_COLLECTION_CLASS(nsApplicationAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsApplicationAccessible,
nsAccessible)
nsCOMPtr<nsISimpleEnumerator> enumerator;
tmp->mChildren->Enumerate(getter_AddRefs(enumerator));
nsCOMPtr<nsIWeakReference> childWeakRef;
nsCOMPtr<nsIAccessible> accessible;
PRBool hasMoreElements;
while(NS_SUCCEEDED(enumerator->HasMoreElements(&hasMoreElements))
&& hasMoreElements) {
enumerator->GetNext(getter_AddRefs(childWeakRef));
accessible = do_QueryReferent(childWeakRef);
if (accessible) {
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "nsApplicationAccessible child");
cb.NoteXPCOMChild(accessible);
}
}
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsApplicationAccessible,
nsAccessible)
tmp->mChildren->Clear();
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsApplicationAccessible)
NS_INTERFACE_MAP_END_INHERITING(nsAccessible)
NS_IMPL_ADDREF_INHERITED(nsApplicationAccessible, nsAccessible)
NS_IMPL_RELEASE_INHERITED(nsApplicationAccessible, nsAccessible)
NS_IMPL_ISUPPORTS_INHERITED0(nsApplicationAccessible, nsAccessible)
////////////////////////////////////////////////////////////////////////////////
// nsIAccessNode
nsresult
nsApplicationAccessible::Init()
{
nsresult rv;
mChildren = do_CreateInstance(NS_ARRAY_CONTRACTID, &rv);
return rv;
}
// nsIAccessible
NS_IMETHODIMP
@ -130,19 +88,67 @@ nsApplicationAccessible::GetName(nsAString& aName)
return NS_OK;
}
nsresult
nsApplicationAccessible::GetRoleInternal(PRUint32 *aRole)
NS_IMETHODIMP
nsApplicationAccessible::GetDescription(nsAString& aValue)
{
*aRole = nsIAccessibleRole::ROLE_APP_ROOT;
aValue.Truncate();
return NS_OK;
}
NS_IMETHODIMP
nsApplicationAccessible::GetRole(PRUint32 *aRole)
{
NS_ENSURE_ARG_POINTER(aRole);
return GetRoleInternal(aRole);
}
NS_IMETHODIMP
nsApplicationAccessible::GetState(PRUint32 *aState, PRUint32 *aExtraState)
{
NS_ENSURE_ARG_POINTER(aState);
*aState = 0;
if (aExtraState)
*aExtraState = 0;
return NS_OK;
}
NS_IMETHODIMP
nsApplicationAccessible::GetParent(nsIAccessible **aAccessible)
{
NS_ENSURE_ARG_POINTER(aAccessible);
*aAccessible = nsnull;
return IsDefunct() ? NS_ERROR_FAILURE : NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessNode public methods
PRBool
nsApplicationAccessible::IsDefunct()
{
return nsAccessibilityService::gIsShutdown;
}
nsresult
nsApplicationAccessible::Init()
{
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessible public methods
nsresult
nsApplicationAccessible::GetRoleInternal(PRUint32 *aRole)
{
*aRole = nsIAccessibleRole::ROLE_APP_ROOT;
return NS_OK;
}
nsresult
nsApplicationAccessible::GetStateInternal(PRUint32 *aState,
PRUint32 *aExtraState)
@ -154,124 +160,59 @@ nsApplicationAccessible::GetStateInternal(PRUint32 *aState,
return NS_OK;
}
NS_IMETHODIMP
nsApplicationAccessible::GetParent(nsIAccessible **aParent)
nsIAccessible*
nsApplicationAccessible::GetParent()
{
*aParent = nsnull;
return NS_OK;
return nsnull;
}
NS_IMETHODIMP
nsApplicationAccessible::GetChildAt(PRInt32 aChildNum, nsIAccessible **aChild)
void
nsApplicationAccessible::InvalidateChildren()
{
NS_ENSURE_ARG_POINTER(aChild);
*aChild = nsnull;
PRUint32 count = 0;
nsresult rv = NS_OK;
if (mChildren) {
rv = mChildren->GetLength(&count);
NS_ENSURE_SUCCESS(rv, rv);
}
if (aChildNum >= static_cast<PRInt32>(count) || count == 0)
return NS_ERROR_INVALID_ARG;
if (aChildNum < 0)
aChildNum = count - 1;
nsCOMPtr<nsIWeakReference> childWeakRef;
rv = mChildren->QueryElementAt(aChildNum, NS_GET_IID(nsIWeakReference),
getter_AddRefs(childWeakRef));
NS_ENSURE_SUCCESS(rv, rv);
if (childWeakRef) {
nsCOMPtr<nsIAccessible> childAcc(do_QueryReferent(childWeakRef));
NS_IF_ADDREF(*aChild = childAcc);
}
return NS_OK;
// Do nothing because application children are kept updated by
// AddRootAccessible() and RemoveRootAccessible() method calls.
}
NS_IMETHODIMP
nsApplicationAccessible::GetNextSibling(nsIAccessible **aNextSibling)
{
NS_ENSURE_ARG_POINTER(aNextSibling);
*aNextSibling = nsnull;
return NS_OK;
}
NS_IMETHODIMP
nsApplicationAccessible::GetPreviousSibling(nsIAccessible **aPreviousSibling)
{
NS_ENSURE_ARG_POINTER(aPreviousSibling);
*aPreviousSibling = nsnull;
return NS_OK;
}
NS_IMETHODIMP
nsApplicationAccessible::GetIndexInParent(PRInt32 *aIndexInParent)
{
NS_ENSURE_ARG_POINTER(aIndexInParent);
*aIndexInParent = -1;
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessible protected methods
void
nsApplicationAccessible::CacheChildren()
{
if (!mChildren) {
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount == eChildCountUninitialized) {
mAccChildCount = 0;// Prevent reentry
nsCOMPtr<nsISimpleEnumerator> enumerator;
mChildren->Enumerate(getter_AddRefs(enumerator));
nsCOMPtr<nsIWeakReference> childWeakRef;
nsCOMPtr<nsIAccessible> accessible;
nsRefPtr<nsAccessible> prevAcc;
PRBool hasMoreElements;
while(NS_SUCCEEDED(enumerator->HasMoreElements(&hasMoreElements)) &&
hasMoreElements) {
enumerator->GetNext(getter_AddRefs(childWeakRef));
accessible = do_QueryReferent(childWeakRef);
if (accessible) {
if (prevAcc)
prevAcc->SetNextSibling(accessible);
else
SetFirstChild(accessible);
prevAcc = nsAccUtils::QueryAccessible(accessible);
prevAcc->SetParent(this);
}
}
PRUint32 count = 0;
mChildren->GetLength(&count);
mAccChildCount = static_cast<PRInt32>(count);
}
// Nothing to do. Children are keeped up to dated by Add/RemoveRootAccessible
// method calls.
}
// nsApplicationAccessible
nsIAccessible*
nsApplicationAccessible::GetSiblingAtOffset(PRInt32 aOffset, nsresult* aError)
{
if (IsDefunct()) {
if (aError)
*aError = NS_ERROR_FAILURE;
return nsnull;
}
if (aError)
*aError = NS_OK; // fail peacefully
return nsnull;
}
////////////////////////////////////////////////////////////////////////////////
// Public methods
nsresult
nsApplicationAccessible::AddRootAccessible(nsIAccessible *aRootAccessible)
{
NS_ENSURE_ARG_POINTER(aRootAccessible);
// add by weak reference
nsresult rv = mChildren->AppendElement(aRootAccessible, PR_TRUE);
NS_ENSURE_SUCCESS(rv, rv);
if (!mChildren.AppendObject(aRootAccessible))
return NS_ERROR_FAILURE;
nsRefPtr<nsAccessible> rootAcc = nsAccUtils::QueryAccessible(aRootAccessible);
rootAcc->SetParent(this);
InvalidateChildren();
return NS_OK;
}
@ -280,17 +221,8 @@ nsApplicationAccessible::RemoveRootAccessible(nsIAccessible *aRootAccessible)
{
NS_ENSURE_ARG_POINTER(aRootAccessible);
PRUint32 index = 0;
// we must use weak ref to get the index
nsCOMPtr<nsIWeakReference> weakPtr = do_GetWeakReference(aRootAccessible);
nsresult rv = mChildren->IndexOf(0, weakPtr, &index);
NS_ENSURE_SUCCESS(rv, rv);
rv = mChildren->RemoveElementAt(index);
NS_ENSURE_SUCCESS(rv, rv);
InvalidateChildren();
return NS_OK;
// It's not needed to void root accessible parent because this method is
// called on root accessible shutdown and its parent will be cleared
// properly.
return mChildren.RemoveObject(aRootAccessible) ? NS_OK : NS_ERROR_FAILURE;
}

View file

@ -63,34 +63,36 @@ public:
// nsISupports
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsApplicationAccessible,
nsAccessible)
// nsAccessNode
virtual nsresult Init();
// nsIAccessible
NS_IMETHOD GetName(nsAString & aName);
NS_IMETHOD GetName(nsAString& aName);
NS_IMETHOD GetDescription(nsAString& aValue);
NS_IMETHOD GetRole(PRUint32 *aRole);
NS_IMETHOD GetParent(nsIAccessible * *aParent);
NS_IMETHOD GetNextSibling(nsIAccessible * *aNextSibling);
NS_IMETHOD GetPreviousSibling(nsIAccessible **aPreviousSibling);
NS_IMETHOD GetIndexInParent(PRInt32 *aIndexInParent);
NS_IMETHOD GetChildAt(PRInt32 aChildNum, nsIAccessible **aChild);
NS_IMETHOD GetState(PRUint32 *aState, PRUint32 *aExtraState);
NS_IMETHOD GetParent(nsIAccessible **aAccessible);
// nsAccessNode
virtual PRBool IsDefunct();
virtual nsresult Init();
// nsAccessible
virtual nsresult GetRoleInternal(PRUint32 *aRole);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual nsIAccessible* GetParent();
virtual void InvalidateChildren();
// nsApplicationAccessible
virtual nsresult AddRootAccessible(nsIAccessible *aRootAccWrap);
virtual nsresult RemoveRootAccessible(nsIAccessible *aRootAccWrap);
protected:
// nsAccessible
virtual void CacheChildren();
nsCOMPtr<nsIMutableArray> mChildren;
virtual nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset,
nsresult *aError = nsnull);
};
#endif

View file

@ -65,7 +65,9 @@ nsAccessibleWrap(aNode, aShell)
NS_IMPL_ISUPPORTS_INHERITED0(nsLeafAccessible, nsAccessible)
// nsAccessible::GetChildAtPoint()
////////////////////////////////////////////////////////////////////////////////
// nsLeafAccessible: nsAccessible public
nsresult
nsLeafAccessible::GetChildAtPoint(PRInt32 aX, PRInt32 aY,
PRBool aDeepestChild,
@ -76,12 +78,13 @@ nsLeafAccessible::GetChildAtPoint(PRInt32 aX, PRInt32 aY,
return NS_OK;
}
// nsAccessible::CacheChildren()
////////////////////////////////////////////////////////////////////////////////
// nsLeafAccessible: nsAccessible private
void
nsLeafAccessible::CacheChildren()
{
// No children for leaf accessible.
mAccChildCount = IsDefunct() ? eChildCountUninitialized : 0;
}

View file

@ -1027,7 +1027,7 @@ nsCoreUtils::GetLastSensibleColumn(nsITreeBoxObject *aTree)
}
PRUint32
nsCoreUtils::GetSensiblecolumnCount(nsITreeBoxObject *aTree)
nsCoreUtils::GetSensibleColumnCount(nsITreeBoxObject *aTree)
{
PRUint32 count = 0;

View file

@ -413,7 +413,7 @@ public:
/**
* Return sensible columns count for the given tree box object.
*/
static PRUint32 GetSensiblecolumnCount(nsITreeBoxObject *aTree);
static PRUint32 GetSensibleColumnCount(nsITreeBoxObject *aTree);
/**
* Return sensible column at the given index for the given tree box object.

View file

@ -73,16 +73,16 @@
#include "nsIXULDocument.h"
#endif
//=============================//
// nsDocAccessible //
//=============================//
////////////////////////////////////////////////////////////////////////////////
// Static member initialization
PRUint32 nsDocAccessible::gLastFocusedAccessiblesState = 0;
nsIAtom *nsDocAccessible::gLastFocusedFrameType = nsnull;
//-----------------------------------------------------
// construction
//-----------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
// Constructor/desctructor
nsDocAccessible::nsDocAccessible(nsIDOMNode *aDOMNode, nsIWeakReference* aShell):
nsHyperTextAccessibleWrap(aDOMNode, aShell), mWnd(nsnull),
mScrollPositionChangedTicks(0), mIsContentLoaded(PR_FALSE),
@ -129,15 +129,13 @@ nsDocAccessible::nsDocAccessible(nsIDOMNode *aDOMNode, nsIWeakReference* aShell)
}
}
//-----------------------------------------------------
// destruction
//-----------------------------------------------------
nsDocAccessible::~nsDocAccessible()
{
}
////////////////////////////////////////////////////////////////////////////////
// nsDocAccessible. nsISupports
// nsISupports
static PLDHashOperator
ElementTraverser(const void *aKey, nsIAccessNode *aAccessNode,
@ -182,6 +180,10 @@ NS_INTERFACE_MAP_END_INHERITING(nsHyperTextAccessible)
NS_IMPL_ADDREF_INHERITED(nsDocAccessible, nsHyperTextAccessible)
NS_IMPL_RELEASE_INHERITED(nsDocAccessible, nsHyperTextAccessible)
////////////////////////////////////////////////////////////////////////////////
// nsIAccessible
NS_IMETHODIMP
nsDocAccessible::GetName(nsAString& aName)
{
@ -204,6 +206,7 @@ nsDocAccessible::GetName(nsAString& aName)
return rv;
}
// nsAccessible public method
nsresult
nsDocAccessible::GetRoleInternal(PRUint32 *aRole)
{
@ -242,6 +245,7 @@ nsDocAccessible::GetRoleInternal(PRUint32 *aRole)
return NS_OK;
}
// nsAccessible public method
void
nsDocAccessible::SetRoleMapEntry(nsRoleMapEntry* aRoleMapEntry)
{
@ -282,6 +286,7 @@ nsDocAccessible::GetDescription(nsAString& aDescription)
return NS_OK;
}
// nsAccessible public method
nsresult
nsDocAccessible::GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState)
{
@ -332,6 +337,7 @@ nsDocAccessible::GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState)
return NS_OK;
}
// nsAccessible public method
nsresult
nsDocAccessible::GetARIAState(PRUint32 *aState, PRUint32 *aExtraState)
{
@ -396,7 +402,9 @@ NS_IMETHODIMP nsDocAccessible::TakeFocus()
return NS_ERROR_FAILURE;
}
// ------- nsIAccessibleDocument Methods (5) ---------------
////////////////////////////////////////////////////////////////////////////////
// nsIAccessibleDocument
NS_IMETHODIMP nsDocAccessible::GetURL(nsAString& aURL)
{
@ -499,6 +507,7 @@ NS_IMETHODIMP nsDocAccessible::GetDocument(nsIDOMDocument **aDOMDoc)
return NS_ERROR_FAILURE;
}
// nsIAccessibleHyperText method
NS_IMETHODIMP nsDocAccessible::GetAssociatedEditor(nsIEditor **aEditor)
{
NS_ENSURE_ARG_POINTER(aEditor);
@ -557,6 +566,7 @@ NS_IMETHODIMP nsDocAccessible::GetCachedAccessNode(void *aUniqueID, nsIAccessNod
return NS_OK;
}
// nsDocAccessible public method
void
nsDocAccessible::CacheAccessNode(void *aUniqueID, nsIAccessNode *aAccessNode)
{
@ -574,6 +584,7 @@ nsDocAccessible::CacheAccessNode(void *aUniqueID, nsIAccessNode *aAccessNode)
PutCacheEntry(mAccessNodeCache, aUniqueID, aAccessNode);
}
// nsDocAccessible public method
void
nsDocAccessible::RemoveAccessNodeFromCache(nsIAccessNode *aAccessNode)
{
@ -585,31 +596,8 @@ nsDocAccessible::RemoveAccessNodeFromCache(nsIAccessNode *aAccessNode)
mAccessNodeCache.Remove(uniqueID);
}
NS_IMETHODIMP nsDocAccessible::GetParent(nsIAccessible **aParent)
{
// Hook up our new accessible with our parent
*aParent = nsnull;
NS_ENSURE_TRUE(mDocument, NS_ERROR_FAILURE);
if (!mParent) {
nsIDocument *parentDoc = mDocument->GetParentDocument();
NS_ENSURE_TRUE(parentDoc, NS_ERROR_FAILURE);
nsIContent *ownerContent = parentDoc->FindContentForSubDocument(mDocument);
nsCOMPtr<nsIDOMNode> ownerNode(do_QueryInterface(ownerContent));
if (ownerNode) {
nsCOMPtr<nsIAccessibilityService> accService =
do_GetService("@mozilla.org/accessibilityService;1");
if (accService) {
// XXX aaronl: ideally we would traverse the presshell chain
// Since there's no easy way to do that, we cheat and use
// the document hierarchy. GetAccessibleFor() is bad because
// it doesn't support our concept of multiple presshells per doc.
// It should be changed to use GetAccessibleInWeakShell()
accService->GetAccessibleFor(ownerNode, getter_AddRefs(mParent));
}
}
}
return mParent ? nsAccessible::GetParent(aParent) : NS_ERROR_FAILURE;
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessNode
nsresult
nsDocAccessible::Init()
@ -618,8 +606,7 @@ nsDocAccessible::Init()
AddEventListeners();
nsCOMPtr<nsIAccessible> parentAccessible; // Ensure outer doc mParent accessible
GetParent(getter_AddRefs(parentAccessible));
GetParent(); // Ensure outer doc mParent accessible.
nsresult rv = nsHyperTextAccessibleWrap::Init();
NS_ENSURE_SUCCESS(rv, rv);
@ -680,6 +667,7 @@ nsDocAccessible::Shutdown()
return NS_OK;
}
// nsDocAccessible protected member
void nsDocAccessible::ShutdownChildDocuments(nsIDocShellTreeItem *aStart)
{
nsCOMPtr<nsIDocShellTreeNode> treeNode(do_QueryInterface(aStart));
@ -725,6 +713,7 @@ nsDocAccessible::IsDefunct()
return !mDocument;
}
// nsDocAccessible protected member
void nsDocAccessible::GetBoundsRect(nsRect& aBounds, nsIFrame** aRelativeFrame)
{
*aRelativeFrame = GetFrame();
@ -768,7 +757,7 @@ void nsDocAccessible::GetBoundsRect(nsRect& aBounds, nsIFrame** aRelativeFrame)
}
}
// nsDocAccessible protected member
nsresult nsDocAccessible::AddEventListeners()
{
// 1) Set up scroll position listener
@ -814,6 +803,7 @@ nsresult nsDocAccessible::AddEventListeners()
return NS_OK;
}
// nsDocAccessible protected member
nsresult nsDocAccessible::RemoveEventListeners()
{
// Remove listeners associated with content documents
@ -860,6 +850,7 @@ nsresult nsDocAccessible::RemoveEventListeners()
return NS_OK;
}
// nsDocAccessible public member
void
nsDocAccessible::FireDocLoadEvents(PRUint32 aEventType)
{
@ -889,8 +880,7 @@ nsDocAccessible::FireDocLoadEvents(PRUint32 aEventType)
if (isFinished) {
// Need to wait until scrollable view is available
AddScrollListener();
nsCOMPtr<nsIAccessible> parent(nsAccessible::GetParent());
nsRefPtr<nsAccessible> acc(nsAccUtils::QueryAccessible(parent));
nsRefPtr<nsAccessible> acc(nsAccUtils::QueryAccessible(GetParent()));
if (acc) {
// Make the parent forget about the old document as a child
acc->InvalidateChildren();
@ -954,6 +944,7 @@ void nsDocAccessible::ScrollTimerCallback(nsITimer *aTimer, void *aClosure)
}
}
// nsDocAccessible protected member
void nsDocAccessible::AddScrollListener()
{
nsCOMPtr<nsIPresShell> presShell(do_QueryReferent(mWeakShell));
@ -970,6 +961,7 @@ void nsDocAccessible::AddScrollListener()
scrollableView->AddScrollPositionListener(this);
}
// nsDocAccessible protected member
void nsDocAccessible::RemoveScrollListener()
{
nsCOMPtr<nsIPresShell> presShell(do_QueryReferent(mWeakShell));
@ -986,6 +978,9 @@ void nsDocAccessible::RemoveScrollListener()
scrollableView->RemoveScrollPositionListener(this);
}
////////////////////////////////////////////////////////////////////////////////
// nsIScrollPositionListener
NS_IMETHODIMP nsDocAccessible::ScrollPositionWillChange(nsIScrollableView *aView, nscoord aX, nscoord aY)
{
return NS_OK;
@ -1012,6 +1007,9 @@ NS_IMETHODIMP nsDocAccessible::ScrollPositionDidChange(nsIScrollableView *aScrol
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsIObserver
NS_IMETHODIMP nsDocAccessible::Observe(nsISupports *aSubject, const char *aTopic,
const PRUnichar *aData)
{
@ -1026,7 +1024,7 @@ NS_IMETHODIMP nsDocAccessible::Observe(nsISupports *aSubject, const char *aTopic
return NS_OK;
}
///////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
// nsIDocumentObserver
NS_IMPL_NSIDOCUMENTOBSERVER_CORE_STUB(nsDocAccessible)
@ -1047,7 +1045,7 @@ nsDocAccessible::AttributeWillChange(nsIDocument *aDocument,
void
nsDocAccessible::AttributeChanged(nsIDocument *aDocument, nsIContent* aContent,
PRInt32 aNameSpaceID, nsIAtom* aAttribute,
PRInt32 aModType, PRUint32 aStateMask)
PRInt32 aModType)
{
AttributeChangedImpl(aContent, aNameSpaceID, aAttribute);
@ -1062,7 +1060,7 @@ nsDocAccessible::AttributeChanged(nsIDocument *aDocument, nsIContent* aContent,
}
}
// nsDocAccessible protected member
void
nsDocAccessible::AttributeChangedImpl(nsIContent* aContent, PRInt32 aNameSpaceID, nsIAtom* aAttribute)
{
@ -1171,7 +1169,7 @@ nsDocAccessible::AttributeChangedImpl(nsIContent* aContent, PRInt32 aNameSpaceID
aAttribute == nsAccessibilityAtoms::aria_selected) {
// ARIA or XUL selection
nsCOMPtr<nsIAccessible> multiSelect =
nsAccUtils::GetMultiSelectFor(targetNode);
nsAccUtils::GetMultiSelectableContainer(targetNode);
// Multi selects use selection_add and selection_remove
// Single select widgets just mirror event_selection for
// whatever gets event_focus, which is done in
@ -1213,6 +1211,7 @@ nsDocAccessible::AttributeChangedImpl(nsIContent* aContent, PRInt32 aNameSpaceID
}
}
// nsDocAccessible protected member
void
nsDocAccessible::ARIAAttributeChanged(nsIContent* aContent, nsIAtom* aAttribute)
{
@ -1362,6 +1361,7 @@ void nsDocAccessible::ContentAppended(nsIDocument *aDocument,
}
}
void nsDocAccessible::ContentStatesChanged(nsIDocument* aDocument,
nsIContent* aContent1,
nsIContent* aContent2,
@ -1417,6 +1417,45 @@ nsDocAccessible::ParentChainChanged(nsIContent *aContent)
{
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessible
nsIAccessible*
nsDocAccessible::GetParent()
{
if (IsDefunct())
return nsnull;
if (mParent)
return mParent;
nsIDocument* parentDoc = mDocument->GetParentDocument();
if (!parentDoc)
return nsnull;
nsIContent* ownerContent = parentDoc->FindContentForSubDocument(mDocument);
nsCOMPtr<nsIDOMNode> ownerNode(do_QueryInterface(ownerContent));
if (ownerNode) {
nsCOMPtr<nsIAccessibilityService> accService = GetAccService();
if (accService) {
// XXX aaronl: ideally we would traverse the presshell chain. Since
// there's no easy way to do that, we cheat and use the document
// hierarchy. GetAccessibleFor() is bad because it doesn't support our
// concept of multiple presshells per doc.
// It should be changed to use GetAccessibleInWeakShell()
accService->GetAccessibleFor(ownerNode, getter_AddRefs(mParent));
}
}
NS_ASSERTION(mParent, "No parent for not root document accessible!");
return mParent;
}
////////////////////////////////////////////////////////////////////////////////
// Protected members
void
nsDocAccessible::FireValueChangeForTextFields(nsIAccessible *aPossibleTextFieldAccessible)
{
@ -1571,7 +1610,8 @@ nsDocAccessible::CreateTextChangeEventForNode(nsIAccessible *aContainerAccessibl
return event;
}
// nsDocAccessible public member
nsresult
nsDocAccessible::FireDelayedAccessibleEvent(PRUint32 aEventType,
nsIDOMNode *aDOMNode,
@ -1585,6 +1625,7 @@ nsDocAccessible::FireDelayedAccessibleEvent(PRUint32 aEventType,
return FireDelayedAccessibleEvent(event);
}
// nsDocAccessible public member
nsresult
nsDocAccessible::FireDelayedAccessibleEvent(nsIAccessibleEvent *aEvent)
{
@ -1953,6 +1994,7 @@ void nsDocAccessible::RefreshNodes(nsIDOMNode *aStartNode)
mAccessNodeCache.Remove(uniqueID);
}
// nsDocAccessible public member
void
nsDocAccessible::InvalidateCacheSubtree(nsIContent *aChild,
PRUint32 aChangeType)
@ -2180,6 +2222,7 @@ nsDocAccessible::InvalidateCacheSubtree(nsIContent *aChild,
FireDelayedAccessibleEvent(reorderEvent);
}
// nsIAccessibleDocument method
NS_IMETHODIMP
nsDocAccessible::GetAccessibleInParentChain(nsIDOMNode *aNode,
PRBool aCanCreate,

View file

@ -87,7 +87,6 @@ public:
NS_IMETHOD GetDescription(nsAString& aDescription);
NS_IMETHOD GetAttributes(nsIPersistentProperties **aAttributes);
NS_IMETHOD GetFocusedChild(nsIAccessible **aFocusedChild);
NS_IMETHOD GetParent(nsIAccessible **aParent);
NS_IMETHOD TakeFocus(void);
// nsIScrollPositionListener
@ -111,7 +110,9 @@ public:
virtual nsresult GetRoleInternal(PRUint32 *aRole);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual nsresult GetARIAState(PRUint32 *aState, PRUint32 *aExtraState);
virtual void SetRoleMapEntry(nsRoleMapEntry* aRoleMapEntry);
virtual nsIAccessible* GetParent();
// nsIAccessibleText
NS_IMETHOD GetAssociatedEditor(nsIEditor **aEditor);

View file

@ -99,25 +99,11 @@ nsOuterDocAccessible::GetChildAtPoint(PRInt32 aX, PRInt32 aY,
return NS_OK;
}
void nsOuterDocAccessible::CacheChildren()
{
// An outer doc accessible usually has 1 nsDocAccessible child,
// but could have none if we can't get to the inner documnet
if (!mWeakShell) {
mAccChildCount = eChildCountUninitialized;
return; // This outer doc node has been shut down
}
if (mAccChildCount != eChildCountUninitialized) {
return;
}
InvalidateChildren();
mAccChildCount = 0;
// In these variable names, "outer" relates to the nsOuterDocAccessible
// as opposed to the nsDocAccessibleWrap which is "inner".
// The outer node is a something like a <browser>, <frame>, <iframe>, <page> or
// <editor> tag, whereas the inner node corresponds to the inner document root.
void
nsOuterDocAccessible::CacheChildren()
{
// An outer doc accessible usually has 1 nsDocAccessible child, but could have
// none if we can't get to the inner documnet.
nsCOMPtr<nsIContent> content(do_QueryInterface(mDOMNode));
NS_ASSERTION(content, "No nsIContent for <browser>/<iframe>/<editor> dom node");
@ -134,18 +120,15 @@ void nsOuterDocAccessible::CacheChildren()
}
nsCOMPtr<nsIAccessible> innerAccessible;
nsCOMPtr<nsIAccessibilityService> accService =
do_GetService("@mozilla.org/accessibilityService;1");
nsCOMPtr<nsIAccessibilityService> accService = GetAccService();
accService->GetAccessibleFor(innerNode, getter_AddRefs(innerAccessible));
nsRefPtr<nsAccessible> innerAcc(nsAccUtils::QueryAccessible(innerAccessible));
if (!innerAcc)
return;
// Success getting inner document as first child -- now we cache it.
mAccChildCount = 1;
SetFirstChild(innerAccessible); // weak ref
mChildren.AppendObject(innerAccessible);
innerAcc->SetParent(this);
innerAcc->SetNextSibling(nsnull);
}
nsresult

View file

@ -42,8 +42,14 @@
#include "nsAccessibleWrap.h"
#include "nsIAccessible.h"
class nsIWeakReference;
/**
* Used for <browser>, <frame>, <iframe>, <page> or editor> elements.
*
* In these variable names, "outer" relates to the nsOuterDocAccessible as
* opposed to the nsDocAccessibleWrap which is "inner". The outer node is
* a something like tags listed above, whereas the inner node corresponds to
* the inner document root.
*/
class nsOuterDocAccessible : public nsAccessibleWrap
{
// XXX: why is it private?
@ -70,7 +76,7 @@ public:
protected:
// nsAccessible
void CacheChildren();
virtual void CacheChildren();
};
#endif

View file

@ -84,6 +84,9 @@
#include "nsIXULWindow.h"
#endif
////////////////////////////////////////////////////////////////////////////////
// nsISupports
// Expanded version of NS_IMPL_ISUPPORTS_INHERITED2
// so we can QI directly to concrete nsRootAccessible
NS_IMPL_QUERY_HEAD(nsRootAccessible)
@ -96,21 +99,21 @@ NS_IMPL_QUERY_TAIL_INHERITING(nsDocAccessible)
NS_IMPL_ADDREF_INHERITED(nsRootAccessible, nsDocAccessible)
NS_IMPL_RELEASE_INHERITED(nsRootAccessible, nsDocAccessible)
//-----------------------------------------------------
// construction
//-----------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
// Constructor/desctructor
nsRootAccessible::nsRootAccessible(nsIDOMNode *aDOMNode, nsIWeakReference* aShell):
nsDocAccessibleWrap(aDOMNode, aShell)
{
}
//-----------------------------------------------------
// destruction
//-----------------------------------------------------
nsRootAccessible::~nsRootAccessible()
{
}
////////////////////////////////////////////////////////////////////////////////
// nsIAccessible
/* readonly attribute AString name; */
NS_IMETHODIMP
nsRootAccessible::GetName(nsAString& aName)
@ -132,21 +135,6 @@ nsRootAccessible::GetName(nsAString& aName)
return document->GetTitle(aName);
}
/* readonly attribute nsIAccessible accParent; */
NS_IMETHODIMP nsRootAccessible::GetParent(nsIAccessible * *aParent)
{
NS_ENSURE_ARG_POINTER(aParent);
*aParent = nsnull;
if (!mParent) {
nsRefPtr<nsApplicationAccessibleWrap> root = GetApplicationAccessible();
mParent = root;
}
NS_IF_ADDREF(*aParent = mParent);
return NS_OK;
}
/* readonly attribute unsigned long accRole; */
nsresult
nsRootAccessible::GetRoleInternal(PRUint32 *aRole)
@ -172,6 +160,7 @@ nsRootAccessible::GetRoleInternal(PRUint32 *aRole)
return nsDocAccessibleWrap::GetRoleInternal(aRole);
}
// nsRootAccessible protected member
#ifdef MOZ_XUL
PRUint32 nsRootAccessible::GetChromeFlags()
{
@ -581,7 +570,8 @@ void nsRootAccessible::FireCurrentFocusEvent()
}
}
// --------------- nsIDOMEventListener Methods (3) ------------------------
////////////////////////////////////////////////////////////////////////////////
// nsIDOMEventListener
NS_IMETHODIMP nsRootAccessible::HandleEvent(nsIDOMEvent* aEvent)
{
@ -595,6 +585,8 @@ NS_IMETHODIMP nsRootAccessible::HandleEvent(nsIDOMEvent* aEvent)
return HandleEventWithTarget(aEvent, targetNode);
}
// nsRootAccessible protected member
nsresult nsRootAccessible::HandleEventWithTarget(nsIDOMEvent* aEvent,
nsIDOMNode* aTargetNode)
{
@ -946,6 +938,9 @@ void nsRootAccessible::FireFocusCallback(nsITimer *aTimer, void *aClosure)
rootAccessible->FireCurrentFocusEvent();
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessNode
nsresult
nsRootAccessible::Init()
{
@ -980,6 +975,7 @@ nsRootAccessible::Shutdown()
return nsDocAccessibleWrap::Shutdown();
}
// nsRootAccessible protected member
already_AddRefed<nsIDocShellTreeItem>
nsRootAccessible::GetContentDocShell(nsIDocShellTreeItem *aStart)
{
@ -1036,6 +1032,7 @@ nsRootAccessible::GetContentDocShell(nsIDocShellTreeItem *aStart)
return nsnull;
}
// nsIAccessible method
NS_IMETHODIMP
nsRootAccessible::GetRelationByType(PRUint32 aRelationType,
nsIAccessibleRelation **aRelation)
@ -1062,6 +1059,20 @@ nsRootAccessible::GetRelationByType(PRUint32 aRelationType,
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsAccessible
nsIAccessible*
nsRootAccessible::GetParent()
{
// Parent has been setted in nsApplicationAccesible::AddRootAccessible()
// when root accessible was intialized.
return mParent;
}
////////////////////////////////////////////////////////////////////////////////
// nsDocAccessible
void
nsRootAccessible::FireDocLoadEvents(PRUint32 aEventType)
{
@ -1084,6 +1095,9 @@ nsRootAccessible::FireDocLoadEvents(PRUint32 aEventType)
aEventType == nsIAccessibleEvent::EVENT_DOCUMENT_LOAD_STOPPED);
}
////////////////////////////////////////////////////////////////////////////////
// Protected members
nsresult
nsRootAccessible::HandlePopupShownEvent(nsIAccessible *aAccessible)
{

View file

@ -74,7 +74,6 @@ public:
// nsIAccessible
NS_IMETHOD GetName(nsAString& aName);
NS_IMETHOD GetParent(nsIAccessible * *aParent);
NS_IMETHOD GetRelationByType(PRUint32 aRelationType,
nsIAccessibleRelation **aRelation);
@ -88,6 +87,7 @@ public:
// nsAccessible
virtual nsresult GetRoleInternal(PRUint32 *aRole);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual nsIAccessible* GetParent();
// nsDocAccessible
virtual void FireDocLoadEvents(PRUint32 aEventType);

View file

@ -70,5 +70,4 @@ void
nsTextAccessible::CacheChildren()
{
// No children for text accessible.
mAccChildCount = IsDefunct() ? eChildCountUninitialized : 0;
}

View file

@ -155,5 +155,4 @@ void
nsHTMLAreaAccessible::CacheChildren()
{
// No children for aria accessible.
mAccChildCount = IsDefunct() ? eChildCountUninitialized : 0;
}

View file

@ -155,42 +155,28 @@ nsHTMLImageAccessible::GetRoleInternal(PRUint32 *aRole)
return NS_OK;
}
void nsHTMLImageAccessible::CacheChildren()
void
nsHTMLImageAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount != eChildCountUninitialized) {
return;
}
mAccChildCount = 0;
nsCOMPtr<nsIDOMHTMLCollection> mapAreas = GetAreaCollection();
if (!mapAreas)
return;
PRUint32 numMapAreas;
mapAreas->GetLength(&numMapAreas);
PRInt32 childCount = 0;
PRUint32 areaCount = 0;
mapAreas->GetLength(&areaCount);
nsCOMPtr<nsIAccessible> areaAccessible;
nsRefPtr<nsAccessible> prevAcc;
while (childCount < (PRInt32)numMapAreas &&
(areaAccessible = GetAreaAccessible(mapAreas, childCount)) != nsnull) {
if (prevAcc)
prevAcc->SetNextSibling(areaAccessible);
else
SetFirstChild(areaAccessible);
nsRefPtr<nsAccessible> areaAcc;
++ childCount;
for (PRUint32 areaIdx = 0; areaIdx < areaCount; areaIdx++) {
areaAccessible = GetAreaAccessible(mapAreas, areaIdx);
if (!areaAccessible)
return;
prevAcc = nsAccUtils::QueryAccessible(areaAccessible);
prevAcc->SetParent(this);
mChildren.AppendObject(areaAccessible);
areaAcc = nsAccUtils::QueryObject<nsAccessible>(areaAccessible);
areaAcc->SetParent(this);
}
mAccChildCount = childCount;
}
NS_IMETHODIMP

View file

@ -83,6 +83,7 @@ protected:
// nsAccessible
virtual void CacheChildren();
// nsHTMLImageAccessible
already_AddRefed<nsIDOMHTMLCollection> GetAreaCollection();
already_AddRefed<nsIAccessible>
GetAreaAccessible(nsIDOMHTMLCollection* aAreaNodes, PRInt32 aAreaNum);

View file

@ -305,7 +305,9 @@ NS_IMETHODIMP nsHTMLSelectableAccessible::SelectAllSelection(PRBool *_retval)
/** First, the common widgets */
/** ------------------------------------------------------ */
/** ----- nsHTMLSelectListAccessible ----- */
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectListAccessible
////////////////////////////////////////////////////////////////////////////////
/** Default Constructor */
nsHTMLSelectListAccessible::nsHTMLSelectListAccessible(nsIDOMNode* aDOMNode,
@ -314,11 +316,9 @@ nsHTMLSelectListAccessible::nsHTMLSelectListAccessible(nsIDOMNode* aDOMNode,
{
}
/**
* As a nsHTMLSelectListAccessible we can have the following states:
* nsIAccessibleStates::STATE_MULTISELECTABLE
* nsIAccessibleStates::STATE_EXTSELECTABLE
*/
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectListAccessible: nsAccessible public
nsresult
nsHTMLSelectListAccessible::GetStateInternal(PRUint32 *aState,
PRUint32 *aExtraState)
@ -327,6 +327,10 @@ nsHTMLSelectListAccessible::GetStateInternal(PRUint32 *aState,
aExtraState);
NS_ENSURE_A11Y_SUCCESS(rv, rv);
// As a nsHTMLSelectListAccessible we can have the following states:
// nsIAccessibleStates::STATE_MULTISELECTABLE
// nsIAccessibleStates::STATE_EXTSELECTABLE
nsCOMPtr<nsIDOMHTMLSelectElement> select (do_QueryInterface(mDOMNode));
if (select) {
if (*aState & nsIAccessibleStates::STATE_FOCUSED) {
@ -360,109 +364,63 @@ nsHTMLSelectListAccessible::GetRoleInternal(PRUint32 *aRole)
return NS_OK;
}
already_AddRefed<nsIAccessible>
nsHTMLSelectListAccessible::AccessibleForOption(nsIAccessibilityService *aAccService,
nsIContent *aContent,
nsIAccessible *aLastGoodAccessible,
PRInt32 *aChildCount)
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectListAccessible: nsAccessible protected
void
nsHTMLSelectListAccessible::CacheChildren()
{
nsCOMPtr<nsIDOMNode> domNode(do_QueryInterface(aContent));
NS_ASSERTION(domNode, "DOM node is null");
// Accessibility service will initialize & cache any accessibles created
nsCOMPtr<nsIAccessible> accessible;
aAccService->GetAccessibleInWeakShell(domNode, mWeakShell, getter_AddRefs(accessible));
nsRefPtr<nsAccessible> acc(nsAccUtils::QueryAccessible(accessible));
if (!acc)
return nsnull;
++ *aChildCount;
acc->SetParent(this);
nsRefPtr<nsAccessible> prevAcc =
nsAccUtils::QueryAccessible(aLastGoodAccessible);
if (prevAcc)
prevAcc->SetNextSibling(accessible);
if (!mFirstChild)
mFirstChild = accessible;
return accessible.forget();
// Cache accessibles for <optgroup> and <option> DOM decendents as children,
// as well as the accessibles for them. Avoid whitespace text nodes. We want
// to count all the <optgroup>s and <option>s as children because we want
// a flat tree under the Select List.
nsCOMPtr<nsIContent> selectContent(do_QueryInterface(mDOMNode));
CacheOptSiblings(selectContent);
}
already_AddRefed<nsIAccessible>
nsHTMLSelectListAccessible::CacheOptSiblings(nsIAccessibilityService *aAccService,
nsIContent *aParentContent,
nsIAccessible *aLastGoodAccessible,
PRInt32 *aChildCount)
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectListAccessible protected
void
nsHTMLSelectListAccessible::CacheOptSiblings(nsIContent *aParentContent)
{
// Recursive helper for CacheChildren()
PRUint32 numChildren = aParentContent->GetChildCount();
nsCOMPtr<nsIAccessible> lastGoodAccessible(aLastGoodAccessible);
nsCOMPtr<nsIAccessible> newAccessible;
for (PRUint32 count = 0; count < numChildren; count ++) {
nsIContent *childContent = aParentContent->GetChildAt(count);
if (!childContent->IsHTML()) {
continue;
}
nsCOMPtr<nsIAtom> tag = childContent->Tag();
if (tag == nsAccessibilityAtoms::option || tag == nsAccessibilityAtoms::optgroup) {
newAccessible = AccessibleForOption(aAccService,
childContent,
lastGoodAccessible,
aChildCount);
if (newAccessible) {
lastGoodAccessible = newAccessible;
}
if (tag == nsAccessibilityAtoms::optgroup) {
newAccessible = CacheOptSiblings(aAccService, childContent,
lastGoodAccessible, aChildCount);
if (newAccessible) {
lastGoodAccessible = newAccessible;
}
if (tag == nsAccessibilityAtoms::option ||
tag == nsAccessibilityAtoms::optgroup) {
// Get an accessible for option or optgroup and cache it.
nsCOMPtr<nsIDOMNode> childNode(do_QueryInterface(childContent));
nsCOMPtr<nsIAccessible> accessible;
GetAccService()->GetAccessibleInWeakShell(childNode, mWeakShell,
getter_AddRefs(accessible));
if (accessible) {
mChildren.AppendObject(accessible);
nsRefPtr<nsAccessible> acc =
nsAccUtils::QueryObject<nsAccessible>(accessible);
acc->SetParent(this);
}
// Deep down into optgroup element.
if (tag == nsAccessibilityAtoms::optgroup)
CacheOptSiblings(childContent);
}
}
if (lastGoodAccessible) {
nsRefPtr<nsAccessible> lastAcc =
nsAccUtils::QueryAccessible(lastGoodAccessible);
lastAcc->SetNextSibling(nsnull);
}
return lastGoodAccessible.forget();
}
/**
* Cache the children and child count of a Select List Accessible. We want to count
* all the <optgroup>s and <option>s as children because we want a
* flat tree under the Select List.
*/
void nsHTMLSelectListAccessible::CacheChildren()
{
// Cache the number of <optgroup> and <option> DOM decendents,
// as well as the accessibles for them. Avoid whitespace text nodes.
nsCOMPtr<nsIContent> selectContent(do_QueryInterface(mDOMNode));
nsCOMPtr<nsIAccessibilityService> accService(do_GetService("@mozilla.org/accessibilityService;1"));
if (!selectContent || !accService) {
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount != eChildCountUninitialized) {
return;
}
mAccChildCount = 0; // Avoid reentry
PRInt32 childCount = 0;
nsCOMPtr<nsIAccessible> lastGoodAccessible =
CacheOptSiblings(accService, selectContent, nsnull, &childCount);
mAccChildCount = childCount;
}
/** ----- nsHTMLSelectOptionAccessible ----- */
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectOptionAccessible
////////////////////////////////////////////////////////////////////////////////
/** Default Constructor */
nsHTMLSelectOptionAccessible::nsHTMLSelectOptionAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell):
@ -837,7 +795,7 @@ void nsHTMLSelectOptionAccessible::SelectionChangedIfOption(nsIContent *aPossibl
NS_ASSERTION(optionNode, "No option node for nsIContent with option tag!");
nsCOMPtr<nsIAccessible> multiSelect =
nsAccUtils::GetMultiSelectFor(optionNode);
nsAccUtils::GetMultiSelectableContainer(optionNode);
if (!multiSelect)
return;
@ -885,7 +843,9 @@ nsIContent* nsHTMLSelectOptionAccessible::GetSelectState(PRUint32* aState,
return nsnull;
}
/** ----- nsHTMLSelectOptGroupAccessible ----- */
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectOptGroupAccessible
////////////////////////////////////////////////////////////////////////////////
/** Default Constructor */
nsHTMLSelectOptGroupAccessible::nsHTMLSelectOptGroupAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell):
@ -929,29 +889,26 @@ NS_IMETHODIMP nsHTMLSelectOptGroupAccessible::GetNumActions(PRUint8 *_retval)
return NS_ERROR_NOT_IMPLEMENTED;
}
void nsHTMLSelectOptGroupAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLSelectOptGroupAccessible: nsAccessible protected
if (mAccChildCount == eChildCountUninitialized) {
// XXX To do (bug 378612) - create text child for the anonymous attribute content, so that
// nsIAccessibleText is supported for the <optgroup> as it is for an <option>
// Attribute content is what layout creates for the label="foo" on the <optgroup>
// See eStyleContentType_Attr and CreateAttributeContent() in nsCSSFrameConstructor
mAccChildCount = 0;
SetFirstChild(nsnull);
}
void
nsHTMLSelectOptGroupAccessible::CacheChildren()
{
// XXX To do (bug 378612) - create text child for the anonymous attribute
// content, so that nsIAccessibleText is supported for the <optgroup> as it is
// for an <option>. Attribute content is what layout creates for
// the label="foo" on the <optgroup>. See eStyleContentType_Attr and
// CreateAttributeContent() in nsCSSFrameConstructor
}
/** ------------------------------------------------------ */
/** Finally, the Combobox widgets */
/** ------------------------------------------------------ */
/** ----- nsHTMLComboboxAccessible ----- */
////////////////////////////////////////////////////////////////////////////////
// nsHTMLComboboxAccessible
////////////////////////////////////////////////////////////////////////////////
nsHTMLComboboxAccessible::nsHTMLComboboxAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell):
nsAccessibleWrap(aDOMNode, aShell)
@ -966,46 +923,32 @@ nsHTMLComboboxAccessible::GetRoleInternal(PRUint32 *aRole)
return NS_OK;
}
void nsHTMLComboboxAccessible::CacheChildren()
void
nsHTMLComboboxAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
nsIFrame* frame = GetFrame();
if (!frame)
return;
nsIComboboxControlFrame *comboFrame = do_QueryFrame(frame);
if (!comboFrame)
return;
nsIFrame *listFrame = comboFrame->GetDropDown();
if (!listFrame)
return;
if (!mListAccessible) {
mListAccessible =
new nsHTMLComboboxListAccessible(mParent, mDOMNode, mWeakShell);
if (!mListAccessible)
return;
mListAccessible->Init();
}
if (mAccChildCount == eChildCountUninitialized) {
mAccChildCount = 0;
nsIFrame *frame = GetFrame();
if (!frame) {
return;
}
nsIComboboxControlFrame *comboFrame = do_QueryFrame(frame);
if (!comboFrame) {
return;
}
nsIFrame *listFrame = comboFrame->GetDropDown();
if (!listFrame) {
return;
}
if (!mListAccessible) {
mListAccessible =
new nsHTMLComboboxListAccessible(mParent, mDOMNode, mWeakShell);
if (!mListAccessible)
return;
mListAccessible->Init();
}
SetFirstChild(mListAccessible);
mListAccessible->SetParent(this);
mListAccessible->SetNextSibling(nsnull);
++ mAccChildCount; // List accessible child successfully added
}
mChildren.AppendObject(mListAccessible);
mListAccessible->SetParent(this);
}
nsresult
@ -1154,6 +1097,7 @@ NS_IMETHODIMP nsHTMLComboboxAccessible::GetActionName(PRUint8 aIndex, nsAString&
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLComboboxListAccessible
////////////////////////////////////////////////////////////////////////////////
@ -1205,13 +1149,6 @@ nsHTMLComboboxListAccessible::GetStateInternal(PRUint32 *aState,
return NS_OK;
}
/** Return our cached parent */
NS_IMETHODIMP nsHTMLComboboxListAccessible::GetParent(nsIAccessible **aParent)
{
NS_IF_ADDREF(*aParent = mParent);
return NS_OK;
}
NS_IMETHODIMP nsHTMLComboboxListAccessible::GetUniqueID(void **aUniqueID)
{
// Since mDOMNode is same for all tree item, use |this| pointer as the unique Id
@ -1227,11 +1164,10 @@ void nsHTMLComboboxListAccessible::GetBoundsRect(nsRect& aBounds, nsIFrame** aBo
{
*aBoundingFrame = nsnull;
nsCOMPtr<nsIAccessible> comboAccessible;
GetParent(getter_AddRefs(comboAccessible));
if (!comboAccessible) {
nsCOMPtr<nsIAccessible> comboAccessible = GetParent();
if (!comboAccessible)
return;
}
if (0 == (nsAccUtils::State(comboAccessible) & nsIAccessibleStates::STATE_COLLAPSED)) {
nsHTMLSelectListAccessible::GetBoundsRect(aBounds, aBoundingFrame);
return;
@ -1259,3 +1195,10 @@ void nsHTMLComboboxListAccessible::GetBoundsRect(nsRect& aBounds, nsIFrame** aBo
*aBoundingFrame = frame->GetParent();
aBounds = (*aBoundingFrame)->GetRect();
}
// nsHTMLComboboxListAccessible. nsAccessible public mehtod
nsIAccessible*
nsHTMLComboboxListAccessible::GetParent()
{
return mParent;
}

View file

@ -130,18 +130,16 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
void CacheChildren();
already_AddRefed<nsIAccessible>
AccessibleForOption(nsIAccessibilityService *aAccService,
nsIContent *aContent,
nsIAccessible *aLastGoodAccessible,
PRInt32 *aChildCount);
already_AddRefed<nsIAccessible>
CacheOptSiblings(nsIAccessibilityService *aAccService,
nsIContent *aParentContent,
nsIAccessible *aLastGoodAccessible,
PRInt32 *aChildCount);
// nsAccessible
virtual void CacheChildren();
// nsHTMLSelectListAccessible
/**
* Recursive helper for CacheChildren().
*/
void CacheOptSiblings(nsIContent *aParentContent);
};
/*
@ -201,7 +199,8 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
void CacheChildren();
// nsAccessible
virtual void CacheChildren();
};
/** ------------------------------------------------------ */
@ -236,8 +235,10 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
void CacheChildren();
// nsAccessible
virtual void CacheChildren();
// nsHTMLComboboxAccessible
already_AddRefed<nsIAccessible> GetFocusedOptionAccessible();
private:
@ -259,7 +260,6 @@ public:
virtual ~nsHTMLComboboxListAccessible() {}
// nsIAccessible
NS_IMETHOD GetParent(nsIAccessible **aParent);
NS_IMETHOD GetUniqueID(void **aUniqueID);
// nsAccessNode
@ -268,6 +268,7 @@ public:
// nsAccessible
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual void GetBoundsRect(nsRect& aBounds, nsIFrame** aBoundingFrame);
virtual nsIAccessible* GetParent();
};
#endif

View file

@ -432,6 +432,10 @@ nsHTMLTableHeaderCellAccessible::GetRoleInternal(PRUint32 *aRole)
}
}
// No elements in siblings what means the table has one column only. Therefore
// it should be column header.
*aRole = nsIAccessibleRole::ROLE_COLUMNHEADER;
return NS_OK;
}
@ -455,47 +459,27 @@ NS_IMPL_ISUPPORTS_INHERITED2(nsHTMLTableAccessible, nsAccessible,
////////////////////////////////////////////////////////////////////////////////
// nsHTMLTableAccessible: nsAccessible implementation
void nsHTMLTableAccessible::CacheChildren()
void
nsHTMLTableAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount == eChildCountUninitialized) {
nsAccessible::CacheChildren();
nsCOMPtr<nsIAccessible> captionAccessible;
while (NextChild(captionAccessible)) {
if (nsAccUtils::Role(captionAccessible) == nsIAccessibleRole::ROLE_CAPTION) {
nsCOMPtr<nsIAccessible> captionParentAccessible;
captionAccessible->GetParent(getter_AddRefs(captionParentAccessible));
if (captionParentAccessible != this) {
NS_WARNING("Should not happen: parser ensures caption is the table's child, not the tbody's");
return;
}
nsCOMPtr<nsIAccessible> beforeCaptionAccessible;
captionAccessible->GetPreviousSibling(getter_AddRefs(beforeCaptionAccessible));
if (beforeCaptionAccessible) {
// Move caption accessible so that it's the first child
nsRefPtr<nsAccessible> acc =
nsAccUtils::QueryAccessible(beforeCaptionAccessible);
nsAccessible::CacheChildren();
nsCOMPtr<nsIAccessible> afterCaptionAccessible;
captionAccessible->GetNextSibling(getter_AddRefs(afterCaptionAccessible));
acc->SetNextSibling(afterCaptionAccessible);
// Move caption accessible so that it's the first child.
PRInt32 length = mChildren.Count();
for (PRInt32 idx = 0; idx < length; idx++) {
// Check for the first caption, because nsAccessibilityService ensures we
// don't create accessibles for the other captions, since only the first is
// actually visible.
GetFirstChild(getter_AddRefs(afterCaptionAccessible));
SetFirstChild(captionAccessible);
acc = nsAccUtils::QueryAccessible(captionAccessible);
acc->SetNextSibling(afterCaptionAccessible);
}
// Don't check for more captions, because nsAccessibilityService ensures
// we don't create accessibles for the other captions, since only the
// first is actually visible
nsIAccessible* child = mChildren.ObjectAt(idx);
if (nsAccUtils::Role(child) == nsIAccessibleRole::ROLE_CAPTION) {
if (idx == 0)
break;
}
nsCOMPtr<nsIAccessible> tmp = mChildren.ObjectAt(0);
mChildren.ReplaceObjectAt(child, 0);
mChildren.ReplaceObjectAt(tmp, idx);
break;
}
}
}

View file

@ -263,20 +263,19 @@ NS_IMETHODIMP nsHTMLLIAccessible::GetBounds(PRInt32 *x, PRInt32 *y, PRInt32 *wid
return NS_OK;
}
void nsHTMLLIAccessible::CacheChildren()
////////////////////////////////////////////////////////////////////////////////
// nsHTMLLIAccessible: nsAccessible protected
void
nsHTMLLIAccessible::CacheChildren()
{
if (!mWeakShell || mAccChildCount != eChildCountUninitialized) {
return;
}
nsAccessibleWrap::CacheChildren();
if (mBulletAccessible) {
mBulletAccessible->SetNextSibling(mFirstChild);
mChildren.AppendObject(mBulletAccessible);
mBulletAccessible->SetParent(this);
SetFirstChild(mBulletAccessible);
++ mAccChildCount;
}
// Cache children from subtree.
nsAccessibleWrap::CacheChildren();
}
////////////////////////////////////////////////////////////////////////////////
@ -332,15 +331,6 @@ nsHTMLListBulletAccessible::GetStateInternal(PRUint32 *aState, PRUint32 *aExtraS
return NS_OK;
}
NS_IMETHODIMP
nsHTMLListBulletAccessible::GetParent(nsIAccessible **aParent)
{
NS_ENSURE_ARG_POINTER(aParent);
NS_IF_ADDREF(*aParent = mParent);
return NS_OK;
}
nsresult
nsHTMLListBulletAccessible::AppendTextTo(nsAString& aText, PRUint32 aStartOffset,
PRUint32 aLength)
@ -353,6 +343,12 @@ nsHTMLListBulletAccessible::AppendTextTo(nsAString& aText, PRUint32 aStartOffset
return NS_OK;
}
nsIAccessible*
nsHTMLListBulletAccessible::GetParent()
{
return mParent;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLListAccessible
////////////////////////////////////////////////////////////////////////////////

View file

@ -106,7 +106,6 @@ public:
// nsIAccessible
NS_IMETHOD GetName(nsAString& aName);
NS_IMETHOD GetParent(nsIAccessible **aParent);
// nsAccessNode
virtual nsresult Shutdown();
@ -117,6 +116,8 @@ public:
virtual nsresult AppendTextTo(nsAString& aText, PRUint32 aStartOffset,
PRUint32 aLength);
virtual nsIAccessible* GetParent();
protected:
// XXX: Ideally we'd get the bullet text directly from the bullet frame via
// nsBulletFrame::GetListItemText(), but we'd need an interface for getting
@ -161,8 +162,10 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
void CacheChildren(); // Include bullet accessible
// nsAccessible
virtual void CacheChildren();
private:
nsRefPtr<nsHTMLListBulletAccessible> mBulletAccessible;
};

View file

@ -201,49 +201,44 @@ nsHyperTextAccessible::GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState)
return NS_OK;
}
void nsHyperTextAccessible::CacheChildren()
void
nsHyperTextAccessible::CacheChildren()
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
PRUint32 role;
GetRoleInternal(&role);
if (role != nsIAccessibleRole::ROLE_ENTRY &&
role != nsIAccessibleRole::ROLE_PASSWORD_TEXT) {
nsAccessible::CacheChildren();
return;
}
// Special case for text entry fields, go directly to editor's root for children
if (mAccChildCount == eChildCountUninitialized) {
PRUint32 role;
GetRoleInternal(&role);
if (role != nsIAccessibleRole::ROLE_ENTRY && role != nsIAccessibleRole::ROLE_PASSWORD_TEXT) {
nsAccessible::CacheChildren();
return;
}
nsCOMPtr<nsIEditor> editor;
GetAssociatedEditor(getter_AddRefs(editor));
if (!editor) {
nsAccessible::CacheChildren();
return;
}
mAccChildCount = 0; // Avoid reentry
nsCOMPtr<nsIDOMElement> editorRoot;
editor->GetRootElement(getter_AddRefs(editorRoot));
nsCOMPtr<nsIDOMNode> editorRootDOMNode = do_QueryInterface(editorRoot);
if (!editorRootDOMNode) {
return;
}
nsAccessibleTreeWalker walker(mWeakShell, editorRootDOMNode, PR_TRUE);
nsRefPtr<nsAccessible> prevAcc;
PRInt32 childCount = 0;
walker.GetFirstChild();
SetFirstChild(walker.mState.accessible);
nsCOMPtr<nsIEditor> editor;
GetAssociatedEditor(getter_AddRefs(editor));
if (!editor) {
nsAccessible::CacheChildren();
return;
}
while (walker.mState.accessible) {
++ childCount;
prevAcc = nsAccUtils::QueryAccessible(walker.mState.accessible);
prevAcc->SetParent(this);
walker.GetNextSibling();
prevAcc->SetNextSibling(walker.mState.accessible);
}
mAccChildCount = childCount;
// Special case for text entry fields, go directly to editor's root for
// children.
nsCOMPtr<nsIDOMElement> editorRoot;
editor->GetRootElement(getter_AddRefs(editorRoot));
nsCOMPtr<nsIDOMNode> editorRootDOMNode = do_QueryInterface(editorRoot);
if (!editorRootDOMNode)
return;
nsAccessibleTreeWalker walker(mWeakShell, editorRootDOMNode, PR_TRUE);
walker.GetFirstChild();
while (walker.mState.accessible) {
mChildren.AppendObject(walker.mState.accessible);
nsRefPtr<nsAccessible> acc =
nsAccUtils::QueryObject<nsAccessible>(walker.mState.accessible);
acc->SetParent(this);
walker.GetNextSibling();
}
}
@ -866,10 +861,11 @@ nsHyperTextAccessible::GetRelativeOffset(nsIPresShell *aPresShell,
hyperTextOffset = 0;
}
else if (aAmount == eSelectBeginLine) {
nsIAccessible *firstChild = mChildren.SafeObjectAt(0);
// For line selection with needsStart, set start of line exactly to line break
if (pos.mContentOffset == 0 && mFirstChild &&
nsAccUtils::Role(mFirstChild) == nsIAccessibleRole::ROLE_STATICTEXT &&
nsAccUtils::TextLength(mFirstChild) == hyperTextOffset) {
if (pos.mContentOffset == 0 && firstChild &&
nsAccUtils::Role(firstChild) == nsIAccessibleRole::ROLE_STATICTEXT &&
nsAccUtils::TextLength(firstChild) == hyperTextOffset) {
// XXX Bullet hack -- we should remove this once list bullets use anonymous content
hyperTextOffset = 0;
}

View file

@ -86,7 +86,6 @@ public:
virtual nsresult GetAttributesInternal(nsIPersistentProperties *aAttributes);
virtual nsresult GetRoleInternal(PRUint32 *aRole);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
void CacheChildren();
// Convert content offset to rendered text offset
static nsresult ContentToRenderedOffset(nsIFrame *aFrame, PRInt32 aContentOffset,
@ -155,6 +154,12 @@ public:
PRInt32 *aEndOffset);
protected:
// nsAccessible
virtual void CacheChildren();
// nsHyperTextAccessible
/*
* This does the work for nsIAccessibleText::GetText[At|Before|After]Offset
* @param aType, eGetBefore, eGetAt, eGetAfter

View file

@ -1105,28 +1105,23 @@ __try {
if (mEnumVARIANTPosition == kIEnumVariantDisconnected)
return CO_E_OBJNOTCONNECTED;
nsCOMPtr<nsIAccessible> traversedAcc;
nsresult rv = GetChildAt(mEnumVARIANTPosition, getter_AddRefs(traversedAcc));
if (!traversedAcc)
return S_FALSE;
PRUint32 numElementsFetched = 0;
for (; numElementsFetched < aNumElementsRequested;
numElementsFetched++, mEnumVARIANTPosition++) {
for (PRUint32 i = 0; i < aNumElementsRequested; i++) {
VariantInit(&aPVar[i]);
aPVar[i].pdispVal = NativeAccessible(traversedAcc);
aPVar[i].vt = VT_DISPATCH;
(*aNumElementsFetched)++;
nsCOMPtr<nsIAccessible> nextAcc;
traversedAcc->GetNextSibling(getter_AddRefs(nextAcc));
if (!nextAcc)
nsIAccessible* accessible = GetChildAt(mEnumVARIANTPosition);
if (!accessible)
break;
traversedAcc = nextAcc;
VariantInit(&aPVar[numElementsFetched]);
aPVar[numElementsFetched].pdispVal = NativeAccessible(accessible);
aPVar[numElementsFetched].vt = VT_DISPATCH;
}
mEnumVARIANTPosition += *aNumElementsFetched;
return (*aNumElementsFetched) < aNumElementsRequested ? S_FALSE : S_OK;
(*aNumElementsFetched) = numElementsFetched;
return numElementsFetched < aNumElementsRequested ? S_FALSE : S_OK;
} __except(nsAccessNodeWrap::FilterA11yExceptions(::GetExceptionCode(), GetExceptionInformation())) { }
return E_FAIL;

View file

@ -49,6 +49,9 @@ nsHTMLWin32ObjectOwnerAccessible::
nsAccessibleWrap(aNode, aShell)
{
mHwnd = aHwnd;
// Our only child is a nsHTMLWin32ObjectAccessible object.
mNativeAccessible = new nsHTMLWin32ObjectAccessible(mHwnd);
}
////////////////////////////////////////////////////////////////////////////////
@ -62,50 +65,6 @@ nsHTMLWin32ObjectOwnerAccessible::Shutdown()
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLWin32ObjectOwnerAccessible: nsIAccessible implementation
NS_IMETHODIMP
nsHTMLWin32ObjectOwnerAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
NS_ENSURE_ARG_POINTER(aFirstChild);
*aFirstChild = nsnull;
// Our only child is a nsHTMLWin32ObjectAccessible object.
if (!mNativeAccessible) {
if (!mHwnd)
return NS_OK;
mNativeAccessible = new nsHTMLWin32ObjectAccessible(mHwnd);
NS_ENSURE_TRUE(mNativeAccessible, NS_ERROR_OUT_OF_MEMORY);
SetFirstChild(mNativeAccessible);
}
*aFirstChild = mNativeAccessible;
NS_IF_ADDREF(*aFirstChild);
return NS_OK;
}
NS_IMETHODIMP
nsHTMLWin32ObjectOwnerAccessible::GetLastChild(nsIAccessible **aLastChild)
{
return GetFirstChild(aLastChild);
}
NS_IMETHODIMP
nsHTMLWin32ObjectOwnerAccessible::GetChildCount(PRInt32 *aChildCount)
{
NS_ENSURE_ARG_POINTER(aChildCount);
nsCOMPtr<nsIAccessible> onlyChild;
GetFirstChild(getter_AddRefs(onlyChild));
*aChildCount = onlyChild ? 1 : 0;
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLWin32ObjectOwnerAccessible: nsAccessible implementation
@ -134,6 +93,21 @@ nsHTMLWin32ObjectOwnerAccessible::GetStateInternal(PRUint32 *aState,
return rv;
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLWin32ObjectOwnerAccessible: nsAccessible protected implementation
void
nsHTMLWin32ObjectOwnerAccessible::CacheChildren()
{
if (mNativeAccessible) {
mChildren.AppendObject(mNativeAccessible);
nsRefPtr<nsAccessible> nativeAcc =
nsAccUtils::QueryObject<nsAccessible>(mNativeAccessible);
nativeAcc->SetParent(this);
}
}
////////////////////////////////////////////////////////////////////////////////
// nsHTMLWin32ObjectAccessible

View file

@ -56,11 +56,6 @@ public:
nsHTMLWin32ObjectOwnerAccessible(nsIDOMNode* aNode, nsIWeakReference* aShell, void* aHwnd);
virtual ~nsHTMLWin32ObjectOwnerAccessible() {}
// nsIAccessible
NS_IMETHOD GetFirstChild(nsIAccessible **aFirstChild);
NS_IMETHOD GetLastChild(nsIAccessible **aLastChild);
NS_IMETHOD GetChildCount(PRInt32 *aChildCount); // Zero or one child
// nsAccessNode
virtual nsresult Shutdown();
@ -69,6 +64,10 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
// nsAccessible
virtual void CacheChildren();
void* mHwnd;
nsCOMPtr<nsIAccessible> mNativeAccessible;
};

View file

@ -105,16 +105,6 @@ nsXFormsAccessible::GetBoundChildElementValue(const nsAString& aTagName,
void
nsXFormsAccessible::CacheSelectChildren(nsIDOMNode *aContainerNode)
{
if (!mWeakShell) {
// This node has been shut down
mAccChildCount = eChildCountUninitialized;
return;
}
if (mAccChildCount != eChildCountUninitialized)
return;
mAccChildCount = 0; // Avoid reentry
nsIAccessibilityService *accService = GetAccService();
if (!accService)
return;
@ -133,7 +123,7 @@ nsXFormsAccessible::CacheSelectChildren(nsIDOMNode *aContainerNode)
children->GetLength(&length);
nsCOMPtr<nsIAccessible> accessible;
nsRefPtr<nsAccessible> currAccessible, prevAccessible;
nsRefPtr<nsAccessible> acc;
PRUint32 childLength = 0;
for (PRUint32 index = 0; index < length; index++) {
@ -143,22 +133,13 @@ nsXFormsAccessible::CacheSelectChildren(nsIDOMNode *aContainerNode)
continue;
accService->GetAttachedAccessibleFor(child, getter_AddRefs(accessible));
currAccessible = nsAccUtils::QueryAccessible(accessible);
if (!currAccessible)
if (!accessible)
continue;
if (childLength == 0)
SetFirstChild(accessible);
currAccessible->SetParent(this);
if (prevAccessible) {
prevAccessible->SetNextSibling(accessible);
}
currAccessible.swap(prevAccessible);
childLength++;
mChildren.AppendObject(accessible);
acc = nsAccUtils::QueryObject<nsAccessible>(accessible);
acc->SetParent(this);
}
mAccChildCount = childLength;
}
// nsIAccessible

View file

@ -211,7 +211,10 @@ public:
// nsAccessible
virtual nsresult GetRoleInternal(PRUint32 *aRole);
void CacheChildren();
protected:
// nsAccessible
virtual void CacheChildren();
};
@ -227,7 +230,10 @@ public:
// nsAccessible
virtual nsresult GetRoleInternal(PRUint32 *aRole);
void CacheChildren();
protected:
// nsAccessible
virtual void CacheChildren();
};

View file

@ -98,7 +98,8 @@ public:
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
protected:
void CacheChildren();
// nsAccessible
virtual void CacheChildren();
};
#endif

View file

@ -166,16 +166,6 @@ nsXULColorPickerAccessible::GetRoleInternal(PRUint32 *aRole)
void
nsXULColorPickerAccessible::CacheChildren()
{
if (IsDefunct()) {
mAccChildCount = eChildCountUninitialized;
return; // This outer doc node has been shut down
}
if (mAccChildCount != eChildCountUninitialized)
return;
mAccChildCount = 0; // Avoid reentry
nsCOMPtr<nsIAccessible> menupopupAccessible;
nsAccessibleTreeWalker walker(mWeakShell, mDOMNode, PR_TRUE);
walker.GetFirstChild();
@ -183,23 +173,17 @@ nsXULColorPickerAccessible::CacheChildren()
while (walker.mState.accessible) {
PRUint32 role = nsAccUtils::Role(walker.mState.accessible);
// Get an accessbile for menupopup or panel elements.
if (role == nsIAccessibleRole::ROLE_ALERT) {
// Get an accessbile for menupopup or panel elements.
menupopupAccessible = walker.mState.accessible;
break;
mChildren.AppendObject(walker.mState.accessible);
nsRefPtr<nsAccessible> menupopupAcc =
nsAccUtils::QueryObject<nsAccessible>(walker.mState.accessible);
menupopupAcc->SetParent(this);
return;
}
walker.GetNextSibling();
}
if (!menupopupAccessible)
return;
SetFirstChild(menupopupAccessible);
nsRefPtr<nsAccessible> menupopupAcc =
nsAccUtils::QueryObject<nsAccessible>(menupopupAccessible);
menupopupAcc->SetParent(this);
mAccChildCount++;
}

View file

@ -186,78 +186,61 @@ nsXULButtonAccessible::CacheChildren()
// buttons can have button (@type="menu-button") and popup accessibles
// (@type="menu-button" or @type="menu").
if (!mWeakShell) {
mAccChildCount = eChildCountUninitialized;
return; // This outer doc node has been shut down
// XXX: no children until the button is menu button. Probably it's not
// totally correct but in general AT wants to have leaf buttons.
nsCOMPtr<nsIContent> content(do_QueryInterface(mDOMNode));
PRBool isMenu = content->AttrValueIs(kNameSpaceID_None,
nsAccessibilityAtoms::type,
nsAccessibilityAtoms::menu,
eCaseMatters);
PRBool isMenuButton = isMenu ?
PR_FALSE :
content->AttrValueIs(kNameSpaceID_None, nsAccessibilityAtoms::type,
nsAccessibilityAtoms::menuButton, eCaseMatters);
if (!isMenu && !isMenuButton)
return;
nsCOMPtr<nsIAccessible> buttonAccessible;
nsCOMPtr<nsIAccessible> menupopupAccessible;
nsAccessibleTreeWalker walker(mWeakShell, mDOMNode, PR_TRUE);
walker.GetFirstChild();
while (walker.mState.accessible) {
PRUint32 role = nsAccUtils::Role(walker.mState.accessible);
if (role == nsIAccessibleRole::ROLE_MENUPOPUP) {
// Get an accessbile for menupopup or panel elements.
menupopupAccessible = walker.mState.accessible;
} else if (isMenuButton && role == nsIAccessibleRole::ROLE_PUSHBUTTON) {
// Button type="menu-button" contains a real button. Get an accessible
// for it. Ignore dropmarker button what is placed as a last child.
buttonAccessible = walker.mState.accessible;
break;
}
walker.GetNextSibling();
}
if (mAccChildCount == eChildCountUninitialized) {
mAccChildCount = 0; // Avoid reentry
SetFirstChild(nsnull);
if (!menupopupAccessible)
return;
// XXX: no children until the button is menu button. Probably it's not
// totally correct but in general AT wants to have leaf buttons.
nsCOMPtr<nsIContent> content(do_QueryInterface(mDOMNode));
mChildren.AppendObject(menupopupAccessible);
PRBool isMenu = content->AttrValueIs(kNameSpaceID_None,
nsAccessibilityAtoms::type,
nsAccessibilityAtoms::menu,
eCaseMatters);
nsRefPtr<nsAccessible> menupopupAcc =
nsAccUtils::QueryObject<nsAccessible>(menupopupAccessible);
menupopupAcc->SetParent(this);
PRBool isMenuButton = isMenu ?
PR_FALSE :
content->AttrValueIs(kNameSpaceID_None, nsAccessibilityAtoms::type,
nsAccessibilityAtoms::menuButton, eCaseMatters);
if (buttonAccessible) {
mChildren.AppendObject(buttonAccessible);
if (!isMenu && !isMenuButton)
return;
nsCOMPtr<nsIAccessible> buttonAccessible;
nsCOMPtr<nsIAccessible> menupopupAccessible;
nsAccessibleTreeWalker walker(mWeakShell, mDOMNode, PR_TRUE);
walker.GetFirstChild();
while (walker.mState.accessible) {
PRUint32 role = nsAccUtils::Role(walker.mState.accessible);
if (role == nsIAccessibleRole::ROLE_MENUPOPUP) {
// Get an accessbile for menupopup or panel elements.
menupopupAccessible = walker.mState.accessible;
} else if (isMenuButton && role == nsIAccessibleRole::ROLE_PUSHBUTTON) {
// Button type="menu-button" contains a real button. Get an accessible
// for it. Ignore dropmarker button what is placed as a last child.
buttonAccessible = walker.mState.accessible;
break;
}
walker.GetNextSibling();
}
if (!menupopupAccessible)
return;
SetFirstChild(menupopupAccessible);
nsRefPtr<nsAccessible> menupopupAcc =
nsAccUtils::QueryObject<nsAccessible>(menupopupAccessible);
menupopupAcc->SetParent(this);
mAccChildCount++;
if (buttonAccessible) {
if (menupopupAcc)
menupopupAcc->SetNextSibling(buttonAccessible);
else
SetFirstChild(buttonAccessible);
nsRefPtr<nsAccessible> buttonAcc =
nsAccUtils::QueryObject<nsAccessible>(buttonAccessible);
buttonAcc->SetParent(this);
mAccChildCount++;
}
nsRefPtr<nsAccessible> buttonAcc =
nsAccUtils::QueryObject<nsAccessible>(buttonAccessible);
buttonAcc->SetParent(this);
}
}

View file

@ -76,7 +76,7 @@ public:
protected:
// nsAccessible
void CacheChildren();
virtual void CacheChildren();
// nsXULButtonAccessible
PRBool ContainsMenu();

View file

@ -236,15 +236,6 @@ nsXULTabBoxAccessible::GetRoleInternal(PRUint32 *aRole)
return NS_OK;
}
#ifdef NEVER
/** 2 children, tabs, tabpanels */
NS_IMETHODIMP nsXULTabBoxAccessible::GetChildCount(PRInt32 *_retval)
{
*_retval = 2;
return NS_OK;
}
#endif
/**
* XUL Tabs - the s really stands for strip. this is a collection of tab objects
*/

View file

@ -220,83 +220,6 @@ nsXULTreeAccessible::GetRoleInternal(PRUint32 *aRole)
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeAccessible: nsIAccessible implementation
NS_IMETHODIMP
nsXULTreeAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
nsAccessible::GetFirstChild(aFirstChild);
// in normal case, tree's first child should be treecols, if it is not here,
// use the first row as tree's first child
if (*aFirstChild == nsnull) {
if (IsDefunct())
return NS_ERROR_FAILURE;
PRInt32 rowCount;
mTreeView->GetRowCount(&rowCount);
if (rowCount > 0)
GetTreeItemAccessible(0, aFirstChild);
}
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeAccessible::GetLastChild(nsIAccessible **aLastChild)
{
NS_ENSURE_ARG_POINTER(aLastChild);
*aLastChild = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
PRInt32 rowCount = 0;
mTreeView->GetRowCount(&rowCount);
if (rowCount > 0) {
GetTreeItemAccessible(rowCount - 1, aLastChild);
if (*aLastChild)
return NS_OK;
}
// If there is not any rows, use treecols as tree's last child.
return nsAccessible::GetLastChild(aLastChild);
}
NS_IMETHODIMP
nsXULTreeAccessible::GetChildCount(PRInt32 *aChildCount)
{
// tree's children count is row count + treecols count.
if (IsDefunct())
return NS_ERROR_FAILURE;
nsAccessible::GetChildCount(aChildCount);
if (*aChildCount != eChildCountUninitialized) {
PRInt32 rowCount = 0;
mTreeView->GetRowCount(&rowCount);
*aChildCount += rowCount;
}
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeAccessible::GetChildAt(PRInt32 aChildIndex, nsIAccessible **aChild)
{
NS_ENSURE_ARG_POINTER(aChild);
*aChild = nsnull;
PRInt32 childCount = 0;
nsresult rv = nsAccessible::GetChildCount(&childCount);
NS_ENSURE_SUCCESS(rv, rv);
if (aChildIndex < childCount)
return nsAccessible::GetChildAt(aChildIndex, aChild);
GetTreeItemAccessible(aChildIndex - childCount, aChild);
return *aChild ? NS_OK : NS_ERROR_INVALID_ARG;
}
NS_IMETHODIMP
nsXULTreeAccessible::GetFocusedChild(nsIAccessible **aFocusedChild)
{
@ -535,6 +458,56 @@ nsXULTreeAccessible::SelectAllSelection(PRBool *aIsMultiSelectable)
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeAccessible: nsAccessible implementation
nsIAccessible*
nsXULTreeAccessible::GetChildAt(PRUint32 aIndex)
{
PRInt32 childCount = nsAccessible::GetChildCount();
if (childCount == -1)
return nsnull;
if (static_cast<PRInt32>(aIndex) < childCount)
return nsAccessible::GetChildAt(aIndex);
nsCOMPtr<nsIAccessible> child;
GetTreeItemAccessible(aIndex - childCount, getter_AddRefs(child));
return child;
}
PRInt32
nsXULTreeAccessible::GetChildCount()
{
// tree's children count is row count + treecols count.
PRInt32 childCount = nsAccessible::GetChildCount();
if (childCount == -1)
return -1;
PRInt32 rowCount = 0;
mTreeView->GetRowCount(&rowCount);
childCount += rowCount;
return childCount;
}
PRInt32
nsXULTreeAccessible::GetIndexOf(nsIAccessible *aChild)
{
if (IsDefunct())
return -1;
nsRefPtr<nsXULTreeItemAccessibleBase> item =
nsAccUtils::QueryObject<nsXULTreeItemAccessibleBase>(aChild);
// If the given child is not treeitem then it should be treecols accessible.
if (!item)
return nsAccessible::GetIndexOf(aChild);
return nsAccessible::GetChildCount() + item->GetRowIndex();
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeAccessible: public implementation
@ -774,67 +747,6 @@ nsXULTreeItemAccessibleBase::GetUniqueID(void **aUniqueID)
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessibleBase: nsIAccessible implementation
NS_IMETHODIMP
nsXULTreeItemAccessibleBase::GetParent(nsIAccessible **aParent)
{
NS_ENSURE_ARG_POINTER(aParent);
*aParent = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
if (mParent) {
*aParent = mParent;
NS_ADDREF(*aParent);
}
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessibleBase::GetNextSibling(nsIAccessible **aNextSibling)
{
NS_ENSURE_ARG_POINTER(aNextSibling);
*aNextSibling = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsRefPtr<nsXULTreeAccessible> treeAcc =
nsAccUtils::QueryAccessibleTree(mParent);
NS_ENSURE_STATE(treeAcc);
PRInt32 rowCount = 0;
mTreeView->GetRowCount(&rowCount);
if (mRow + 1 >= rowCount)
return NS_OK;
treeAcc->GetTreeItemAccessible(mRow + 1, aNextSibling);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessibleBase::GetPreviousSibling(nsIAccessible **aPreviousSibling)
{
NS_ENSURE_ARG_POINTER(aPreviousSibling);
*aPreviousSibling = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsRefPtr<nsXULTreeAccessible> treeAcc =
nsAccUtils::QueryAccessibleTree(mParent);
NS_ENSURE_STATE(treeAcc);
// Get previous row accessible or tree columns accessible.
if (mRow > 0)
treeAcc->GetTreeItemAccessible(mRow - 1, aPreviousSibling);
else
treeAcc->GetFirstChild(aPreviousSibling);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessibleBase::GetFocusedChild(nsIAccessible **aFocusedChild)
{
@ -1048,7 +960,7 @@ nsXULTreeItemAccessibleBase::Shutdown()
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessibleBase: nsAccessible implementation
// nsXULTreeItemAccessibleBase: nsAccessible public methods
nsresult
nsXULTreeItemAccessibleBase::GetAttributesInternal(nsIPersistentProperties *aAttributes)
@ -1158,8 +1070,14 @@ nsXULTreeItemAccessibleBase::GetStateInternal(PRUint32 *aState,
return NS_OK;
}
nsIAccessible*
nsXULTreeItemAccessibleBase::GetParent()
{
return IsDefunct() ? nsnull : mParent.get();
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessibleBase: protected implementation
// nsXULTreeItemAccessibleBase: nsAccessible protected methods
void
nsXULTreeItemAccessibleBase::DispatchClickEvent(nsIContent *aContent,
@ -1190,6 +1108,41 @@ nsXULTreeItemAccessibleBase::DispatchClickEvent(nsIContent *aContent,
nsCoreUtils::DispatchClickEvent(mTree, mRow, column, pseudoElm);
}
nsIAccessible*
nsXULTreeItemAccessibleBase::GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError)
{
if (mRow + aOffset < 0)
return nsAccessible::GetSiblingAtOffset(mRow + aOffset, aError);
if (IsDefunct()) {
if (aError)
*aError = NS_ERROR_FAILURE;
return nsnull;
}
if (aError)
*aError = NS_OK; // fail peacefully
nsRefPtr<nsXULTreeAccessible> treeAcc =
nsAccUtils::QueryAccessibleTree(mParent);
if (!treeAcc)
return nsnull;
PRInt32 rowCount = 0;
mTreeView->GetRowCount(&rowCount);
if (mRow + aOffset >= rowCount)
return nsnull;
nsCOMPtr<nsIAccessible> sibling;
treeAcc->GetTreeItemAccessible(mRow + aOffset, getter_AddRefs(sibling));
return sibling;
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessibleBase: protected implementation
PRBool
nsXULTreeItemAccessibleBase::IsExpandable()
{
@ -1230,33 +1183,6 @@ nsXULTreeItemAccessible(nsIDOMNode *aDOMNode, nsIWeakReference *aShell,
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessible: nsIAccessible implementation
NS_IMETHODIMP
nsXULTreeItemAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
NS_ENSURE_ARG_POINTER(aFirstChild);
*aFirstChild = nsnull;
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessible::GetLastChild(nsIAccessible **aLastChild)
{
NS_ENSURE_ARG_POINTER(aLastChild);
*aLastChild = nsnull;
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessible::GetChildCount(PRInt32 *aChildCount)
{
NS_ENSURE_ARG_POINTER(aChildCount);
*aChildCount = 0;
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeItemAccessible::GetName(nsAString& aName)
{
@ -1338,6 +1264,14 @@ nsXULTreeItemAccessible::RowInvalidated(PRInt32 aStartColIdx,
}
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeItemAccessible: nsAccessible protected implementation
void
nsXULTreeItemAccessible::CacheChildren()
{
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeColumnsAccessible
@ -1349,11 +1283,22 @@ nsXULTreeColumnsAccessible::
{
}
NS_IMETHODIMP
nsXULTreeColumnsAccessible::GetNextSibling(nsIAccessible **aNextSibling)
nsIAccessible*
nsXULTreeColumnsAccessible::GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError)
{
NS_ENSURE_ARG_POINTER(aNextSibling);
*aNextSibling = nsnull;
if (aOffset < 0)
return nsXULColumnsAccessible::GetSiblingAtOffset(aOffset, aError);
if (IsDefunct()) {
if (aError)
*aError = NS_ERROR_FAILURE;
return nsnull;
}
if (aError)
*aError = NS_OK; // fail peacefully
nsCOMPtr<nsITreeBoxObject> tree;
nsCOMPtr<nsITreeView> treeView;
@ -1364,16 +1309,19 @@ nsXULTreeColumnsAccessible::GetNextSibling(nsIAccessible **aNextSibling)
if (treeView) {
PRInt32 rowCount = 0;
treeView->GetRowCount(&rowCount);
if (rowCount > 0) {
if (rowCount > 0 && aOffset <= rowCount) {
nsRefPtr<nsXULTreeAccessible> treeAcc =
nsAccUtils::QueryAccessibleTree(mParent);
NS_ENSURE_STATE(treeAcc);
treeAcc->GetTreeItemAccessible(0, aNextSibling);
if (treeAcc) {
nsCOMPtr<nsIAccessible> sibling;
treeAcc->GetTreeItemAccessible(aOffset - 1, getter_AddRefs(sibling));
return sibling;
}
}
}
}
return NS_OK;
return nsnull;
}

View file

@ -73,12 +73,6 @@ public:
// nsIAccessible
NS_IMETHOD GetValue(nsAString& aValue);
NS_IMETHOD GetFirstChild(nsIAccessible **aFirstChild);
NS_IMETHOD GetLastChild(nsIAccessible **aLastChild);
NS_IMETHOD GetChildCount(PRInt32 *aChildCount);
NS_IMETHOD GetChildAt(PRInt32 aChildIndex, nsIAccessible **aChild);
NS_IMETHOD GetFocusedChild(nsIAccessible **aFocusedChild);
// nsIAccessibleSelectable
@ -95,6 +89,10 @@ public:
PRBool aDeepestChild,
nsIAccessible **aChild);
virtual nsIAccessible* GetChildAt(PRUint32 aIndex);
virtual PRInt32 GetChildCount();
virtual PRInt32 GetIndexOf(nsIAccessible *aChild);
// nsXULTreeAccessible
NS_DECLARE_STATIC_IID_ACCESSOR(NS_XULTREEACCESSIBLE_IMPL_CID)
@ -178,10 +176,6 @@ public:
NS_IMETHOD GetUniqueID(void **aUniqueID);
// nsIAccessible
NS_IMETHOD GetParent(nsIAccessible **aParent);
NS_IMETHOD GetNextSibling(nsIAccessible **aNextSibling);
NS_IMETHOD GetPreviousSibling(nsIAccessible **aPreviousSibling);
NS_IMETHOD GetFocusedChild(nsIAccessible **aFocusedChild);
NS_IMETHOD GetBounds(PRInt32 *aX, PRInt32 *aY,
@ -204,10 +198,16 @@ public:
// nsAccessible
virtual nsresult GetAttributesInternal(nsIPersistentProperties *aAttributes);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual nsIAccessible* GetParent();
// nsXULTreeItemAccessibleBase
NS_DECLARE_STATIC_IID_ACCESSOR(NS_XULTREEITEMBASEACCESSIBLE_IMPL_CID)
/**
* Return row index associated with the accessible.
*/
PRInt32 GetRowIndex() const { return mRow; }
/**
* Return cell accessible for the given column. If XUL tree accessible is not
* accessible table then return null.
@ -226,6 +226,8 @@ protected:
// nsAccessible
virtual void DispatchClickEvent(nsIContent *aContent, PRUint32 aActionIndex);
virtual nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError = nsnull);
// nsXULTreeItemAccessibleBase
@ -253,11 +255,6 @@ public:
nsIAccessible *aParent, nsITreeBoxObject *aTree,
nsITreeView *aTreeView, PRInt32 aRow);
// nsIAccessible
NS_IMETHOD GetFirstChild(nsIAccessible **aFirstChild);
NS_IMETHOD GetLastChild(nsIAccessible **aLastChild);
NS_IMETHOD GetChildCount(PRInt32 *aChildCount);
NS_IMETHOD GetName(nsAString& aName);
// nsAccessNode
@ -272,6 +269,11 @@ public:
virtual void RowInvalidated(PRInt32 aStartColIdx, PRInt32 aEndColIdx);
protected:
// nsAccessible
virtual void CacheChildren();
// nsXULTreeItemAccessible
nsCOMPtr<nsITreeColumn> mColumn;
nsString mCachedName;
};
@ -285,8 +287,10 @@ class nsXULTreeColumnsAccessible : public nsXULColumnsAccessible
public:
nsXULTreeColumnsAccessible(nsIDOMNode* aDOMNode, nsIWeakReference* aShell);
// nsIAccessible
NS_IMETHOD GetNextSibling(nsIAccessible **aNextSibling);
protected:
// nsAccessible
nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset, nsresult* aError = nsnull);
};
#endif

View file

@ -95,15 +95,15 @@ nsXULTreeGridAccessible::GetSummary(nsAString &aSummary)
}
NS_IMETHODIMP
nsXULTreeGridAccessible::GetColumnCount(PRInt32 *acolumnCount)
nsXULTreeGridAccessible::GetColumnCount(PRInt32 *aColumnCount)
{
NS_ENSURE_ARG_POINTER(acolumnCount);
*acolumnCount = 0;
NS_ENSURE_ARG_POINTER(aColumnCount);
*aColumnCount = 0;
if (IsDefunct())
return NS_ERROR_FAILURE;
*acolumnCount = nsCoreUtils::GetSensiblecolumnCount(mTree);
*aColumnCount = nsCoreUtils::GetSensibleColumnCount(mTree);
return NS_OK;
}
@ -635,77 +635,6 @@ NS_IMPL_ADDREF_INHERITED(nsXULTreeGridRowAccessible,
NS_IMPL_RELEASE_INHERITED(nsXULTreeGridRowAccessible,
nsXULTreeItemAccessibleBase)
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridRowAccessible: nsIAccessible implementation
NS_IMETHODIMP
nsXULTreeGridRowAccessible::GetFirstChild(nsIAccessible **aFirstChild)
{
NS_ENSURE_ARG_POINTER(aFirstChild);
*aFirstChild = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsCOMPtr<nsITreeColumn> column = nsCoreUtils::GetFirstSensibleColumn(mTree);
NS_ASSERTION(column, "No column for table grid!");
if (!column)
return NS_ERROR_FAILURE;
GetCellAccessible(column, aFirstChild);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridRowAccessible::GetLastChild(nsIAccessible **aLastChild)
{
NS_ENSURE_ARG_POINTER(aLastChild);
*aLastChild = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsCOMPtr<nsITreeColumn> column = nsCoreUtils::GetLastSensibleColumn(mTree);
NS_ASSERTION(column, "No column for table grid!");
if (!column)
return NS_ERROR_FAILURE;
GetCellAccessible(column, aLastChild);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridRowAccessible::GetChildCount(PRInt32 *aChildCount)
{
NS_ENSURE_ARG_POINTER(aChildCount);
*aChildCount = 0;
if (IsDefunct())
return NS_ERROR_FAILURE;
*aChildCount = nsCoreUtils::GetSensiblecolumnCount(mTree);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridRowAccessible::GetChildAt(PRInt32 aChildIndex,
nsIAccessible **aChild)
{
NS_ENSURE_ARG_POINTER(aChild);
*aChild = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsCOMPtr<nsITreeColumn> column =
nsCoreUtils::GetSensibleColumnAt(mTree, aChildIndex);
if (!column)
return NS_ERROR_INVALID_ARG;
GetCellAccessible(column, aChild);
return NS_OK;
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridRowAccessible: nsAccessNode implementation
@ -760,6 +689,43 @@ nsXULTreeGridRowAccessible::GetChildAtPoint(PRInt32 aX, PRInt32 aY,
return NS_OK;
}
nsIAccessible*
nsXULTreeGridRowAccessible::GetChildAt(PRUint32 aIndex)
{
if (IsDefunct())
return nsnull;
nsCOMPtr<nsITreeColumn> column =
nsCoreUtils::GetSensibleColumnAt(mTree, aIndex);
if (!column)
return nsnull;
nsCOMPtr<nsIAccessible> cell;
GetCellAccessible(column, getter_AddRefs(cell));
return cell;
}
PRInt32
nsXULTreeGridRowAccessible::GetChildCount()
{
if (IsDefunct())
return -1;
return nsCoreUtils::GetSensibleColumnCount(mTree);
}
PRInt32
nsXULTreeGridRowAccessible::GetIndexOf(nsIAccessible *aChild)
{
if (IsDefunct())
return -1;
nsRefPtr<nsXULTreeGridCellAccessible> cell =
nsAccUtils::QueryObject<nsXULTreeGridCellAccessible>(aChild);
return cell ? cell->GetColumnIndex() : -1;
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridRowAccessible: nsXULTreeItemAccessibleBase implementation
@ -818,6 +784,13 @@ nsXULTreeGridRowAccessible::RowInvalidated(PRInt32 aStartColIdx,
}
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridRowAccessible: nsAccessible protected implementation
void
nsXULTreeGridRowAccessible::CacheChildren()
{
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible
@ -857,64 +830,6 @@ nsXULTreeGridCellAccessible::GetUniqueID(void **aUniqueID)
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible: nsIAccessible implementation
NS_IMETHODIMP
nsXULTreeGridCellAccessible::GetParent(nsIAccessible **aParent)
{
NS_ENSURE_ARG_POINTER(aParent);
*aParent = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
if (mParent) {
*aParent = mParent;
NS_ADDREF(*aParent);
}
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridCellAccessible::GetNextSibling(nsIAccessible **aNextSibling)
{
NS_ENSURE_ARG_POINTER(aNextSibling);
*aNextSibling = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsCOMPtr<nsITreeColumn> nextColumn =
nsCoreUtils::GetNextSensibleColumn(mColumn);
if (!nextColumn)
return NS_OK;
nsRefPtr<nsXULTreeItemAccessibleBase> rowAcc =
nsAccUtils::QueryObject<nsXULTreeItemAccessibleBase>(mParent);
rowAcc->GetCellAccessible(nextColumn, aNextSibling);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridCellAccessible::GetPreviousSibling(nsIAccessible **aPreviousSibling)
{
NS_ENSURE_ARG_POINTER(aPreviousSibling);
*aPreviousSibling = nsnull;
if (IsDefunct())
return NS_ERROR_FAILURE;
nsCOMPtr<nsITreeColumn> nextColumn =
nsCoreUtils::GetPreviousSensibleColumn(mColumn);
if (!nextColumn)
return NS_OK;
nsRefPtr<nsXULTreeItemAccessibleBase> rowAcc =
nsAccUtils::QueryObject<nsXULTreeItemAccessibleBase>(mParent);
rowAcc->GetCellAccessible(nextColumn, aPreviousSibling);
return NS_OK;
}
NS_IMETHODIMP
nsXULTreeGridCellAccessible::GetFocusedChild(nsIAccessible **aFocusedChild)
{
@ -1219,7 +1134,7 @@ nsXULTreeGridCellAccessible::Init()
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible: nsAccessible implementation
// nsXULTreeGridCellAccessible: nsAccessible public implementation
nsresult
nsXULTreeGridCellAccessible::GetAttributesInternal(nsIPersistentProperties *aAttributes)
@ -1307,6 +1222,12 @@ nsXULTreeGridCellAccessible::GetStateInternal(PRUint32 *aStates,
return NS_OK;
}
nsIAccessible*
nsXULTreeGridCellAccessible::GetParent()
{
return IsDefunct() ? nsnull : mParent.get();
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible: public implementation
@ -1352,7 +1273,46 @@ nsXULTreeGridCellAccessible::CellInvalidated()
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible: protected implementation
// nsXULTreeGridCellAccessible: nsAccessible protected implementation
nsIAccessible*
nsXULTreeGridCellAccessible::GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError)
{
if (IsDefunct()) {
if (aError)
*aError = NS_ERROR_FAILURE;
return nsnull;
}
if (aError)
*aError = NS_OK; // fail peacefully
nsCOMPtr<nsITreeColumn> columnAtOffset(mColumn), column;
if (aOffset < 0) {
for (PRInt32 index = aOffset; index < 0 && columnAtOffset; index++) {
column = nsCoreUtils::GetPreviousSensibleColumn(columnAtOffset);
column.swap(columnAtOffset);
}
} else {
for (PRInt32 index = aOffset; index > 0 && columnAtOffset; index--) {
column = nsCoreUtils::GetNextSensibleColumn(columnAtOffset);
column.swap(columnAtOffset);
}
}
if (!columnAtOffset)
return nsnull;
nsRefPtr<nsXULTreeItemAccessibleBase> rowAcc =
nsAccUtils::QueryObject<nsXULTreeItemAccessibleBase>(mParent);
nsCOMPtr<nsIAccessible> sibling;
rowAcc->GetCellAccessible(columnAtOffset, getter_AddRefs(sibling));
return sibling;
}
void
nsXULTreeGridCellAccessible::DispatchClickEvent(nsIContent *aContent,
@ -1364,6 +1324,9 @@ nsXULTreeGridCellAccessible::DispatchClickEvent(nsIContent *aContent,
nsCoreUtils::DispatchClickEvent(mTree, mRow, mColumn);
}
////////////////////////////////////////////////////////////////////////////////
// nsXULTreeGridCellAccessible: protected implementation
PRBool
nsXULTreeGridCellAccessible::IsEditable() const
{

View file

@ -86,12 +86,6 @@ public:
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsXULTreeGridRowAccessible,
nsAccessible)
// nsIAccessible
NS_IMETHOD GetFirstChild(nsIAccessible **aFirstChild);
NS_IMETHOD GetLastChild(nsIAccessible **aLastChild);
NS_IMETHOD GetChildCount(PRInt32 *aChildCount);
NS_IMETHOD GetChildAt(PRInt32 aChildIndex, nsIAccessible **aChild);
// nsAccessNode
virtual nsresult Shutdown();
@ -101,11 +95,20 @@ public:
PRBool aDeepestChild,
nsIAccessible **aChild);
virtual nsIAccessible* GetChildAt(PRUint32 aIndex);
virtual PRInt32 GetChildCount();
virtual PRInt32 GetIndexOf(nsIAccessible *aChild);
// nsXULTreeItemAccessibleBase
virtual void GetCellAccessible(nsITreeColumn *aColumn, nsIAccessible **aCell);
virtual void RowInvalidated(PRInt32 aStartColIdx, PRInt32 aEndColIdx);
protected:
// nsAccessible
virtual void CacheChildren();
// nsXULTreeItemAccessibleBase
nsAccessNodeHashtable mAccessNodeCache;
};
@ -139,10 +142,6 @@ public:
NS_IMETHOD GetUniqueID(void **aUniqueID);
// nsIAccessible
NS_IMETHOD GetParent(nsIAccessible **aParent);
NS_IMETHOD GetNextSibling(nsIAccessible **aNextSibling);
NS_IMETHOD GetPreviousSibling(nsIAccessible **aPrevSibling);
NS_IMETHOD GetFocusedChild(nsIAccessible **aFocusedChild);
NS_IMETHOD GetName(nsAString& aName);
@ -165,6 +164,8 @@ public:
virtual nsresult GetRoleInternal(PRUint32 *aRole);
virtual nsresult GetStateInternal(PRUint32 *aState, PRUint32 *aExtraState);
virtual nsIAccessible* GetParent();
// nsXULTreeGridCellAccessible
NS_DECLARE_STATIC_IID_ACCESSOR(NS_XULTREEGRIDCELLACCESSIBLE_IMPL_CID)
@ -181,6 +182,8 @@ public:
protected:
// nsAccessible
virtual nsIAccessible* GetSiblingAtOffset(PRInt32 aOffset,
nsresult* aError = nsnull);
virtual void DispatchClickEvent(nsIContent *aContent, PRUint32 aActionIndex);
// nsXULTreeGridCellAccessible

View file

@ -42,7 +42,7 @@ srcdir = @srcdir@
VPATH = @srcdir@
relativesrcdir = accessible
DIRS = tree
DIRS = tree selectable
include $(DEPTH)/config/autoconf.mk
include $(topsrcdir)/config/rules.mk
@ -108,14 +108,13 @@ _TEST_FILES =\
test_groupattrs.xul \
test_groupattrs.html \
test_invalidate_accessnode.html \
test_invalidate_elmli.html \
test_name.html \
test_name.xul \
test_name_button.html \
test_name_link.html \
test_name_markup.html \
test_name_nsApplicationAcc.html \
test_name_nsRootAcc.xul \
test_nsIAccessible_applicationAccessible.html \
$(warning test_nsIAccessible_comboboxes.xul temporarily disabled) \
test_nsIAccessible_selects.html \
test_nsIAccessible_focus.html \
@ -133,7 +132,6 @@ _TEST_FILES =\
test_relations_tree.xul \
test_role_nsHyperTextAcc.html \
test_role_table_cells.html \
test_selectable_tree.xul \
test_states.html \
test_states_doc.html \
test_states_docarticle.html \

View file

@ -270,6 +270,35 @@ function getRootAccessible(aAccOrElmOrID)
return null;
}
/**
* Return application accessible.
*/
function getApplicationAccessible()
{
var acc = getAccessible(document), parent = null;
while (acc) {
try {
parent = acc.parent;
} catch (e) {
ok(false, "Can't get a parent for " + prettyName(acc));
return null;
}
if (!parent) {
if (acc.role == ROLE_APP_ROOT)
return acc;
ok(false, "No application accessible!");
return null;
}
acc = parent;
}
return null;
}
/**
* Run through accessible tree of the given identifier so that we ensure
* accessible tree is created.
@ -356,6 +385,12 @@ function testAccessibleTree(aAccOrElmOrID, aAccTree)
try { parent = child.parent; } catch (e) {}
is(parent, acc, "Wrong parent of " + prettyName(child));
// nsIAccessible::indexInParent
var indexInParent = -1;
try { indexInParent = child.indexInParent; } catch(e) {}
is(indexInParent, i,
"Wrong index in parent of " + prettyName(child));
// nsIAccessible::nextSibling
var expectedNextSibling = (i < childCount - 1) ?
children.queryElementAt(i + 1, nsIAccessible) : null;
@ -379,6 +414,84 @@ function testAccessibleTree(aAccOrElmOrID, aAccTree)
}
}
/**
* Test accessible tree for defunct accessible.
*
* @param aAcc [in] the defunct accessible
* @param aNodeOrId [in] the DOM node identifier for the defunct accessible
*/
function testDefunctAccessible(aAcc, aNodeOrId)
{
if (aNodeOrId)
ok(!isAccessible(aNodeOrId),
"Accessible for " + aNodeOrId + " wasn't properly shut down!");
var msg = " doesn't fail for shut down accessible " + prettyName(aNodeOrId) + "!";
// firstChild
var success = false;
try {
aAcc.firstChild;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE)
}
ok(success, "firstChild" + msg);
// lastChild
success = false;
try {
aAcc.lastChild;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE)
}
ok(success, "lastChild" + msg);
// childCount
success = false;
try {
aAcc.childCount;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE)
}
ok(success, "childCount" + msg);
// children
success = false;
try {
aAcc.children;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE)
}
ok(success, "children" + msg);
// nextSibling
success = false;
try {
aAcc.nextSibling;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "nextSibling" + msg);
// previousSibling
success = false;
try {
aAcc.previousSibling;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "previousSibling" + msg);
// parent
success = false;
try {
aAcc.parent;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "parent" + msg);
}
/**
* Convert role to human readable string.

View file

@ -8,6 +8,7 @@ const ROLE_AUTOCOMPLETE = nsIAccessibleRole.ROLE_AUTOCOMPLETE;
const ROLE_BUTTONDROPDOWNGRID = nsIAccessibleRole.ROLE_BUTTONDROPDOWNGRID;
const ROLE_CAPTION = nsIAccessibleRole.ROLE_CAPTION;
const ROLE_CELL = nsIAccessibleRole.ROLE_CELL;
const ROLE_CHECKBUTTON = nsIAccessibleRole.ROLE_CHECKBUTTON;
const ROLE_CHROME_WINDOW = nsIAccessibleRole.ROLE_CHROME_WINDOW;
const ROLE_COMBOBOX = nsIAccessibleRole.ROLE_COMBOBOX;
const ROLE_COMBOBOX_LIST = nsIAccessibleRole.ROLE_COMBOBOX_LIST;
@ -40,9 +41,11 @@ const ROLE_PARENT_MENUITEM = nsIAccessibleRole.ROLE_PARENT_MENUITEM;
const ROLE_PASSWORD_TEXT = nsIAccessibleRole.ROLE_PASSWORD_TEXT;
const ROLE_PROGRESSBAR = nsIAccessibleRole.ROLE_PROGRESSBAR;
const ROLE_PUSHBUTTON = nsIAccessibleRole.ROLE_PUSHBUTTON;
const ROLE_RADIOBUTTON = nsIAccessibleRole.ROLE_RADIOBUTTON;
const ROLE_ROW = nsIAccessibleRole.ROLE_ROW;
const ROLE_ROWHEADER = nsIAccessibleRole.ROLE_ROWHEADER;
const ROLE_SECTION = nsIAccessibleRole.ROLE_SECTION;
const ROLE_SEPARATOR = nsIAccessibleRole.ROLE_SEPARATOR;
const ROLE_SLIDER = nsIAccessibleRole.ROLE_SLIDER;
const ROLE_STATICTEXT = nsIAccessibleRole.ROLE_STATICTEXT;
const ROLE_TABLE = nsIAccessibleRole.ROLE_TABLE;
@ -50,6 +53,7 @@ const ROLE_TEXT_CONTAINER = nsIAccessibleRole.ROLE_TEXT_CONTAINER;
const ROLE_TEXT_LEAF = nsIAccessibleRole.ROLE_TEXT_LEAF;
const ROLE_TOGGLE_BUTTON = nsIAccessibleRole.ROLE_TOGGLE_BUTTON;
const ROLE_TREE_TABLE = nsIAccessibleRole.ROLE_TREE_TABLE;
const ROLE_WHITESPACE = nsIAccessibleRole.ROLE_WHITESPACE;
////////////////////////////////////////////////////////////////////////////////
// Public methods

View file

@ -0,0 +1,55 @@
#
# ***** BEGIN LICENSE BLOCK *****
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
#
# The contents of this file are subject to the Mozilla Public License Version
# 1.1 (the "License"); you may not use this file except in compliance with
# the License. You may obtain a copy of the License at
# http://www.mozilla.org/MPL/
#
# Software distributed under the License is distributed on an "AS IS" basis,
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
# for the specific language governing rights and limitations under the
# License.
#
# The Original Code is mozilla.org code.
#
# The Initial Developer of the Original Code is
# Mozilla Corporation.
# Portions created by the Initial Developer are Copyright (C) 2009
# the Initial Developer. All Rights Reserved.
#
# Contributor(s):
# Alexander Surkov <surkov.alexander@gmail.com> (original author)
#
# Alternatively, the contents of this file may be used under the terms of
# either of the GNU General Public License Version 2 or later (the "GPL"),
# or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
# in which case the provisions of the GPL or the LGPL are applicable instead
# of those above. If you wish to allow use of your version of this file only
# under the terms of either the GPL or the LGPL, and not to allow others to
# use your version of this file under the terms of the MPL, indicate your
# decision by deleting the provisions above and replace them with the notice
# and other provisions required by the GPL or the LGPL. If you do not delete
# the provisions above, a recipient may use your version of this file under
# the terms of any one of the MPL, the GPL or the LGPL.
#
# ***** END LICENSE BLOCK *****
DEPTH = ../../../..
topsrcdir = @top_srcdir@
srcdir = @srcdir@
VPATH = @srcdir@
relativesrcdir = accessible/selectable
include $(DEPTH)/config/autoconf.mk
include $(topsrcdir)/config/rules.mk
_TEST_FILES =\
test_aria.html \
test_select.html \
test_tree.xul \
$(NULL)
libs:: $(_TEST_FILES)
$(INSTALL) $(foreach f,$^,"$f") $(DEPTH)/_tests/testing/mochitest/a11y/$(relativesrcdir)

View file

@ -0,0 +1,120 @@
<html>
<head>
<title>nsIAccessibleSelectable ARIA widgets testing</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
</style>
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
var id = "list1";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
id = "listbox1";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
id = "listbox2";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
id = "grid1";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
id = "tree1";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
id = "treegrid1";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=530014"
title="ARIA single selectable widget should implement nsIAccessibleSelectable">
Mozilla Bug 530014
</a><br>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<div role="list" id="list1">
<div role="listitem">item1</div>
<div role="listitem">item2</div>
</div>
<div role="listbox" id="listbox1">
<div role="listitem">item1</div>
<div role="listitem">item2</div>
</div>
<div role="listbox" id="listbox2" aria-multiselectable="true">
<div role="listitem">item1</div>
<div role="listitem">item2</div>
</div>
<div role="grid" id="grid1">
<div role="row">
<span role="gridcell">cell</span>
<span role="gridcell">cell</span>
</div>
<div role="row">
<span role="gridcell">cell</span>
<span role="gridcell">cell</span>
</div>
</div>
<div role="tree" id="tree1">
<div role="treeitem">
item1
<div role="group">
<div role="treeitem">item1.1</div>
</div>
</div>
<div>item2</div>
</div>
<div role="treegrid" id="treegrid1">
<div role="row" aria-level="1">
<span role="gridcell">cell</span>
<span role="gridcell">cell</span>
</div>
<div role="row" aria-level="2">
<span role="gridcell">cell</span>
<span role="gridcell">cell</span>
</div>
<div role="row" aria-level="1">
<span role="gridcell">cell</span>
<span role="gridcell">cell</span>
</div>
</div>
</body>
</html>

View file

@ -0,0 +1,66 @@
<html>
<head>
<title>nsIAccessibleSelectable HTML select testing</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
</style>
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
var combobox = getAccessible("combobox");
var comboboxList = combobox.firstChild;
ok(isAccessible(comboboxList, [nsIAccessibleSelectable]),
"No selectable accessible for list of " + id);
var id = "listbox";
ok(isAccessible(id, [nsIAccessibleSelectable]),
"No selectable accessible for " + id);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=530014"
title="ARIA single selectable widget should implement nsIAccessibleSelectable">
Mozilla Bug 530014
</a><br>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<select id="combobox">
<option>option</option>
<option>option</option>
</select>
<select id="listbox" size="4">
<option>option</option>
<option>option</option>
</select>
</body>
</html>

View file

@ -47,7 +47,12 @@
var docAcc = getAccessible(document);
while (docAcc) {
this.mRootAcc = docAcc;
docAcc = docAcc.parent;
try {
docAcc = docAcc.parent;
} catch (e) {
ok(false, "Can't get parent for " + prettyName(docAcc));
throw e;
}
}
this.eventSeq = [

View file

@ -7,22 +7,20 @@
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js">
</script>
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js" ></script>
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
var accessible = getAccessible(document);
while (accessible && accessible.parent) {
accessible = accessible.parent;
}
var accessible = getApplicationAccessible();
if (!accessible) {
SimpleTest.finish();
return;
SimpleTest.finish();
return;
}
var bundleServ = Components.classes["@mozilla.org/intl/stringbundle;1"]

View file

@ -119,6 +119,32 @@
testHeaderCells(headerInfoMap);
//////////////////////////////////////////////////////////////////////////
// table consisted of one column
headerInfoMap = [
{
cell: "table4_cell",
rowHeaderCells: [],
columnHeaderCells: [ "table4_ch" ]
}
];
testHeaderCells(headerInfoMap);
//////////////////////////////////////////////////////////////////////////
// table consisted of one row
headerInfoMap = [
{
cell: "table5_cell",
rowHeaderCells: [ "table5_rh" ],
columnHeaderCells: [ ]
}
];
testHeaderCells(headerInfoMap);
SimpleTest.finish();
}
@ -200,5 +226,25 @@
<td id="table3_ch_2" scope="col">col2</td>
</tr>
</table>
<table id="table4">
<thead>
<tr>
<th id="table4_ch">colheader</th>
</tr>
</thead>
<tbody>
<tr>
<td id="table4_cell">bla</td>
</tr>
</tbody>
</table>
<table id="table5">
<tr>
<th id="table5_rh">rowheader</th>
<td id="table5_cell">cell</td>
</tr>
</table>
</body>
</html>

View file

@ -50,10 +50,19 @@ _TEST_FILES =\
test_colorpicker.xul \
test_combobox.xul \
test_filectrl.html \
test_formctrl.html \
test_formctrl.xul \
test_groupbox.xul \
test_iframe.html \
test_img.html \
test_list.html \
test_list_invalidate.html \
test_media.html \
test_menu.xul \
test_select.html \
test_table.html \
test_tree.xul \
test_txtcntr.html \
test_txtctrl.html \
$(NULL)

View file

@ -0,0 +1,83 @@
<!DOCTYPE html>
<html>
<head>
<title>HTML form controls tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
// input@type="checkbox"
var accTree = {
role: ROLE_CHECKBUTTON,
children: [ ]
};
testAccessibleTree("checkbox", accTree);
// input@type="radio"
accTree = {
role: ROLE_RADIOBUTTON,
children: [ ]
};
testAccessibleTree("radio", accTree);
// input@type="button" and button
accTree = {
role: ROLE_PUSHBUTTON,
children: [ ]
};
testAccessibleTree("btn1", accTree);
// button
accTree = {
role: ROLE_PUSHBUTTON,
children: [
{
role: ROLE_TEXT_LEAF
}
]
};
testAccessibleTree("btn2", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="Fix O(n^2) access to all the children of a container"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045">
Mozilla Bug 342045
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<input type="checkbox" id="checkbox">
<input type="radio" id="radio">
<input type="button" value="button" id="btn1">
<button id="btn2">button</button>
</body>
</html>

View file

@ -0,0 +1,83 @@
<?xml version="1.0"?>
<?xml-stylesheet href="chrome://global/skin" type="text/css"?>
<?xml-stylesheet href="chrome://mochikit/content/tests/SimpleTest/test.css"
type="text/css"?>
<window xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
title="Accessible XUL checkbox and radio hierarchy tests">
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js" />
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js" />
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js" />
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js" />
<script type="application/javascript">
<![CDATA[
////////////////////////////////////////////////////////////////////////////
// Test
function doTest()
{
// checkbox
var accTree = {
role: ROLE_CHECKBUTTON,
children: [ ]
};
testAccessibleTree("checkbox", accTree);
// radiogroup
accTree = {
role: ROLE_GROUPING,
children: [
{
role: ROLE_RADIOBUTTON,
children: [ ]
},
{
role: ROLE_RADIOBUTTON,
children: [ ]
}
]
};
testAccessibleTree("radiogroup", accTree);
SimpleTest.finish()
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
]]>
</script>
<hbox flex="1" style="overflow: auto;">
<body xmlns="http://www.w3.org/1999/xhtml">
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045"
title="Fix O(n^2) access to all the children of a container">
Mozilla Bug 342045
</a><br/>
<p id="display"></p>
<div id="content" style="display: none">
</div>
<pre id="test">
</pre>
</body>
<vbox flex="1">
<checkbox id="checkbox" label="checkbox"/>
<radiogroup id="radiogroup">
<radio label="radio1"/>
<radio label="radio2"/>
</radiogroup>
</vbox>
</hbox>
</window>

View file

@ -0,0 +1,73 @@
<?xml version="1.0"?>
<?xml-stylesheet href="chrome://global/skin" type="text/css"?>
<?xml-stylesheet href="chrome://mochikit/content/tests/SimpleTest/test.css"
type="text/css"?>
<window xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
title="Accessible XUL groupbox hierarchy tests">
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js" />
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js" />
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js" />
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js" />
<script type="application/javascript">
<![CDATA[
////////////////////////////////////////////////////////////////////////////
// Test
function doTest()
{
accTree = {
role: ROLE_GROUPING,
children: [
{
role: ROLE_LABEL,
children: [ ]
},
{
role: ROLE_CHECKBUTTON,
children: [ ]
}
]
};
testAccessibleTree("groupbox", accTree);
SimpleTest.finish()
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
]]>
</script>
<hbox flex="1" style="overflow: auto;">
<body xmlns="http://www.w3.org/1999/xhtml">
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045"
title="Fix O(n^2) access to all the children of a container">
Mozilla Bug 342045
</a><br/>
<p id="display"></p>
<div id="content" style="display: none">
</div>
<pre id="test">
</pre>
</body>
<vbox flex="1">
<groupbox id="groupbox">
<caption label="Some caption" />
<checkbox label="some checkbox label" />
</groupbox>
</vbox>
</hbox>
</window>

View file

@ -0,0 +1,54 @@
<!DOCTYPE html>
<html>
<head>
<title>Outer document accessible tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
var accTree = {
role: ROLE_INTERNAL_FRAME,
children: [
{
role: ROLE_DOCUMENT
}
]
};
testAccessibleTree("iframe", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="Fix O(n^2) access to all the children of a container"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045">
Mozilla Bug 342045
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<iframe id="iframe" src="about:mozilla">
</body>
</html>

View file

@ -0,0 +1,79 @@
<!DOCTYPE html>
<html>
<head>
<title>HTML img tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
// image map
var accTree = {
role: ROLE_IMAGE_MAP,
children: [
{
role: ROLE_LINK,
children: []
},
{
role: ROLE_LINK,
children: []
}
]
};
testAccessibleTree("imgmap", accTree);
// img
accTree = {
role: ROLE_GRAPHIC,
children: []
};
testAccessibleTree("img", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="Fix O(n^2) access to all the children of a container"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045">
Mozilla Bug 342045
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<map name="atoz_map">
<area href="http://www.bbc.co.uk/radio4/atoz/index.shtml#b"
coords="17,0,30,14" alt="b" shape="rect">
<area href="http://www.bbc.co.uk/radio4/atoz/index.shtml#a"
coords="0,0,13,14" alt="a" shape="rect">
</map>
<img id="imgmap" width="447" height="15"
usemap="#atoz_map"
src="chrome://mochikit/content/a11y/accessible/letters.gif">
<img id="img" src="chrome://mochikit/content/a11y/accessible/moz.png">
</body>
</html>

View file

@ -0,0 +1,105 @@
<!DOCTYPE html>
<html>
<head>
<title>HTML ul/li element tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function listItemTree(aBulletText, aName, aSubtree)
{
var obj = {
role: ROLE_LISTITEM,
children: [
{
role: ROLE_STATICTEXT,
name: aBulletText
},
{
role: ROLE_TEXT_LEAF,
name: aName
}
]
};
if (aSubtree)
obj.children.push(aSubtree);
return obj;
}
function doTest()
{
var bulletText = String.fromCharCode(0x2022) + " ";
// list1
var accTree = {
role: ROLE_LIST,
children: [
new listItemTree(bulletText, "Oranges"),
new listItemTree(bulletText, "Apples"),
new listItemTree(bulletText, "Bananas")
]
};
testAccessibleTree("list1", accTree);
// list2
accTree = {
role: ROLE_LIST,
children: [
new listItemTree("1. ", "Oranges"),
new listItemTree("2. ", "Apples"),
new listItemTree("3. ", "Bananas", accTree)
]
};
testAccessibleTree("list2", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="Fix O(n^2) access to all the children of a container"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=342045">
Mozilla Bug 342045
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<ul id="list1">
<li id="li1">Oranges</li>
<li id="li2">Apples</li>
<li id="li3">Bananas</li>
</ul>
<ol id="list2">
<li id="li4">Oranges</li>
<li id="li5">Apples</li>
<li id="li6">Bananas<ul>
<li id="n_li4">Oranges</li>
<li id="n_li5">Apples</li>
<li id="n_li6">Bananas</li>
</ul>
</li>
</ol>
</body>
</html>

View file

@ -23,47 +23,6 @@
////////////////////////////////////////////////////////////////////////////
// Helpers
function testDefunctAccessible(aAcc, aNodeOrId)
{
if (aNodeOrId)
ok(!isAccessible(aNodeOrId),
"Accessible for " + aNodeOrId + " wasn't properly shut down!");
ok(!aAcc.firstChild, "There is first child for shut down accessible!");
ok(!aAcc.lastChild, "There is last child for shut down accessible!");
ok(!aAcc.children.length, "There are children for shut down accessible!");
// nextSibling
var success = false;
try {
aAcc.nextSibling;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "There is next sibling for shut down accessible!");
// previousSibling
var success = false;
try {
aAcc.previousSibling;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "There is previous sibling for shut down accessible!");
// parent
var success = false;
try {
aAcc.parent;
} catch (e) {
success = (e.result == Components.results.NS_ERROR_FAILURE);
}
ok(success, "There is parent for shut down accessible!");
}
function testLiAccessibleTree()
{
// Test accessible tree.
@ -101,12 +60,14 @@
this.onProcessed = function hideProcessor_onProcessed()
{
window.setTimeout(
function(aArg1, aArg2)
function(aLiAcc, aLiNode, aBulletAcc)
{
testDefunctAccessible(aArg1, aArg2);
testDefunctAccessible(aLiAcc, aLiNode);
testDefunctAccessible(aBulletAcc);
gSequence.processNext();
},
0, this.li, this.liNode
0, this.li, this.liNode, this.bullet
);
}
};

View file

@ -0,0 +1,195 @@
<!DOCTYPE html>
<html>
<head>
<title>HTML table tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
//////////////////////////////////////////////////////////////////////////
// table1
var accTree = {
role: ROLE_TABLE,
children: [
{
role: ROLE_CAPTION,
children: [
{
role: ROLE_TEXT_LEAF
}
]
},
{
role: ROLE_ROW,
children: [
{
role: ROLE_COLUMNHEADER
},
{
role: ROLE_COLUMNHEADER
}
]
},
{
role: ROLE_ROW,
children: [
{
role: ROLE_CELL
},
{
role: ROLE_CELL
}
]
},
{
role: ROLE_ROW,
children: [
{
role: ROLE_CELL
},
{
role: ROLE_CELL
}
]
},
{
role: ROLE_ROW,
children: [
{
role: ROLE_CELL
},
{
role: ROLE_CELL
}
]
}
]
};
testAccessibleTree("table", accTree);
//////////////////////////////////////////////////////////////////////////
// table2 (consist of one column)
accTree = {
role: ROLE_TABLE,
children: [
{
role: ROLE_ROW,
children: [
{
role: ROLE_COLUMNHEADER
}
]
},
{
role: ROLE_ROW,
children: [
{
role: ROLE_CELL
}
]
}
]
};
testAccessibleTree("table2", accTree);
//////////////////////////////////////////////////////////////////////////
// table3 (consist of one row)
accTree = {
role: ROLE_TABLE,
children: [
{
role: ROLE_ROW,
children: [
{
role: ROLE_ROWHEADER
},
{
role: ROLE_CELL
}
]
}
]
};
testAccessibleTree("table3", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="When a table has only one column per row and that column happens to be a column header its role is exposed wrong"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=529621">
Mozilla Bug 529621
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<table id="table">
<thead>
<tr>
<th>col1</th><th>col2</th>
</tr>
</thead>
<caption>caption</caption>
<tbody>
<tr>
<td>cell1</td><td>cell2</td>
</tr>
</tbody>
<tr>
<td>cell3</td><td>cell4</td>
</tr>
<caption>caption2</caption>
<tfoot>
<tr>
<td>cell5</td><td>cell6</td>
</tr>
</tfoot>
</table>
<table id="table2">
<thead>
<tr>
<th>colheader</th>
</tr>
</thead>
<tbody>
<tr>
<td>bla</td>
</tr>
</tbody>
</table>
<table id="table3">
<tr>
<th>rowheader</th>
<td>cell</td>
</tr>
</table>
</body>
</html>

View file

@ -0,0 +1,102 @@
<!DOCTYPE html>
<html>
<head>
<title>HTML text containers tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/common.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/role.js"></script>
<script type="application/javascript">
function doTest()
{
var accTree = {
role: ROLE_SECTION,
children: [
{ // text child
role: ROLE_TEXT_LEAF,
children: []
}
]
};
testAccessibleTree("c1", accTree);
testAccessibleTree("c2", accTree);
accTree = {
role: ROLE_SECTION,
children: [
{
role: ROLE_TEXT_LEAF,
name: "Hello1"
},
{
role: ROLE_WHITESPACE
},
{
role: ROLE_TEXT_LEAF,
name: "Hello2"
},
{
role: ROLE_SEPARATOR
},
{
role: ROLE_TEXT_LEAF,
name: "Hello3 "
},
{
role: ROLE_PARAGRAPH,
children: [
{
role: ROLE_TEXT_LEAF,
name: "Hello4 "
}
]
}
]
};
testAccessibleTree("c3", accTree);
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addA11yLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
title="overflowed content doesn't expose child text accessibles"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=489306">Mozilla Bug 489306</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<div id="c1" style="width: 100px; height: 100px; overflow: auto;">
1hellohello 2hellohello 3hellohello 4hellohello 5hellohello 6hellohello 7hellohello
</div>
<div id="c2">
1hellohello 2hellohello 3hellohello 4hellohello 5hellohello 6hellohello 7hellohello
</div>
<div id="c3">
Hello1<br>
Hello2<hr>
Hello3
<p>
Hello4
</p>
</div>
</body>
</html>

View file

@ -2,8 +2,9 @@
<html>
<head>
<title>HTML text containers tests</title>
<link rel="stylesheet" type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<title>HTML text controls tests</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
@ -18,17 +19,58 @@
<script type="application/javascript">
function doTest()
{
// editable div
var accTree = {
role: ROLE_SECTION,
children: [
{ // text child
role: ROLE_TEXT_LEAF
role: ROLE_TEXT_LEAF,
children: []
}
]
};
testAccessibleTree("c1", accTree);
testAccessibleTree("c2", accTree);
testAccessibleTree("txc1", accTree);
// input@type="text"
accTree = {
role: ROLE_ENTRY,
children: [
{ // text child
role: ROLE_TEXT_LEAF,
children: []
}
]
};
testAccessibleTree("txc2", accTree);
// textarea
accTree = {
role: ROLE_ENTRY,
children: [
{
role: ROLE_TEXT_LEAF // hello1 text
},
{
role: ROLE_WHITESPACE
},
{
role: ROLE_TEXT_LEAF, // hello2 text
},
{
role: ROLE_WHITESPACE
},
{
role: ROLE_TEXT_LEAF, // whitepsace text
},
{
role: ROLE_WHITESPACE
}
]
};
testAccessibleTree("txc3", accTree);
SimpleTest.finish();
}
@ -47,11 +89,14 @@
<pre id="test">
</pre>
<div id="c1" style="width: 100px; height: 100px; overflow: auto;">
1hellohello 2hellohello 3hellohello 4hellohello 5hellohello 6hellohello 7hellohello
</div>
<div id="c2">
1hellohello 2hellohello 3hellohello 4hellohello 5hellohello 6hellohello 7hellohello
<div id="txc1" contentEditable="true">
1hellohello
</div>
<input id="txc2" value="hello">
<textarea id="txc3">
hello1
hello2
</textarea>
</body>
</html>

View file

@ -3398,7 +3398,7 @@
this._updateTabsVisibilityStatus();
]]></handler>
<handler event="popuphiding">
<handler event="popuphidden">
<![CDATA[
// clear out the menu popup and remove the listeners
while (this.hasChildNodes()) {

View file

@ -20,4 +20,7 @@ function test()
var dt = EventUtils.synthesizeDragStart(proxyicon, expected);
is(dt, null, "drag on proxy icon");
proxyicon.setAttribute("pageproxystate", oldstate);
// Now, the identity information panel is opened by the proxy icon click.
// We need to close it for next tests.
EventUtils.synthesizeKey("VK_ESCAPE", {}, window);
}

View file

@ -16,6 +16,13 @@ function nextRightElement() elementFromPoint(right(scrollbox) + 1);
function test() {
waitForExplicitFinish();
// If the previous (or more) test finished with cleaning up the tabs,
// there may be some pending animations. That can cause a failure of
// this tests, so, we should test this in another stack.
setTimeout(doTest, 0);
}
function doTest() {
tabstrip.smoothScroll = false;
var tabMinWidth = gPrefService.getIntPref("browser.tabs.tabMinWidth");

View file

@ -53,7 +53,8 @@
<xul:vbox class="menupopup-drop-indicator-bar" hidden="true">
<xul:image class="menupopup-drop-indicator" mousethrough="always"/>
</xul:vbox>
<xul:arrowscrollbox class="popup-internal-box" flex="1" orient="vertical">
<xul:arrowscrollbox class="popup-internal-box" flex="1" orient="vertical"
smoothscroll="false">
<children/>
</xul:arrowscrollbox>
</xul:hbox>

View file

@ -587,7 +587,7 @@ SessionStoreService.prototype = {
// ignore non-browser windows and windows opened while shutting down
if (aWindow.document.documentElement.getAttribute("windowtype") != "navigator:browser" ||
this._loadState == STATE_QUITTING)
this._loadState == STATE_QUITTING)
return;
// assign it a unique identifier (timestamp)
@ -595,6 +595,8 @@ SessionStoreService.prototype = {
// and create its data object
this._windows[aWindow.__SSi] = { tabs: [], selected: 0, _closedTabs: [] };
if (!this._isWindowLoaded(aWindow))
this._windows[aWindow.__SSi]._restoring = true;
if (!aWindow.toolbar.visible)
this._windows[aWindow.__SSi].isPopup = true;
@ -1742,6 +1744,8 @@ SessionStoreService.prototype = {
var nonPopupCount = 0;
var ix;
for (ix in this._windows) {
if (this._windows[ix]._restoring) // window data is still in _statesToRestore
continue;
total.push(this._windows[ix]);
windows.push(ix);
if (!this._windows[ix].isPopup)
@ -2033,6 +2037,7 @@ SessionStoreService.prototype = {
// from now on, the data will come from the actual window
delete this._statesToRestore[aWindow.__SS_restoreID];
delete aWindow.__SS_restoreID;
delete this._windows[aWindow.__SSi]._restoring;
}
// helper hash for ensuring unique frame IDs

View file

@ -45,12 +45,12 @@
border-top: @sidebarItemFocusedBorderTop@;
}
.sidebar-placesTreechildren::-moz-tree-row(selected):-moz-system-metric(mac-graphite-theme) {
.sidebar-placesTreechildren:-moz-system-metric(mac-graphite-theme)::-moz-tree-row(selected) {
background: @sidebarItemGraphiteBackground@;
border-top: @sidebarItemGraphiteBorderTop@;
}
.sidebar-placesTreechildren::-moz-tree-row(selected,focus):-moz-system-metric(mac-graphite-theme) {
.sidebar-placesTreechildren:-moz-system-metric(mac-graphite-theme)::-moz-tree-row(selected,focus) {
background: @sidebarItemGraphiteFocusedBackground@;
border-top: @sidebarItemGraphiteFocusedBorderTop@;
}
@ -68,7 +68,7 @@
-moz-appearance: none;
border: 1px solid #7F7F7F;
-moz-border-radius: 10px;
background: url("chrome://global/skin/icons/white-gray-gradient.gif") #A09E9D repeat-x top center;
background: @toolbarbuttonBackground@;
min-width: 0px;
min-height: 0px;
-moz-padding-start: 5px;

View file

@ -4,7 +4,7 @@
# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
# Free Software Foundation, Inc.
timestamp='2009-08-19'
timestamp='2009-12-04'
# This file is (in principle) common to ALL GNU software.
# The presence of a machine in this file suggests that SOME GNU software
@ -126,7 +126,7 @@ case $maybe_os in
nto-qnx* | linux-gnu* | linux-dietlibc | linux-newlib* | linux-uclibc* | \
uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* | \
kopensolaris*-gnu* | \
storm-chaos* | os2-emx* | rtmk-nova*)
storm-chaos* | os2-emx* | rtmk-nova* | wince-winmo*)
os=-$maybe_os
basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
;;
@ -1296,7 +1296,7 @@ case $os in
| -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
| -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
| -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \
| -skyos* | -haiku* | -rdos* | -toppers* | -drops*)
| -skyos* | -haiku* | -rdos* | -toppers* | -drops* | -winmo*)
# Remember, each alternative MUST END IN *, to match a version number.
;;
-qnx*)
@ -1338,6 +1338,9 @@ case $os in
-os400*)
os=-os400
;;
-wince-winmo*)
os=-wince-winmo
;;
-wince*)
os=-wince
;;

View file

@ -260,7 +260,6 @@ user_pref("network.manage-offline-status", false);
user_pref("test.mousescroll", true);
user_pref("security.default_personal_cert", "Select Automatically"); // Need to client auth test be w/o any dialogs
user_pref("network.http.prompt-temp-redirect", false);
user_pref("svg.smil.enabled", true); // Needed for SMIL mochitests until bug 482402 lands
user_pref("media.cache_size", 100);
user_pref("security.warn_viewing_mixed", false);

View file

@ -94,11 +94,11 @@ CFLAGS += -DJEMALLOC_LIB='"$(OBJDIR)/dist/lib/jemalloc.lib"'
endif
CFLAGS += -DEBUG -Zi
SDK_TOOLS = $(MOZCE_TOOLS_BIN_DIR)/arm-wince-as.exe \
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-gcc.exe \
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-lib.exe \
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-link.exe \
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-res.exe
SDK_TOOLS = $(MOZCE_TOOLS_BIN_DIR)/$(target)-as.exe \
$(MOZCE_TOOLS_BIN_DIR)/$(target)-gcc.exe \
$(MOZCE_TOOLS_BIN_DIR)/$(target)-lib.exe \
$(MOZCE_TOOLS_BIN_DIR)/$(target)-link.exe \
$(MOZCE_TOOLS_BIN_DIR)/$(target)-res.exe
all: libs export
@ -118,23 +118,23 @@ $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj: $(MOZCE_TOOLS_DIR)/toolspath.c $(MOZCE_TOO
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -c -Fo$(MOZCE_TOOLS_BIN_DIR)/toolspath.obj $(MOZCE_TOOLS_DIR)/toolspath.c
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-as.exe: $(MOZCE_TOOLS_DIR)/arm-wince-as.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/$(target)-as.exe: $(MOZCE_TOOLS_DIR)/arm-wince-as.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -Fo$(MOZCE_TOOLS_BIN_DIR) -Fe$@ $(MOZCE_TOOLS_DIR)/arm-wince-as.c -link $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-gcc.exe: $(MOZCE_TOOLS_DIR)/arm-wince-gcc.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/$(target)-gcc.exe: $(MOZCE_TOOLS_DIR)/arm-wince-gcc.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -Fo$(MOZCE_TOOLS_BIN_DIR) -Fe$@ $(MOZCE_TOOLS_DIR)/arm-wince-gcc.c -link $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-lib.exe: $(MOZCE_TOOLS_DIR)/arm-wince-lib.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/$(target)-lib.exe: $(MOZCE_TOOLS_DIR)/arm-wince-lib.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -Fo$(MOZCE_TOOLS_BIN_DIR) -Fe$@ $(MOZCE_TOOLS_DIR)/arm-wince-lib.c -link $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-link.exe: $(MOZCE_TOOLS_DIR)/arm-wince-link.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/$(target)-link.exe: $(MOZCE_TOOLS_DIR)/arm-wince-link.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -Fo$(MOZCE_TOOLS_BIN_DIR) -Fe$@ $(MOZCE_TOOLS_DIR)/arm-wince-link.c -link $(MOZCE_TOOLS_BIN_DIR)/linkargs.obj $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/arm-wince-res.exe: $(MOZCE_TOOLS_DIR)/arm-wince-res.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
$(MOZCE_TOOLS_BIN_DIR)/$(target)-res.exe: $(MOZCE_TOOLS_DIR)/arm-wince-res.c $(MOZCE_TOOLS_DIR)/toolspath.h $(MOZCE_TOOLS_DIR)/Makefile $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj
mkdir -p $(MOZCE_TOOLS_BIN_DIR);
$(CC) $(CFLAGS) -Fo$(MOZCE_TOOLS_BIN_DIR) -Fe$@ $(MOZCE_TOOLS_DIR)/arm-wince-res.c -link $(MOZCE_TOOLS_BIN_DIR)/toolspath.obj

View file

@ -699,7 +699,7 @@ ifneq (,$(filter WINCE,$(OS_ARCH)))
OUTOPTION = -Fo# eol
endif
ifeq ($(OS_TARGET), WINCE)
ifeq ($(OS_ARCH), WINCE)
OUTOPTION = -Fo# eol
HOST_OUTOPTION = -Fo# eol
else

View file

@ -252,7 +252,7 @@ if test "$COMPILE_ENVIRONMENT"; then
dnl Do some special WinCE toolchain stuff
case "$target" in
*wince)
*wince|*winmo)
MOZ_ARG_WITH_STRING(wince-sdk,
[ --with-wince-sdk=WINCE_SDK_DIR
@ -264,19 +264,6 @@ case "$target" in
The path to the OGLES SDK],
OGLES_SDK_DIR=$withval)
dnl Default to Windows Mobile components enabled
WINCE_WINDOWS_MOBILE=1
MOZ_ARG_DISABLE_BOOL(windows-mobile-components,
[ --disable-windows-mobile-components
Disable Windows Mobile specific components from CE build],
WINCE_WINDOWS_MOBILE=,
WINCE_WINDOWS_MOBILE=1)
if test "$WINCE_WINDOWS_MOBILE"; then
AC_DEFINE(WINCE_WINDOWS_MOBILE)
fi
AC_DEFINE(WINCE)
export WINCE=1
@ -290,16 +277,18 @@ case "$target" in
_pwd=`pwd -W`
_topsrcdirwin=`cd \`dirname $0\`; pwd -W`
make OGLES_SDK_DIR="$OGLES_SDK_DIR" WINCE_SDK_DIR="$WINCE_SDK_DIR" TOPSRCDIR="$_topsrcdirwin" OBJDIR="$_pwd" -C $srcdir/build/wince/tools
make OGLES_SDK_DIR="$OGLES_SDK_DIR" WINCE_SDK_DIR="$WINCE_SDK_DIR" \
TOPSRCDIR="$_topsrcdirwin" OBJDIR="$_pwd" target="$target" \
-C $srcdir/build/wince/tools
CC="$_pwd/dist/sdk/bin/arm-wince-gcc.exe"
CXX="$_pwd/dist/sdk/bin/arm-wince-gcc.exe"
CPP="$_pwd/dist/sdk/bin/arm-wince-gcc.exe -E -nologo"
CXXCPP="$_pwd/dist/sdk/bin/arm-wince-gcc.exe -TP -E -nologo"
LD="$_pwd/dist/sdk/bin/arm-wince-link.exe"
AR="$_pwd/dist/sdk/bin/arm-wince-lib.exe"
AS="$_pwd/dist/sdk/bin/arm-wince-as.exe"
RC="$_pwd/dist/sdk/bin/arm-wince-res.exe"
CC="$_pwd/dist/sdk/bin/$target-gcc.exe"
CXX="$_pwd/dist/sdk/bin/$target-gcc.exe"
CPP="$_pwd/dist/sdk/bin/$target-gcc.exe -E -nologo"
CXXCPP="$_pwd/dist/sdk/bin/$target-gcc.exe -TP -E -nologo"
LD="$_pwd/dist/sdk/bin/$target-link.exe"
AR="$_pwd/dist/sdk/bin/$target-lib.exe"
AS="$_pwd/dist/sdk/bin/$target-as.exe"
RC="$_pwd/dist/sdk/bin/$target-res.exe"
echo -----------------------------------------------------------------------------
@ -473,7 +462,7 @@ fi
dnl Special win32 checks
dnl ========================================================
case "$target" in
*-wince)
*-wince|*-winmo)
WINVER=500
;;
*)
@ -526,7 +515,7 @@ fi
AC_SUBST(MOZ_DISABLE_VISTA_SDK_REQUIREMENTS)
case "$target" in
*-cygwin*|*-mingw*|*-msvc*|*-mks*|*-wince)
*-cygwin*|*-mingw*|*-msvc*|*-mks*|*-wince|*-winmo)
if test "$GCC" != "yes"; then
# Check to see if we are really running in a msvc environemnt
_WIN32_MSVC=1
@ -781,7 +770,7 @@ if test -n "$_WIN32_MSVC"; then
# Since we're skipping compiler and library checks, hard-code
# some facts here.
case "$target" in
*-wince)
*-wince|*-winmo)
;;
*)
AC_DEFINE(HAVE_IO_H)
@ -1092,6 +1081,7 @@ if test -n "$CROSS_COMPILE"; then
solaris*) OS_ARCH=SunOS OS_RELEASE=5 ;;
mingw*) OS_ARCH=WINNT ;;
wince*) OS_ARCH=WINCE ;;
winmo*) OS_ARCH=WINCE ;;
darwin*) OS_ARCH=Darwin OS_TARGET=Darwin ;;
esac
else
@ -1302,7 +1292,16 @@ UnixWare)
;;
WINCE)
OS_ARCH=WINCE
OS_TARGET=WINCE
case "${target_os}" in
*winmo)
OS_TARGET=WINMO
WINCE_WINDOWS_MOBILE=1
AC_DEFINE(WINCE_WINDOWS_MOBILE)
;;
*)
OS_TARGET=WINCE
;;
esac
;;
Darwin)
case "${target_cpu}" in
@ -1650,7 +1649,7 @@ case "$host" in
HOST_OPTIMIZE_FLAGS="${HOST_OPTIMIZE_FLAGS=-O3}"
;;
*cygwin*|*mingw*|*mks*|*msvc*|*wince)
*cygwin*|*mingw*|*mks*|*msvc*|*wince|*winmo)
# we need Python 2.5 on Windows
PYTHON_VERSION=2.5
if test -n "$_WIN32_MSVC"; then
@ -2021,7 +2020,7 @@ case "$target" in
esac
;;
*-wince*)
*-wince*|*-winmo*)
TARGET_COMPILER_ABI=msvc
_PLATFORM_DEFAULT_TOOLKIT=cairo-windows
_PLATFORM_MOZ_DISABLE_VISTA_SDK_REQUIREMENTS=1
@ -2715,7 +2714,7 @@ case "$target" in
*-openvms*)
NO_LD_ARCHIVE_FLAGS=
;;
*-msvc*|*-mks*|*-mingw*|*-cygwin*|*-wince)
*-msvc*|*-mks*|*-mingw*|*-cygwin*|*-wince|*-winmo)
if test -z "$GNU_CC"; then
NO_LD_ARCHIVE_FLAGS=
fi
@ -2747,7 +2746,7 @@ case "$target" in
*-darwin*)
MOZ_COMPONENTS_VERSION_SCRIPT_LDFLAGS='-Wl,-exported_symbols_list -Wl,$(BUILD_TOOLS)/gnu-ld-scripts/components-export-list'
;;
*-cygwin*|*-mingw*|*-mks*|*-msvc|*-wince)
*-cygwin*|*-mingw*|*-mks*|*-msvc|*-wince|*-winmo)
if test -n "$GNU_CC"; then
MOZ_COMPONENTS_VERSION_SCRIPT_LDFLAGS='-Wl,--version-script,$(BUILD_TOOLS)/gnu-ld-scripts/components-version-script'
fi
@ -3642,7 +3641,7 @@ if test "$ac_cv_func_gnu_get_libc_version" = "yes"; then
fi
case $target_os in
os2*|msvc*|mks*|cygwin*|mingw*|darwin*|wince*|beos*)
os2*|msvc*|mks*|cygwin*|mingw*|darwin*|wince*|winmo*|beos*)
;;
*)
@ -4777,9 +4776,7 @@ photon)
cairo-windows)
MOZ_WIDGET_TOOLKIT=windows
if test -z "$WINCE"; then
MOZ_WEBGL=1
fi
MOZ_WEBGL=1
;;
cairo-gtk2|cairo-gtk2-x11)
@ -4787,6 +4784,7 @@ cairo-gtk2|cairo-gtk2-x11)
MOZ_ENABLE_GTK2=1
MOZ_ENABLE_XREMOTE=1
MOZ_WEBGL=1
MOZ_WEBGL_GLX=1
AC_DEFINE(MOZ_X11)
MOZ_X11=1
@ -4800,7 +4798,7 @@ cairo-gtk2|cairo-gtk2-x11)
cairo-gtk2-dfb)
MOZ_WIDGET_TOOLKIT=gtk2
MOZ_ENABLE_GTK2=1
MOZ_WEBGL=1
MOZ_WEBGL=
AC_DEFINE(MOZ_DFB)
MOZ_DFB=1
@ -5956,7 +5954,7 @@ dnl ========================================================
dnl Installer
dnl ========================================================
case "$target_os" in
aix*|solaris*|linux*|msvc*|mks*|cygwin*|mingw*|os2*|wince*)
aix*|solaris*|linux*|msvc*|mks*|cygwin*|mingw*|os2*|wince*|winmo*)
MOZ_INSTALLER=1
;;
esac
@ -6301,7 +6299,7 @@ if test $NS_OSSO; then
fi
AC_DEFINE(NS_OSSO)
MOZ_GFX_OPTIMIZE_MOBILE=1
MOZ_WEBGL=
MOZ_WEBGL_GLX=
fi
AC_SUBST(LIBOSSO_CFLAGS)
AC_SUBST(LIBOSSO_LIBS)
@ -6381,7 +6379,7 @@ MOZ_DEBUG_ENABLE_DEFS="-DDEBUG -D_DEBUG"
beos*)
MOZ_DEBUG_ENABLE_DEFS="$MOZ_DEBUG_ENABLE_DEFS -DDEBUG_${USER}"
;;
msvc*|mks*|cygwin*|mingw*|os2*|wince*)
msvc*|mks*|cygwin*|mingw*|os2*|wince*|winmo*)
MOZ_DEBUG_ENABLE_DEFS="$MOZ_DEBUG_ENABLE_DEFS -DDEBUG_`echo ${USERNAME} | sed -e 's| |_|g'`"
;;
*)
@ -6634,6 +6632,10 @@ if test "$MOZ_MEMORY"; then
AC_DEFINE(MOZ_MEMORY_WINCE6)
fi
;;
*winmo)
AC_DEFINE(MOZ_MEMORY_WINCE)
AC_DEFINE(MOZ_MEMORY_WINDOWS)
;;
*)
AC_MSG_ERROR([--enable-jemalloc not supported on ${target}])
;;
@ -7366,7 +7368,7 @@ MOZ_ARG_HEADER(Standalone module options (Not for building Mozilla))
dnl Check for GLib and libIDL.
dnl ========================================================
case "$target_os" in
msvc*|mks*|cygwin*|mingw*|wince*)
msvc*|mks*|cygwin*|mingw*|wince*|winmo*)
SKIP_IDL_CHECK="yes"
;;
*)
@ -7811,7 +7813,7 @@ dnl
dnl Build jsctypes on the platforms we can.
dnl
AC_SUBST(BUILD_CTYPES)
if test "$OS_TARGET" != "WINCE" -o `echo $OS_TEST | grep -ic arm` != 1; then
if test "$OS_ARCH" != "WINCE" -o `echo $OS_TEST | grep -ic arm` != 1; then
BUILD_CTYPES=1
AC_DEFINE(BUILD_CTYPES)
fi
@ -8141,14 +8143,12 @@ if test "$MOZ_X11"; then
fi # MOZ_X11
dnl Check for headers, etc. needed by WebGL.
if test -n "$MOZ_WEBGL"; then
if test "$MOZ_WIDGET_TOOLKIT" = gtk2; then
AC_CHECK_HEADER(GL/glx.h)
if test "$ac_cv_header_GL_glx_h" != "yes"; then
AC_MSG_ERROR([Can't find header GL/glx.h for WebGL (install mesa-common-dev (Ubuntu), mesa-libGL-devel (Fedora), or Mesa (SuSE))])
fi
if test -n "$MOZ_WEBGL_GLX"; then
AC_CHECK_HEADER(GL/glx.h)
if test "$ac_cv_header_GL_glx_h" != "yes"; then
AC_MSG_ERROR([Can't find header GL/glx.h for WebGL (install mesa-common-dev (Ubuntu), mesa-libGL-devel (Fedora), or Mesa (SuSE))])
fi
fi # MOZ_WEBGL
fi # MOZ_WEBGL_GLX
fi # COMPILE_ENVIRONMENT
if test "$USE_FC_FREETYPE"; then

View file

@ -0,0 +1,9 @@
<html>
<BODY></BODY>
<SCRIPT>
document.addEventListener("DOMCharacterDataModified",function(){
document.body.innerHTML=""; // change this to see memory corruption
},true);
document.body.innerHTML="<optGroup</form<textArea";
</SCRIPT>
</html>

View file

@ -0,0 +1,11 @@
<html>
<BODY></BODY>
<SCRIPT>
document.body.addEventListener("DOMCharacterDataModified", function () {
document.body.innerHTML = "";
eventChild.appendChild(event.relatedNode);
}, true);
document.addEventListener("DOMNodeInserted", function () {}, true);
document.body.innerHTML="]<kbd><small></kbd><base><optGroup></optGroup>";
</SCRIPT>
</html>

View file

@ -48,6 +48,8 @@ load 420620-1.html
load 424276-1.html
load 426987-1.html
load 443538-1.svg
load 450383-1.html
load 450385-1.html
skip load 458637-1.html # sporadically fails -- see bug 473680
load 472593-1.html
load 474041-1.svg

View file

@ -573,6 +573,7 @@ public:
PrefChangedFunc aCallback,
void * aClosure);
static void AddBoolPrefVarCache(const char* aPref, PRBool* aVariable);
static void AddIntPrefVarCache(const char* aPref, PRInt32* aVariable);
static nsIPrefBranch *GetPrefBranch()
{
return sPrefBranch;
@ -670,6 +671,11 @@ public:
*/
static already_AddRefed<imgIContainer> GetImageFromContent(nsIImageLoadingContent* aContent, imgIRequest **aRequest = nsnull);
/**
* Helper method to call imgIRequest::GetStaticRequest.
*/
static already_AddRefed<imgIRequest> GetStaticRequest(imgIRequest* aRequest);
/**
* Method that decides whether a content node is draggable
*

View file

@ -1159,6 +1159,25 @@ public:
PRBool IsDNSPrefetchAllowed() const { return mAllowDNSPrefetch; }
/**
* PR_TRUE when this document is a static clone of a normal document.
* For example print preview and printing use static documents.
*/
PRBool IsStaticDocument() { return mIsStaticDocument; }
/**
* Clones the document and subdocuments and stylesheet etc.
* @param aCloneContainer The container for the clone document.
*/
virtual already_AddRefed<nsIDocument>
CreateStaticClone(nsISupports* aCloneContainer);
/**
* If this document is a static clone, this returns the original
* document.
*/
nsIDocument* GetOriginalDocument() { return mOriginalDocument; }
/**
* Called by nsParser to preload images. Can be removed and code moved
* to nsPreloadURIs::PreloadURIs() in file nsParser.cpp whenever the
@ -1308,6 +1327,16 @@ protected:
// document has no window, DNS prefetch won't be performed no matter what.
PRPackedBool mAllowDNSPrefetch;
// True when this document is a static clone of a normal document
PRPackedBool mIsStaticDocument;
// True while this document is being cloned to a static document.
PRPackedBool mCreatingStaticClone;
// If mIsStaticDocument is true, mOriginalDocument points to the original
// document.
nsCOMPtr<nsIDocument> mOriginalDocument;
// The bidi options for this document. What this bitfield means is
// defined in nsBidiUtils.h
PRUint32 mBidiOptions;

View file

@ -165,15 +165,12 @@ public:
* @param aModType Whether or not the attribute was added, changed, or
* removed. The constants are defined in
* nsIDOMMutationEvent.h.
* @param aStateMask If this attribute change caused content state changes,
* the bits that changed. Might be 0 if no bits changed.
*/
virtual void AttributeChanged(nsIDocument* aDocument,
nsIContent* aContent,
PRInt32 aNameSpaceID,
nsIAtom* aAttribute,
PRInt32 aModType,
PRUint32 aStateMask) = 0;
PRInt32 aModType) = 0;
/**
* Notification that one or more content nodes have been appended to the
@ -280,8 +277,7 @@ NS_DEFINE_STATIC_IID_ACCESSOR(nsIMutationObserver, NS_IMUTATION_OBSERVER_IID)
nsIContent* aContent, \
PRInt32 aNameSpaceID, \
nsIAtom* aAttribute, \
PRInt32 aModType, \
PRUint32 aStateMask);
PRInt32 aModType);
#define NS_DECL_NSIMUTATIONOBSERVER_CONTENTAPPENDED \
virtual void ContentAppended(nsIDocument* aDocument, \
@ -349,8 +345,7 @@ _class::AttributeChanged(nsIDocument* aDocument, \
nsIContent* aContent, \
PRInt32 aNameSpaceID, \
nsIAtom* aAttribute, \
PRInt32 aModType, \
PRUint32 aStateMask) \
PRInt32 aModType) \
{ \
} \
void \

View file

@ -803,7 +803,8 @@ public:
* user does "Select All" while the focus is in this node. Note that if this
* node is not in an editor, the result comes from the nsFrameSelection that
* is related to aPresShell, so the result might not be the ancestor of this
* node.
* node. Be aware that if this node and the computed selection limiter are
* not in same subtree, this returns the root content of the closeset subtree.
*/
nsIContent* GetSelectionRootContent(nsIPresShell* aPresShell);

View file

@ -37,6 +37,7 @@
#include "nsISupports.idl"
interface nsIFrame;
interface nsIObjectFrame;
interface nsIPluginInstance;
interface nsIDOMElement;
@ -45,7 +46,7 @@ interface nsIDOMClientRect;
/**
* This interface represents a content node that loads objects.
*/
[scriptable, uuid(8afe3b08-293c-48bd-a997-321745478611)]
[scriptable, uuid(7749d965-92f3-473e-b12d-de1e342acf1c)]
interface nsIObjectLoadingContent : nsISupports
{
const unsigned long TYPE_LOADING = 0;
@ -115,4 +116,12 @@ interface nsIObjectLoadingContent : nsISupports
void setAbsoluteScreenPosition(in nsIDOMElement element,
in nsIDOMClientRect position,
in nsIDOMClientRect clip);
/**
* If this object is in going to be printed, this method
* returns the nsIObjectFrame object which should be used when
* printing the plugin. The returned nsIFrame is in the original document,
* not in the static clone.
*/
[noscript] nsIFrame getPrintFrame();
};

View file

@ -47,8 +47,8 @@
#include "nsIParser.h"
#define NS_ISCRIPTELEMENT_IID \
{ 0xa28c198e, 0x14f0, 0x42b1, \
{ 0x8f, 0x6b, 0x0e, 0x7f, 0xca, 0xb4, 0xf4, 0xe8 } }
{ 0xa9d5732a, 0x8c1f, 0x439d, \
{ 0x83, 0x75, 0x3d, 0xf6, 0xa9, 0xba, 0xa3, 0x7d } }
/**
* Internal interface implemented by script elements
@ -62,6 +62,9 @@ public:
mIsEvaluated(PR_FALSE),
mMalformed(PR_FALSE),
mDoneAddingChildren(PR_TRUE),
mFrozen(PR_FALSE),
mDefer(PR_FALSE),
mAsync(PR_FALSE),
mCreatorParser(nsnull)
{
}
@ -76,7 +79,11 @@ public:
* Location of script source text. Can return null, in which case
* this is assumed to be an inline script element.
*/
virtual already_AddRefed<nsIURI> GetScriptURI() = 0;
nsIURI* GetScriptURI()
{
NS_PRECONDITION(mFrozen, "Not ready for this call yet!");
return mUri;
}
/**
* Script source text for inline script elements.
@ -85,15 +92,30 @@ public:
virtual void GetScriptCharset(nsAString& charset) = 0;
/**
* Freezes the return values of GetScriptDeferred(), GetScriptAsync() and
* GetScriptURI() so that subsequent modifications to the attributes don't
* change execution behavior.
*/
virtual void FreezeUriAsyncDefer() = 0;
/**
* Is the script deferred. Currently only supported by HTML scripts.
*/
virtual PRBool GetScriptDeferred() = 0;
PRBool GetScriptDeferred()
{
NS_PRECONDITION(mFrozen, "Not ready for this call yet!");
return mDefer;
}
/**
* Is the script async. Currently only supported by HTML scripts.
*/
virtual PRBool GetScriptAsync() = 0;
PRBool GetScriptAsync()
{
NS_PRECONDITION(mFrozen, "Not ready for this call yet!");
return mAsync;
}
void SetScriptLineNumber(PRUint32 aLineNumber)
{
@ -134,8 +156,6 @@ public:
*/
void BeginEvaluating()
{
// Once the async attribute is supported, don't do this if this is an
// async script.
nsCOMPtr<nsIParser> parser = do_QueryReferent(mCreatorParser);
if (parser) {
parser->BeginEvaluatingParserInsertedScript();
@ -147,8 +167,6 @@ public:
*/
void EndEvaluating()
{
// Once the async attribute is supported, don't do this if this is an
// async script.
nsCOMPtr<nsIParser> parser = do_QueryReferent(mCreatorParser);
if (parser) {
parser->EndEvaluatingParserInsertedScript();
@ -165,11 +183,50 @@ public:
}
protected:
/**
* The start line number of the script.
*/
PRUint32 mLineNumber;
/**
* The "already started" flag per HTML5.
*/
PRPackedBool mIsEvaluated;
/**
* The script didn't have an end tag.
*/
PRPackedBool mMalformed;
/**
* False if parser-inserted but the parser hasn't triggered running yet.
*/
PRPackedBool mDoneAddingChildren;
nsWeakPtr mCreatorParser;
/**
* Whether src, defer and async are frozen.
*/
PRPackedBool mFrozen;
/**
* The effective deferredness.
*/
PRPackedBool mDefer;
/**
* The effective asyncness.
*/
PRPackedBool mAsync;
/**
* The effective src (or null if no src).
*/
nsCOMPtr<nsIURI> mUri;
/**
* The creator parser of a non-defer, non-async parser-inserted script.
*/
nsWeakPtr mCreatorParser;
};
NS_DEFINE_STATIC_IID_ACCESSOR(nsIScriptElement, NS_ISCRIPTELEMENT_IID)

View file

@ -532,7 +532,7 @@ nsContentList::GetNamedItem(const nsAString& aName, nsresult* aResult)
void
nsContentList::AttributeChanged(nsIDocument *aDocument, nsIContent* aContent,
PRInt32 aNameSpaceID, nsIAtom* aAttribute,
PRInt32 aModType, PRUint32 aStateMask)
PRInt32 aModType)
{
NS_PRECONDITION(aContent, "Must have a content node to work with");
NS_PRECONDITION(aContent->IsNodeOfType(nsINode::eELEMENT),

View file

@ -360,6 +360,9 @@ nsContentSink::ScriptAvailable(nsresult aResult,
return NS_OK;
}
NS_ASSERTION(!aElement->GetScriptDeferred(), "defer script was in mScriptElements");
NS_ASSERTION(!aElement->GetScriptAsync(), "async script was in mScriptElements");
if (mParser && !mParser->IsParserEnabled()) {
// make sure to unblock the parser before evaluating the script,
// we must unblock the parser even if loading the script failed or
@ -402,6 +405,9 @@ nsContentSink::ScriptEvaluated(nsresult aResult,
return NS_OK;
}
NS_ASSERTION(!aElement->GetScriptDeferred(), "defer script was in mScriptElements");
NS_ASSERTION(!aElement->GetScriptAsync(), "async script was in mScriptElements");
// Pop the script element stack
mScriptElements.RemoveObjectAt(count - 1);

View file

@ -1957,6 +1957,9 @@ nsContentUtils::GenerateStateKey(nsIContent* aContent,
if (htmlDocument) {
// Flush our content model so it'll be up to date
// If this becomes unnecessary and the following line is removed,
// please also remove the corresponding flush operation from
// nsHtml5TreeBuilderCppSupplement.h. (Look for "See bug 497861." there.)
aContent->GetCurrentDoc()->FlushPendingNotifications(Flush_Content);
nsContentList *htmlForms = htmlDocument->GetForms();
@ -2504,6 +2507,16 @@ nsContentUtils::GetImageFromContent(nsIImageLoadingContent* aContent,
return imgContainer.forget();
}
//static
already_AddRefed<imgIRequest>
nsContentUtils::GetStaticRequest(imgIRequest* aRequest)
{
NS_ENSURE_TRUE(aRequest, nsnull);
nsCOMPtr<imgIRequest> retval;
aRequest->GetStaticRequest(getter_AddRefs(retval));
return retval.forget();
}
// static
PRBool
nsContentUtils::ContentIsDraggable(nsIContent* aContent)
@ -2665,6 +2678,23 @@ nsContentUtils::AddBoolPrefVarCache(const char *aPref,
RegisterPrefCallback(aPref, BoolVarChanged, aCache);
}
static int
IntVarChanged(const char *aPref, void *aClosure)
{
PRInt32* cache = static_cast<PRInt32*>(aClosure);
*cache = nsContentUtils::GetIntPref(aPref, 0);
return 0;
}
void
nsContentUtils::AddIntPrefVarCache(const char *aPref,
PRInt32* aCache)
{
*aCache = GetIntPref(aPref, PR_FALSE);
RegisterPrefCallback(aPref, IntVarChanged, aCache);
}
static const char *gEventNames[] = {"event"};
static const char *gSVGEventNames[] = {"evt"};
// for b/w compat, the first name to onerror is still 'event', even though it

View file

@ -2462,8 +2462,7 @@ nsDocument::AttributeWillChange(nsIDocument* aDocument,
void
nsDocument::AttributeChanged(nsIDocument* aDocument,
nsIContent* aContent, PRInt32 aNameSpaceID,
nsIAtom* aAttribute, PRInt32 aModType,
PRUint32 aStateMask)
nsIAtom* aAttribute, PRInt32 aModType)
{
NS_ASSERTION(aDocument == this, "unexpected doc");
@ -3061,6 +3060,9 @@ nsDocument::doCreateShell(nsPresContext* aContext,
// Note: we don't hold a ref to the shell (it holds a ref to us)
NS_ENSURE_TRUE(mPresShells.AppendElementUnlessExists(shell),
NS_ERROR_OUT_OF_MEMORY);
NS_WARN_IF_FALSE(mPresShells.Length() == 1, "More than one presshell!");
shell.swap(*aInstancePtrResult);
return NS_OK;
@ -5344,8 +5346,9 @@ nsDocument::GetAnimationController()
// one and only SVG documents and the like will call this
if (mAnimationController)
return mAnimationController;
// Refuse to create an Animation Controller if SMIL is disabled
if (!NS_SMILEnabled())
// Refuse to create an Animation Controller if SMIL is disabled, and also
// for data documents.
if (!NS_SMILEnabled() || mLoadedAsData)
return nsnull;
mAnimationController = NS_NewSMILAnimationController(this);
@ -7587,6 +7590,8 @@ nsDocument::QuerySelectorAll(const nsAString& aSelector,
nsresult
nsDocument::CloneDocHelper(nsDocument* clone) const
{
clone->mIsStaticDocument = mCreatingStaticClone;
// Init document
nsresult rv = clone->Init();
NS_ENSURE_SUCCESS(rv, rv);
@ -7597,6 +7602,21 @@ nsDocument::CloneDocHelper(nsDocument* clone) const
clone->SetPrincipal(NodePrincipal());
clone->mDocumentBaseURI = mDocumentBaseURI;
if (mCreatingStaticClone) {
nsCOMPtr<nsIChannel> channel = GetChannel();
nsCOMPtr<nsILoadGroup> loadGroup = GetDocumentLoadGroup();
if (channel && loadGroup) {
clone->Reset(channel, loadGroup);
} else {
nsIURI* uri = static_cast<const nsIDocument*>(this)->GetDocumentURI();
if (uri) {
clone->ResetToURI(uri, loadGroup, NodePrincipal());
}
}
nsCOMPtr<nsISupports> container = GetContainer();
clone->SetContainer(container);
}
// Set scripting object
PRBool hasHadScriptObject = PR_TRUE;
nsIScriptGlobalObject* scriptObject =
@ -7821,3 +7841,67 @@ nsIDocument::EnumerateFreezableElements(FreezableElementEnumerator aEnumerator,
EnumerateFreezablesData data = { aEnumerator, aData };
mFreezableElements->EnumerateEntries(EnumerateFreezables, &data);
}
already_AddRefed<nsIDocument>
nsIDocument::CreateStaticClone(nsISupports* aCloneContainer)
{
nsCOMPtr<nsIDOMDocument> domDoc = do_QueryInterface(this);
NS_ENSURE_TRUE(domDoc, nsnull);
mCreatingStaticClone = PR_TRUE;
// Make document use different container during cloning.
nsCOMPtr<nsISupports> originalContainer = GetContainer();
SetContainer(aCloneContainer);
nsCOMPtr<nsIDOMNode> clonedNode;
nsresult rv = domDoc->CloneNode(PR_TRUE, getter_AddRefs(clonedNode));
SetContainer(originalContainer);
nsCOMPtr<nsIDocument> clonedDoc;
if (NS_SUCCEEDED(rv)) {
clonedDoc = do_QueryInterface(clonedNode);
nsCOMPtr<nsIDOMDocument> clonedDOMDoc = do_QueryInterface(clonedDoc);
if (clonedDOMDoc) {
clonedDoc->mOriginalDocument = this;
PRInt32 sheetsCount = GetNumberOfStyleSheets();
for (PRInt32 i = 0; i < sheetsCount; ++i) {
nsCOMPtr<nsICSSStyleSheet> sheet =
do_QueryInterface(GetStyleSheetAt(i));
if (sheet) {
PRBool applicable = PR_TRUE;
sheet->GetApplicable(applicable);
if (applicable) {
nsCOMPtr<nsICSSStyleSheet> clonedSheet;
sheet->Clone(nsnull, nsnull, clonedDoc, nsnull,
getter_AddRefs(clonedSheet));
NS_WARN_IF_FALSE(clonedSheet, "Cloning a stylesheet didn't work!");
if (clonedSheet) {
clonedDoc->AddStyleSheet(clonedSheet);
}
}
}
}
sheetsCount = GetNumberOfCatalogStyleSheets();
for (PRInt32 i = 0; i < sheetsCount; ++i) {
nsCOMPtr<nsICSSStyleSheet> sheet =
do_QueryInterface(GetCatalogStyleSheetAt(i));
if (sheet) {
PRBool applicable = PR_TRUE;
sheet->GetApplicable(applicable);
if (applicable) {
nsCOMPtr<nsICSSStyleSheet> clonedSheet;
sheet->Clone(nsnull, nsnull, clonedDoc, nsnull,
getter_AddRefs(clonedSheet));
NS_WARN_IF_FALSE(clonedSheet, "Cloning a stylesheet didn't work!");
if (clonedSheet) {
clonedDoc->AddCatalogStyleSheet(clonedSheet);
}
}
}
}
}
}
mCreatingStaticClone = PR_FALSE;
return clonedDoc.forget();
}

View file

@ -94,6 +94,8 @@
#include "nsINameSpaceManager.h"
#include "nsThreadUtils.h"
#include "nsICSSStyleSheet.h"
#include "nsIContentViewer.h"
#include "nsIView.h"
#ifdef MOZ_WIDGET_GTK2
@ -161,9 +163,11 @@ nsFrameLoader*
nsFrameLoader::Create(nsIContent* aOwner)
{
NS_ENSURE_TRUE(aOwner, nsnull);
nsIDocument* doc = aOwner->GetCurrentDoc();
nsIDocument* doc = aOwner->GetOwnerDoc();
NS_ENSURE_TRUE(doc && !doc->GetDisplayDocument() &&
!doc->IsLoadedAsData(), nsnull);
((!doc->IsLoadedAsData() && aOwner->GetCurrentDoc()) ||
doc->IsStaticDocument()),
nsnull);
return new nsFrameLoader(aOwner);
}
@ -183,7 +187,7 @@ nsFrameLoader::LoadFrame()
}
nsIDocument* doc = mOwnerContent->GetOwnerDoc();
if (!doc) {
if (!doc || doc->IsStaticDocument()) {
return NS_OK;
}
@ -1107,8 +1111,8 @@ nsFrameLoader::MaybeCreateDocShell()
// Get our parent docshell off the document of mOwnerContent
// XXXbz this is such a total hack.... We really need to have a
// better setup for doing this.
nsIDocument* doc = mOwnerContent->GetDocument();
if (!doc) {
nsIDocument* doc = mOwnerContent->GetOwnerDoc();
if (!doc || !(doc->IsStaticDocument() || mOwnerContent->IsInDoc())) {
return NS_ERROR_UNEXPECTED;
}
@ -1117,8 +1121,9 @@ nsFrameLoader::MaybeCreateDocShell()
return NS_ERROR_NOT_AVAILABLE;
}
nsCOMPtr<nsIWebNavigation> parentAsWebNav =
do_GetInterface(doc->GetScriptGlobalObject());
nsCOMPtr<nsISupports> container =
doc->GetContainer();
nsCOMPtr<nsIWebNavigation> parentAsWebNav = do_QueryInterface(container);
// Create the docshell...
mDocShell = do_CreateInstance("@mozilla.org/docshell;1");
@ -1508,3 +1513,27 @@ nsFrameLoader::ActivateFrameEvent(const nsAString& aType,
return NS_ERROR_FAILURE;
}
nsresult
nsFrameLoader::CreateStaticClone(nsIFrameLoader* aDest)
{
nsFrameLoader* dest = static_cast<nsFrameLoader*>(aDest);
dest->MaybeCreateDocShell();
NS_ENSURE_STATE(dest->mDocShell);
nsCOMPtr<nsIDOMDocument> dummy = do_GetInterface(dest->mDocShell);
nsCOMPtr<nsIContentViewer> viewer;
dest->mDocShell->GetContentViewer(getter_AddRefs(viewer));
NS_ENSURE_STATE(viewer);
nsCOMPtr<nsIDocShell> origDocShell;
GetDocShell(getter_AddRefs(origDocShell));
nsCOMPtr<nsIDOMDocument> domDoc = do_GetInterface(origDocShell);
nsCOMPtr<nsIDocument> doc = do_QueryInterface(domDoc);
NS_ENSURE_STATE(doc);
nsCOMPtr<nsIDocument> clonedDoc = doc->CreateStaticClone(dest->mDocShell);
nsCOMPtr<nsIDOMDocument> clonedDOMDoc = do_QueryInterface(clonedDoc);
viewer->SetDOMDocument(clonedDOMDoc);
return NS_OK;
}

View file

@ -104,6 +104,8 @@ public:
void Finalize();
nsIDocShell* GetExistingDocShell() { return mDocShell; }
nsresult CreateStaticClone(nsIFrameLoader* aDest);
/**
* Called from the layout frame associated with this frame loader;
* this notifies us to hook up with the widget and view.
@ -119,6 +121,8 @@ public:
*/
void Hide();
nsresult CloneForStatic(nsIFrameLoader* aOriginal);
// The guts of an nsIFrameLoaderOwner::SwapFrameLoader implementation. A
// frame loader owner needs to call this, and pass in the two references to
// nsRefPtrs for frame loaders that need to be swapped.

View file

@ -372,6 +372,20 @@ static nsIEditor* GetHTMLEditor(nsPresContext* aPresContext)
return editor;
}
static nsIContent* GetRootForContentSubtree(nsIContent* aContent)
{
NS_ENSURE_TRUE(aContent, nsnull);
nsIContent* stop = aContent->GetBindingParent();
while (aContent) {
nsIContent* parent = aContent->GetParent();
if (parent == stop) {
break;
}
aContent = parent;
}
return aContent;
}
nsIContent*
nsINode::GetSelectionRootContent(nsIPresShell* aPresShell)
{
@ -397,8 +411,13 @@ nsINode::GetSelectionRootContent(nsIPresShell* aPresShell)
if (editor) {
// This node is in HTML editor.
nsIDocument* doc = GetCurrentDoc();
if (!doc || doc->HasFlag(NODE_IS_EDITABLE) || !HasFlag(NODE_IS_EDITABLE))
return GetEditorRootContent(editor);
if (!doc || doc->HasFlag(NODE_IS_EDITABLE) ||
!HasFlag(NODE_IS_EDITABLE)) {
nsIContent* editorRoot = GetEditorRootContent(editor);
return nsContentUtils::IsInSameAnonymousTree(this, editorRoot) ?
editorRoot :
GetRootForContentSubtree(static_cast<nsIContent*>(this));
}
// If the current document is not editable, but current content is
// editable, we should assume that the child of the nearest non-editable
// ancestor is selection root.
@ -413,14 +432,21 @@ nsINode::GetSelectionRootContent(nsIPresShell* aPresShell)
nsCOMPtr<nsFrameSelection> fs = aPresShell->FrameSelection();
nsIContent* content = fs->GetLimiter();
if (content)
return content;
content = fs->GetAncestorLimiter();
if (content)
return content;
nsIDocument* doc = aPresShell->GetDocument();
NS_ENSURE_TRUE(doc, nsnull);
return doc->GetRootContent();
if (!content) {
content = fs->GetAncestorLimiter();
if (!content) {
nsIDocument* doc = aPresShell->GetDocument();
NS_ENSURE_TRUE(doc, nsnull);
content = doc->GetRootContent();
if (!content)
return nsnull;
}
}
// This node might be in another subtree, if so, we should find this subtree's
// root. Otherwise, we can return the content simply.
return nsContentUtils::IsInSameAnonymousTree(this, content) ?
content : GetRootForContentSubtree(static_cast<nsIContent*>(this));
}
nsINodeList*
@ -4432,8 +4458,7 @@ nsGenericElement::SetAttrAndNotify(PRInt32 aNamespaceID,
MOZ_AUTO_DOC_UPDATE(document, UPDATE_CONTENT_STATE, aNotify);
document->ContentStatesChanged(this, nsnull, stateMask);
}
nsNodeUtils::AttributeChanged(this, aNamespaceID, aName, modType,
stateMask);
nsNodeUtils::AttributeChanged(this, aNamespaceID, aName, modType);
}
if (aNamespaceID == kNameSpaceID_XMLEvents &&
@ -4694,8 +4719,7 @@ nsGenericElement::UnsetAttr(PRInt32 aNameSpaceID, nsIAtom* aName,
document->ContentStatesChanged(this, nsnull, stateMask);
}
nsNodeUtils::AttributeChanged(this, aNameSpaceID, aName,
nsIDOMMutationEvent::REMOVAL,
stateMask);
nsIDOMMutationEvent::REMOVAL);
}
rv = AfterSetAttr(aNameSpaceID, aName, nsnull, aNotify);
@ -5142,6 +5166,8 @@ nsGenericElement::GetLinkTarget(nsAString& aTarget)
}
// NOTE: The aPresContext pointer is NOT addrefed.
// *aSelectorList might be null even if NS_OK is returned; this
// happens when all the selectors were pseudo-element selectors.
static nsresult
ParseSelectorList(nsINode* aNode,
const nsAString& aSelectorString,
@ -5157,13 +5183,28 @@ ParseSelectorList(nsINode* aNode,
nsresult rv = doc->CSSLoader()->GetParserFor(nsnull, getter_AddRefs(parser));
NS_ENSURE_SUCCESS(rv, rv);
nsCSSSelectorList* selectorList;
rv = parser->ParseSelectorString(aSelectorString,
doc->GetDocumentURI(),
0, // XXXbz get the right line number!
aSelectorList);
&selectorList);
doc->CSSLoader()->RecycleParser(parser);
NS_ENSURE_SUCCESS(rv, rv);
// Filter out pseudo-element selectors from selectorList
nsCSSSelectorList** slot = &selectorList;
do {
nsCSSSelectorList* cur = *slot;
if (cur->mSelectors->IsPseudoElement()) {
*slot = cur->mNext;
cur->mNext = nsnull;
delete cur;
} else {
slot = &cur->mNext;
}
} while (*slot);
*aSelectorList = selectorList;
// It's not strictly necessary to have a prescontext here, but it's
// a bit of an optimization for various stuff.
*aPresContext = nsnull;

View file

@ -201,7 +201,6 @@ GK_ATOM(click, "click")
GK_ATOM(clickcount, "clickcount")
GK_ATOM(movetoclick, "movetoclick")
GK_ATOM(clip, "clip")
GK_ATOM(clonedTextForPrint, "clonedTextForPrint")
GK_ATOM(close, "close")
GK_ATOM(closed, "closed")
GK_ATOM(closemenu, "closemenu")

View file

@ -987,3 +987,19 @@ nsImageLoadingContent::SetBlockingOnload(PRBool aBlocking)
mBlockingOnload = aBlocking;
}
}
void
nsImageLoadingContent::CreateStaticImageClone(nsImageLoadingContent* aDest) const
{
aDest->mCurrentRequest = nsContentUtils::GetStaticRequest(mCurrentRequest);
aDest->mForcedImageState = mForcedImageState;
aDest->mImageBlockingStatus = mImageBlockingStatus;
aDest->mLoadingEnabled = mLoadingEnabled;
aDest->mStartingLoad = mStartingLoad;
aDest->mIsImageStateForced = mIsImageStateForced;
aDest->mLoading = mLoading;
aDest->mBroken = mBroken;
aDest->mUserDisabled = mUserDisabled;
aDest->mSuppressed = mSuppressed;
}

View file

@ -247,9 +247,10 @@ private:
nsresult FireEvent(const nsAString& aEventType);
class Event;
friend class Event;
protected:
void CreateStaticImageClone(nsImageLoadingContent* aDest) const;
/* MEMBERS */
protected:
nsCOMPtr<imgIRequest> mCurrentRequest;
nsCOMPtr<imgIRequest> mPendingRequest;
nsCOMPtr<nsIURI> mCurrentURI;

View file

@ -118,13 +118,12 @@ void
nsNodeUtils::AttributeChanged(nsIContent* aContent,
PRInt32 aNameSpaceID,
nsIAtom* aAttribute,
PRInt32 aModType,
PRUint32 aStateMask)
PRInt32 aModType)
{
nsIDocument* doc = aContent->GetOwnerDoc();
IMPL_MUTATION_NOTIFICATION(AttributeChanged, aContent,
(doc, aContent, aNameSpaceID, aAttribute,
aModType, aStateMask));
aModType));
}
void

View file

@ -92,14 +92,12 @@ public:
* @param aNameSpaceID Namespace of changed attribute
* @param aAttribute Local-name of changed attribute
* @param aModType Type of change (add/change/removal)
* @param aStateMask States which changed
* @see nsIMutationObserver::AttributeChanged
*/
static void AttributeChanged(nsIContent* aContent,
PRInt32 aNameSpaceID,
nsIAtom* aAttribute,
PRInt32 aModType,
PRUint32 aStateMask);
PRInt32 aModType);
/**
* Send ContentAppended notifications to nsIMutationObservers

View file

@ -812,6 +812,14 @@ nsObjectLoadingContent::HasNewFrame(nsIObjectFrame* aFrame)
LOG(("OBJLC [%p]: Got frame %p (mInstantiating=%i)\n", this, aFrame,
mInstantiating));
nsCOMPtr<nsIContent> thisContent =
do_QueryInterface(static_cast<nsIImageLoadingContent*>(this));
NS_ASSERTION(thisContent, "must be a content");
nsIDocument* doc = thisContent->GetOwnerDoc();
if (!doc || doc->IsStaticDocument()) {
return NS_OK;
}
// "revoke" any existing instantiate event as it likely has out of
// date data (frame pointer etc).
mPendingInstantiateEvent = nsnull;
@ -1098,7 +1106,9 @@ nsObjectLoadingContent::LoadObject(nsIURI* aURI,
// Security checks
if (doc->IsLoadedAsData()) {
Fallback(PR_FALSE);
if (!doc->IsStaticDocument()) {
Fallback(PR_FALSE);
}
return NS_OK;
}
@ -1876,6 +1886,40 @@ nsObjectLoadingContent::GetPluginDisabledState(const nsCString& aContentType)
return ePluginUnsupported;
}
void
nsObjectLoadingContent::CreateStaticClone(nsObjectLoadingContent* aDest) const
{
nsImageLoadingContent::CreateStaticImageClone(aDest);
aDest->mType = mType;
nsObjectLoadingContent* thisObj = const_cast<nsObjectLoadingContent*>(this);
if (thisObj->mPrintFrame.IsAlive()) {
aDest->mPrintFrame = thisObj->mPrintFrame;
} else {
nsIObjectFrame* frame =
const_cast<nsObjectLoadingContent*>(this)->GetExistingFrame(eDontFlush);
nsIFrame* f = do_QueryFrame(frame);
aDest->mPrintFrame = f;
}
if (mFrameLoader) {
nsCOMPtr<nsIContent> content =
do_QueryInterface(static_cast<nsIImageLoadingContent*>((aDest)));
nsFrameLoader* fl = nsFrameLoader::Create(content);
if (fl) {
aDest->mFrameLoader = fl;
mFrameLoader->CreateStaticClone(fl);
}
}
}
NS_IMETHODIMP
nsObjectLoadingContent::GetPrintFrame(nsIFrame** aFrame)
{
*aFrame = mPrintFrame.GetFrame();
return NS_OK;
}
NS_IMETHODIMP
nsObjectLoadingContent::SetAbsoluteScreenPosition(nsIDOMElement* element,
nsIDOMClientRect* position,

View file

@ -53,6 +53,7 @@
#include "nsIObjectLoadingContent.h"
#include "nsIRunnable.h"
#include "nsIChannelClassifier.h"
#include "nsIFrame.h"
class nsAsyncInstantiateEvent;
class AutoNotifier;
@ -223,6 +224,7 @@ class nsObjectLoadingContent : public nsImageLoadingContent
void Traverse(nsCycleCollectionTraversalCallback &cb);
void CreateStaticClone(nsObjectLoadingContent* aDest) const;
private:
/**
* Check whether the given request represents a successful load.
@ -422,6 +424,8 @@ class nsObjectLoadingContent : public nsImageLoadingContent
// A specific state that caused us to fallback
PluginSupportState mPluginState;
nsWeakFrame mPrintFrame;
friend class nsAsyncInstantiateEvent;
};

Some files were not shown because too many files have changed in this diff Show more