rpms/xulrunner/devel xulrunner-a11y.patch, NONE, 1.1 .cvsignore, 1.40, 1.41 sources, 1.41, 1.42 xulrunner.spec, 1.96, 1.97
Christopher Aillon (caillon)
fedora-extras-commits at redhat.com
Mon Mar 17 03:28:34 UTC 2008
Author: caillon
Update of /cvs/extras/rpms/xulrunner/devel
In directory cvs-int.fedora.redhat.com:/tmp/cvs-serv22397
Modified Files:
.cvsignore sources xulrunner.spec
Added Files:
xulrunner-a11y.patch
Log Message:
* Sat Mar 16 2008 Christopher Aillon <caillon at redhat.com> 1.9-0.43
- Update to latest trunk (2008-03-16)
- Add patch to negate a11y slowdown on some pages (#431162)
xulrunner-a11y.patch:
--- NEW FILE xulrunner-a11y.patch ---
a11y perf patch from https://bugzilla.mozilla.org/show_bug.cgi?id=418845
Index: accessible/src/base/nsAccessibilityUtils.cpp
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsAccessibilityUtils.cpp,v
retrieving revision 1.27
diff -u -p -8 -r1.27 nsAccessibilityUtils.cpp
--- accessible/src/base/nsAccessibilityUtils.cpp 20 Feb 2008 07:50:45 -0000 1.27
+++ accessible/src/base/nsAccessibilityUtils.cpp 13 Mar 2008 02:36:00 -0000
@@ -314,31 +314,45 @@ nsAccUtils::FireAccEvent(PRUint32 aEvent
return pAccessible->FireAccessibleEvent(event);
}
PRBool
nsAccUtils::IsAncestorOf(nsIDOMNode *aPossibleAncestorNode,
nsIDOMNode *aPossibleDescendantNode)
{
- NS_ENSURE_TRUE(aPossibleAncestorNode, PR_FALSE);
- NS_ENSURE_TRUE(aPossibleDescendantNode, PR_FALSE);
+ NS_ENSURE_TRUE(aPossibleAncestorNode && aPossibleDescendantNode, PR_FALSE);
nsCOMPtr<nsIDOMNode> loopNode = aPossibleDescendantNode;
nsCOMPtr<nsIDOMNode> parentNode;
while (NS_SUCCEEDED(loopNode->GetParentNode(getter_AddRefs(parentNode))) &&
parentNode) {
if (parentNode == aPossibleAncestorNode) {
return PR_TRUE;
}
loopNode.swap(parentNode);
}
return PR_FALSE;
}
+PRBool
+nsAccUtils::AreSiblings(nsIDOMNode *aDOMNode1,
+ nsIDOMNode *aDOMNode2)
+{
+ NS_ENSURE_TRUE(aDOMNode1 && aDOMNode2, PR_FALSE);
+
+ nsCOMPtr<nsIDOMNode> parentNode1, parentNode2;
+ if (NS_SUCCEEDED(aDOMNode1->GetParentNode(getter_AddRefs(parentNode1))) &&
+ NS_SUCCEEDED(aDOMNode2->GetParentNode(getter_AddRefs(parentNode2))) &&
+ parentNode1 == parentNode2) {
+ return PR_TRUE;
+ }
+ return PR_FALSE;
+}
+
already_AddRefed<nsIAccessible>
nsAccUtils::GetAncestorWithRole(nsIAccessible *aDescendant, PRUint32 aRole)
{
nsCOMPtr<nsIAccessible> parentAccessible = aDescendant, testRoleAccessible;
while (NS_SUCCEEDED(parentAccessible->GetParent(getter_AddRefs(testRoleAccessible))) &&
testRoleAccessible) {
PRUint32 testRole;
testRoleAccessible->GetFinalRole(&testRole);
Index: accessible/src/base/nsAccessibilityUtils.h
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsAccessibilityUtils.h,v
retrieving revision 1.21
diff -u -p -8 -r1.21 nsAccessibilityUtils.h
--- accessible/src/base/nsAccessibilityUtils.h 12 Feb 2008 07:24:05 -0000 1.21
+++ accessible/src/base/nsAccessibilityUtils.h 13 Mar 2008 02:36:00 -0000
@@ -144,16 +144,23 @@ public:
* @param aPossibleAncestorNode -- node to test for ancestor-ness of aPossibleDescendantNode
* @param aPossibleDescendantNode -- node to test for descendant-ness of aPossibleAncestorNode
* @return PR_TRUE if aPossibleAncestorNode is an ancestor of aPossibleDescendantNode
*/
static PRBool IsAncestorOf(nsIDOMNode *aPossibleAncestorNode,
nsIDOMNode *aPossibleDescendantNode);
/**
+ * Are the first node and the second siblings?
+ * @return PR_TRUE if aDOMNode1 and aDOMNode2 have same parent
+ */
+ static PRBool AreSiblings(nsIDOMNode *aDOMNode1,
+ nsIDOMNode *aDOMNode2);
+
+ /**
* If an ancestor in this document exists with the given role, return it
* @param aDescendant Descendant to start search with
* @param aRole Role to find matching ancestor for
* @return The ancestor accessible with the given role, or nsnull if no match is found
*/
static already_AddRefed<nsIAccessible>
GetAncestorWithRole(nsIAccessible *aDescendant, PRUint32 aRole);
Index: accessible/src/base/nsAccessibleEventData.cpp
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsAccessibleEventData.cpp,v
retrieving revision 1.28
diff -u -p -8 -r1.28 nsAccessibleEventData.cpp
--- accessible/src/base/nsAccessibleEventData.cpp 19 Feb 2008 11:22:01 -0000 1.28
+++ accessible/src/base/nsAccessibleEventData.cpp 13 Mar 2008 02:36:00 -0000
@@ -52,28 +52,35 @@
#include "nsIAccessibleText.h"
#include "nsIContent.h"
#include "nsIPresShell.h"
#include "nsPresContext.h"
PRBool nsAccEvent::gLastEventFromUserInput = PR_FALSE;
nsIDOMNode* nsAccEvent::gLastEventNodeWeak = 0;
-NS_IMPL_ISUPPORTS1(nsAccEvent, nsIAccessibleEvent)
+NS_IMPL_QUERY_HEAD(nsAccEvent)
+NS_IMPL_QUERY_BODY(nsAccEvent)
+NS_IMPL_QUERY_BODY(nsISupports)
+NS_IMPL_QUERY_BODY(nsIAccessibleEvent)
+NS_IMPL_QUERY_TAIL_GUTS
+
+NS_IMPL_ADDREF(nsAccEvent)
+NS_IMPL_RELEASE(nsAccEvent)
nsAccEvent::nsAccEvent(PRUint32 aEventType, nsIAccessible *aAccessible,
- PRBool aIsAsynch):
- mEventType(aEventType), mAccessible(aAccessible)
+ PRBool aIsAsynch, EEventRule aEventRule):
+ mEventType(aEventType), mAccessible(aAccessible), mEventRule(aEventRule)
{
CaptureIsFromUserInput(aIsAsynch);
}
nsAccEvent::nsAccEvent(PRUint32 aEventType, nsIDOMNode *aDOMNode,
- PRBool aIsAsynch):
- mEventType(aEventType), mDOMNode(aDOMNode)
+ PRBool aIsAsynch, EEventRule aEventRule):
+ mEventType(aEventType), mDOMNode(aDOMNode), mEventRule(aEventRule)
{
CaptureIsFromUserInput(aIsAsynch);
}
void nsAccEvent::GetLastEventAttributes(nsIDOMNode *aNode,
nsIPersistentProperties *aAttributes)
{
if (aNode == gLastEventNodeWeak) {
@@ -277,16 +284,102 @@ nsAccEvent::GetAccessibleByNode()
}
}
}
#endif
return accessible;
}
+/* static */
+void
+nsAccEvent::ApplyEventRules(nsCOMArray<nsIAccessibleEvent> &aEventsToFire)
+{
+ PRUint32 numQueuedEvents = aEventsToFire.Count();
+ for (PRInt32 tail = numQueuedEvents - 1; tail >= 0; tail --) {
+ nsRefPtr<nsAccEvent> tailEvent = GetAccEventPtr(aEventsToFire[tail]);
+ switch(tailEvent->mEventRule) {
+ case nsAccEvent::eCoalesceFromSameSubtree:
+ {
+ for (PRInt32 index = 0; index < tail; index ++) {
+ nsRefPtr<nsAccEvent> thisEvent = GetAccEventPtr(aEventsToFire[index]);
+ if (thisEvent->mEventType != tailEvent->mEventType)
+ continue; // Different type
+
+ if (thisEvent->mEventRule == nsAccEvent::eAllowDupes ||
+ thisEvent->mEventRule == nsAccEvent::eDoNotEmit)
+ continue; // Do not need to check
+
+ if (thisEvent->mDOMNode == tailEvent->mDOMNode) {
+ // Dupe
+ thisEvent->mEventRule = nsAccEvent::eDoNotEmit;
+ continue;
+ }
+ if (nsAccUtils::IsAncestorOf(tailEvent->mDOMNode,
+ thisEvent->mDOMNode)) {
+ // thisDOMNode is a descendant of tailDOMNode
+ // Do not emit thisEvent, also apply this result to sibling
+ // nodes of thisDOMNode.
+ thisEvent->mEventRule = nsAccEvent::eDoNotEmit;
+ ApplyToSiblings(aEventsToFire, 0, index, thisEvent->mEventType,
+ thisEvent->mDOMNode, nsAccEvent::eDoNotEmit);
+ continue;
+ }
+ if (nsAccUtils::IsAncestorOf(thisEvent->mDOMNode,
+ tailEvent->mDOMNode)) {
+ // tailDOMNode is a descendant of thisDOMNode
+ // Do not emit tailEvent, also apply this result to sibling
+ // nodes of tailDOMNode.
+ tailEvent->mEventRule = nsAccEvent::eDoNotEmit;
+ ApplyToSiblings(aEventsToFire, 0, tail, tailEvent->mEventType,
+ tailEvent->mDOMNode, nsAccEvent::eDoNotEmit);
+ break;
+ }
+ } // for (index)
+
+ if (tailEvent->mEventRule != nsAccEvent::eDoNotEmit) {
+ // This event should be emitted
+ // Apply this result to sibling nodes of tailDOMNode
+ ApplyToSiblings(aEventsToFire, 0, tail, tailEvent->mEventType,
+ tailEvent->mDOMNode, nsAccEvent::eAllowDupes);
+ }
+ } break; // case eCoalesceFromSameSubtree
+
+ case nsAccEvent::eRemoveDupes:
+ {
+ // Check for repeat events.
+ for (PRInt32 index = 0; index < tail; index ++) {
+ nsRefPtr<nsAccEvent> accEvent = GetAccEventPtr(aEventsToFire[index]);
+ if (accEvent->mEventType == tailEvent->mEventType &&
+ accEvent->mEventRule == tailEvent->mEventRule &&
+ accEvent->mDOMNode == tailEvent->mDOMNode) {
+ accEvent->mEventRule = nsAccEvent::eDoNotEmit;
+ }
+ }
+ } break; // case eRemoveDupes
+ } // switch
+ } // for (tail)
+}
+
+/* static */
+void
+nsAccEvent::ApplyToSiblings(nsCOMArray<nsIAccessibleEvent> &aEventsToFire,
+ PRUint32 aStart, PRUint32 aEnd,
+ PRUint32 aEventType, nsIDOMNode* aDOMNode,
+ EEventRule aEventRule)
+{
+ for (PRUint32 index = aStart; index < aEnd; index ++) {
+ nsRefPtr<nsAccEvent> accEvent = GetAccEventPtr(aEventsToFire[index]);
+ if (accEvent->mEventType == aEventType &&
+ accEvent->mEventRule != nsAccEvent::eDoNotEmit &&
+ nsAccUtils::AreSiblings(accEvent->mDOMNode, aDOMNode)) {
+ accEvent->mEventRule = aEventRule;
+ }
+ }
+}
// nsAccStateChangeEvent
NS_IMPL_ISUPPORTS_INHERITED1(nsAccStateChangeEvent, nsAccEvent,
nsIAccessibleStateChangeEvent)
nsAccStateChangeEvent::
nsAccStateChangeEvent(nsIAccessible *aAccessible,
PRUint32 aState, PRBool aIsExtraState,
Index: accessible/src/base/nsAccessibleEventData.h
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsAccessibleEventData.h,v
retrieving revision 1.31
diff -u -p -8 -r1.31 nsAccessibleEventData.h
--- accessible/src/base/nsAccessibleEventData.h 19 Feb 2008 11:22:01 -0000 1.31
+++ accessible/src/base/nsAccessibleEventData.h 13 Mar 2008 02:36:00 -0000
@@ -36,56 +36,106 @@
* 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 ***** */
#ifndef _nsAccessibleEventData_H_
#define _nsAccessibleEventData_H_
+#include "nsAutoPtr.h"
#include "nsCOMPtr.h"
+#include "nsCOMArray.h"
#include "nsIAccessibleEvent.h"
#include "nsIAccessible.h"
#include "nsIAccessibleDocument.h"
#include "nsIDOMNode.h"
#include "nsString.h"
class nsIPresShell;
+#define NS_ACCEVENT_IMPL_CID \
+{ /* 55b89892-a83d-4252-ba78-cbdf53a86936 */ \
+ 0x55b89892, \
+ 0xa83d, \
+ 0x4252, \
+ { 0xba, 0x78, 0xcb, 0xdf, 0x53, 0xa8, 0x69, 0x36 } \
+}
+
class nsAccEvent: public nsIAccessibleEvent
{
public:
+
+ // Rule for accessible events.
+ // The rule will be applied when flushing pending events.
+ enum EEventRule {
+ // eAllowDupes : More than one event of the same type is allowed.
+ // This event will always be emitted.
+ eAllowDupes,
+ // eCoalesceFromSameSubtree : For events of the same type from the same
+ // subtree or the same node, only the umbrelle event on the ancestor
+ // will be emitted.
+ eCoalesceFromSameSubtree,
+ // eRemoveDupes : For repeat events, only the newest event in queue
+ // will be emitted.
+ eRemoveDupes,
+ // eDoNotEmit : This event is confirmed as a duplicate, do not emit it.
+ eDoNotEmit
+ };
+
+ NS_DECLARE_STATIC_IID_ACCESSOR(NS_ACCEVENT_IMPL_CID)
+
// Initialize with an nsIAccessible
- nsAccEvent(PRUint32 aEventType, nsIAccessible *aAccessible, PRBool aIsAsynch = PR_FALSE);
+ nsAccEvent(PRUint32 aEventType, nsIAccessible *aAccessible,
+ PRBool aIsAsynch = PR_FALSE,
+ EEventRule aEventRule = eRemoveDupes);
// Initialize with an nsIDOMNode
- nsAccEvent(PRUint32 aEventType, nsIDOMNode *aDOMNode, PRBool aIsAsynch = PR_FALSE);
+ nsAccEvent(PRUint32 aEventType, nsIDOMNode *aDOMNode,
+ PRBool aIsAsynch = PR_FALSE,
+ EEventRule aEventRule = eRemoveDupes);
virtual ~nsAccEvent() {}
NS_DECL_ISUPPORTS
NS_DECL_NSIACCESSIBLEEVENT
static void GetLastEventAttributes(nsIDOMNode *aNode,
nsIPersistentProperties *aAttributes);
protected:
already_AddRefed<nsIAccessible> GetAccessibleByNode();
void CaptureIsFromUserInput(PRBool aIsAsynch);
PRBool mIsFromUserInput;
private:
PRUint32 mEventType;
+ EEventRule mEventRule;
nsCOMPtr<nsIAccessible> mAccessible;
nsCOMPtr<nsIDOMNode> mDOMNode;
nsCOMPtr<nsIAccessibleDocument> mDocAccessible;
static PRBool gLastEventFromUserInput;
static nsIDOMNode* gLastEventNodeWeak;
public:
+ static PRUint32 EventType(nsIAccessibleEvent *aAccEvent) {
+ PRUint32 eventType;
+ aAccEvent->GetEventType(&eventType);
+ return eventType;
+ }
+ static EEventRule EventRule(nsIAccessibleEvent *aAccEvent) {
+ nsRefPtr<nsAccEvent> accEvent = GetAccEventPtr(aAccEvent);
+ return accEvent->mEventRule;
+ }
+ static PRBool IsFromUserInput(nsIAccessibleEvent *aAccEvent) {
+ PRBool isFromUserInput;
+ aAccEvent->GetIsFromUserInput(&isFromUserInput);
+ return isFromUserInput;
+ }
+
static void ResetLastInputState()
{gLastEventFromUserInput = PR_FALSE; gLastEventNodeWeak = nsnull; }
/**
* Find and cache the last input state. This will be called automatically
* for synchronous events. For asynchronous events it should be
* called from the synchronous code which is the true source of the event,
* before the event is fired.
@@ -98,18 +148,51 @@ public:
/**
* The input state was previously stored with the nsIAccessibleEvent,
* so use that state now -- call this when about to flush an event that
* was waiting in an event queue
*/
static void PrepareForEvent(nsIAccessibleEvent *aEvent,
PRBool aForceIsFromUserInput = PR_FALSE);
+
+ /**
+ * Apply event rules to pending events, this method is called in
+ * FlushingPendingEvents().
+ * Result of this method:
+ * Event rule of filtered events will be set to eDoNotEmit.
+ * Events with other event rule are good to emit.
+ */
+ static void ApplyEventRules(nsCOMArray<nsIAccessibleEvent> &aEventsToFire);
+
+private:
+ static already_AddRefed<nsAccEvent> GetAccEventPtr(nsIAccessibleEvent *aAccEvent) {
+ nsAccEvent* accEvent = nsnull;
+ aAccEvent->QueryInterface(NS_GET_IID(nsAccEvent), (void**)&accEvent);
+ return accEvent;
+ }
+
+ /**
+ * Apply aEventRule to same type event that from sibling nodes of aDOMNode.
+ * @param aEventsToFire array of pending events
+ * @param aStart start index of pending events to be scanned
+ * @param aEnd end index to be scanned (not included)
+ * @param aEventType target event type
+ * @param aDOMNode target are siblings of this node
+ * @param aEventRule the event rule to be applied
+ * (should be eDoNotEmit or eAllowDupes)
+ */
+ static void ApplyToSiblings(nsCOMArray<nsIAccessibleEvent> &aEventsToFire,
+ PRUint32 aStart, PRUint32 aEnd,
+ PRUint32 aEventType, nsIDOMNode* aDOMNode,
+ EEventRule aEventRule);
};
+NS_DEFINE_STATIC_IID_ACCESSOR(nsAccEvent, NS_ACCEVENT_IMPL_CID)
+
class nsAccStateChangeEvent: public nsAccEvent,
public nsIAccessibleStateChangeEvent
{
public:
nsAccStateChangeEvent(nsIAccessible *aAccessible,
PRUint32 aState, PRBool aIsExtraState,
PRBool aIsEnabled);
Index: accessible/src/base/nsCaretAccessible.cpp
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsCaretAccessible.cpp,v
retrieving revision 1.64
diff -u -p -8 -r1.64 nsCaretAccessible.cpp
--- accessible/src/base/nsCaretAccessible.cpp 26 Feb 2008 08:51:11 -0000 1.64
+++ accessible/src/base/nsCaretAccessible.cpp 13 Mar 2008 02:36:00 -0000
@@ -239,17 +239,17 @@ NS_IMETHODIMP nsCaretAccessible::NotifyS
}
mLastCaretOffset = caretOffset;
mLastTextAccessible = textAcc;
nsCOMPtr<nsIAccessibleCaretMoveEvent> event =
new nsAccCaretMoveEvent(focusNode);
NS_ENSURE_TRUE(event, NS_ERROR_OUT_OF_MEMORY);
- return mRootAccessible->FireDelayedAccessibleEvent(event, nsDocAccessible::eRemoveDupes);
+ return mRootAccessible->FireDelayedAccessibleEvent(event);
}
nsRect
nsCaretAccessible::GetCaretRect(nsIWidget **aOutWidget)
{
nsRect caretRect;
NS_ENSURE_TRUE(aOutWidget, caretRect);
*aOutWidget = nsnull;
Index: accessible/src/base/nsDocAccessible.cpp
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsDocAccessible.cpp,v
retrieving revision 1.234
diff -u -p -8 -r1.234 nsDocAccessible.cpp
--- accessible/src/base/nsDocAccessible.cpp 29 Feb 2008 15:38:35 -0000 1.234
+++ accessible/src/base/nsDocAccessible.cpp 13 Mar 2008 02:36:01 -0000
@@ -1021,17 +1021,17 @@ nsDocAccessible::AttributeChangedImpl(ns
// in the wrong namespace or an element that doesn't support it
InvalidateCacheSubtree(aContent, nsIAccessibleEvent::EVENT_DOM_SIGNIFICANT_CHANGE);
return;
}
if (aAttribute == nsAccessibilityAtoms::alt ||
aAttribute == nsAccessibilityAtoms::title) {
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_NAME_CHANGE,
- targetNode, eRemoveDupes);
+ targetNode);
return;
}
if (aAttribute == nsAccessibilityAtoms::selected ||
aAttribute == nsAccessibilityAtoms::aria_selected) {
// ARIA or XUL selection
nsCOMPtr<nsIAccessible> multiSelect = GetMultiSelectFor(targetNode);
// Multi selects use selection_add and selection_remove
@@ -1043,17 +1043,18 @@ nsDocAccessible::AttributeChangedImpl(ns
// Need to find the right event to use here, SELECTION_WITHIN would
// seem right but we had started using it for something else
nsCOMPtr<nsIAccessNode> multiSelectAccessNode =
do_QueryInterface(multiSelect);
nsCOMPtr<nsIDOMNode> multiSelectDOMNode;
multiSelectAccessNode->GetDOMNode(getter_AddRefs(multiSelectDOMNode));
NS_ASSERTION(multiSelectDOMNode, "A new accessible without a DOM node!");
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_SELECTION_WITHIN,
- multiSelectDOMNode, eAllowDupes);
+ multiSelectDOMNode,
+ nsAccEvent::eAllowDupes);
static nsIContent::AttrValuesArray strings[] =
{&nsAccessibilityAtoms::_empty, &nsAccessibilityAtoms::_false, nsnull};
if (aContent->FindAttrValueIn(kNameSpaceID_None, aAttribute,
strings, eCaseMatters) >= 0) {
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_SELECTION_REMOVE,
targetNode);
return;
@@ -1394,103 +1395,39 @@ nsDocAccessible::CreateTextChangeEventFo
new nsAccTextChangeEvent(aContainerAccessible, offset, length, aIsInserting, aIsAsynch);
NS_IF_ADDREF(event);
return event;
}
nsresult nsDocAccessible::FireDelayedToolkitEvent(PRUint32 aEvent,
nsIDOMNode *aDOMNode,
- EDupeEventRule aAllowDupes,
+ nsAccEvent::EEventRule aAllowDupes,
PRBool aIsAsynch)
{
nsCOMPtr<nsIAccessibleEvent> event =
- new nsAccEvent(aEvent, aDOMNode, aIsAsynch);
+ new nsAccEvent(aEvent, aDOMNode, aIsAsynch, aAllowDupes);
NS_ENSURE_TRUE(event, NS_ERROR_OUT_OF_MEMORY);
- return FireDelayedAccessibleEvent(event, aAllowDupes);
+ return FireDelayedAccessibleEvent(event);
}
nsresult
-nsDocAccessible::FireDelayedAccessibleEvent(nsIAccessibleEvent *aEvent,
- EDupeEventRule aAllowDupes)
+nsDocAccessible::FireDelayedAccessibleEvent(nsIAccessibleEvent *aEvent)
{
NS_ENSURE_TRUE(aEvent, NS_ERROR_FAILURE);
- PRBool isTimerStarted = PR_TRUE;
- PRInt32 numQueuedEvents = mEventsToFire.Count();
if (!mFireEventTimer) {
// Do not yet have a timer going for firing another event.
mFireEventTimer = do_CreateInstance("@mozilla.org/timer;1");
NS_ENSURE_TRUE(mFireEventTimer, NS_ERROR_OUT_OF_MEMORY);
}
- PRUint32 newEventType;
- aEvent->GetEventType(&newEventType);
-
- nsCOMPtr<nsIDOMNode> newEventDOMNode;
- aEvent->GetDOMNode(getter_AddRefs(newEventDOMNode));
-
- if (numQueuedEvents == 0) {
- isTimerStarted = PR_FALSE;
- } else if (aAllowDupes == eCoalesceFromSameSubtree) {
- // Especially for mutation events, we will define a duplicate event
- // as one on the same node or on a descendant node.
- // This prevents a flood of events when a subtree is changed.
- for (PRInt32 index = 0; index < numQueuedEvents; index ++) {
- nsIAccessibleEvent *accessibleEvent = mEventsToFire[index];
- NS_ASSERTION(accessibleEvent, "Array item is not an accessible event");
- if (!accessibleEvent) {
- continue;
- }
- PRUint32 eventType;
- accessibleEvent->GetEventType(&eventType);
- if (eventType == newEventType) {
- nsCOMPtr<nsIDOMNode> domNode;
- accessibleEvent->GetDOMNode(getter_AddRefs(domNode));
- if (newEventDOMNode == domNode || nsAccUtils::IsAncestorOf(newEventDOMNode, domNode)) {
- mEventsToFire.RemoveObjectAt(index);
- // The other event is the same type, but in a descendant of this
- // event, so remove that one. The umbrella event in the ancestor
- // is already enough
- -- index;
- -- numQueuedEvents;
- }
- else if (nsAccUtils::IsAncestorOf(domNode, newEventDOMNode)) {
- // There is a better SHOW/HIDE event (it's in an ancestor)
- return NS_OK;
- }
- }
- }
- } else if (aAllowDupes == eRemoveDupes) {
- // Check for repeat events. If a redundant event exists remove
- // original and put the new event at the end of the queue
- // so it is fired after the others
- for (PRInt32 index = 0; index < numQueuedEvents; index ++) {
- nsIAccessibleEvent *accessibleEvent = mEventsToFire[index];
- NS_ASSERTION(accessibleEvent, "Array item is not an accessible event");
- if (!accessibleEvent) {
- continue;
- }
- PRUint32 eventType;
- accessibleEvent->GetEventType(&eventType);
- if (eventType == newEventType) {
- nsCOMPtr<nsIDOMNode> domNode;
- accessibleEvent->GetDOMNode(getter_AddRefs(domNode));
- if (domNode == newEventDOMNode) {
- mEventsToFire.RemoveObjectAt(index);
- -- index;
- -- numQueuedEvents;
- }
- }
- }
- }
-
mEventsToFire.AppendObject(aEvent);
- if (!isTimerStarted) {
+ if (mEventsToFire.Count() == 1) {
// This is be the first delayed event in queue, start timer
// so that event gets fired via FlushEventsCallback
NS_ADDREF_THIS(); // Kung fu death grip to prevent crash in callback
mFireEventTimer->InitWithFuncCallback(FlushEventsCallback,
static_cast<nsPIAccessibleDocument*>(this),
0, nsITimer::TYPE_ONE_SHOT);
}
@@ -1499,30 +1436,32 @@ nsDocAccessible::FireDelayedAccessibleEv
NS_IMETHODIMP nsDocAccessible::FlushPendingEvents()
{
PRUint32 length = mEventsToFire.Count();
NS_ASSERTION(length, "How did we get here without events to fire?");
nsCOMPtr<nsIPresShell> presShell = GetPresShell();
if (!presShell)
length = 0; // The doc is now shut down, don't fire events in it anymore
- PRUint32 index;
- for (index = 0; index < length; index ++) {
+ else
+ nsAccEvent::ApplyEventRules(mEventsToFire);
+
+ for (PRUint32 index = 0; index < length; index ++) {
nsCOMPtr<nsIAccessibleEvent> accessibleEvent(
do_QueryInterface(mEventsToFire[index]));
- NS_ASSERTION(accessibleEvent, "Array item is not an accessible event");
+
+ if (nsAccEvent::EventRule(accessibleEvent) == nsAccEvent::eDoNotEmit)
+ continue;
nsCOMPtr<nsIAccessible> accessible;
accessibleEvent->GetAccessible(getter_AddRefs(accessible));
nsCOMPtr<nsIDOMNode> domNode;
accessibleEvent->GetDOMNode(getter_AddRefs(domNode));
- PRUint32 eventType;
- accessibleEvent->GetEventType(&eventType);
- PRBool isFromUserInput;
- accessibleEvent->GetIsFromUserInput(&isFromUserInput);
+ PRUint32 eventType = nsAccEvent::EventType(accessibleEvent);
+ PRBool isFromUserInput = nsAccEvent::IsFromUserInput(accessibleEvent);
if (domNode == gLastFocusedNode &&
eventType == nsIAccessibleEvent::EVENT_ASYNCH_HIDE ||
eventType == nsIAccessibleEvent::EVENT_ASYNCH_SHOW) {
// If frame type didn't change for this event, then we don't actually need to invalidate
// However, we only keep track of the old frame type for the focus, where it's very
// important not to destroy and recreate the accessible for minor style changes,
// such as a:focus { overflow: scroll; }
@@ -1935,33 +1874,35 @@ NS_IMETHODIMP nsDocAccessible::Invalidat
// Fire EVENT_SHOW, EVENT_MENUPOPUP_START for newly visible content.
// Fire after a short timer, because we want to make sure the view has been
// updated to make this accessible content visible. If we don't wait,
// the assistive technology may receive the event and then retrieve
// nsIAccessibleStates::STATE_INVISIBLE for the event's accessible object.
PRUint32 additionEvent = isAsynch ? nsIAccessibleEvent::EVENT_ASYNCH_SHOW :
nsIAccessibleEvent::EVENT_DOM_CREATE;
FireDelayedToolkitEvent(additionEvent, childNode,
- eCoalesceFromSameSubtree, isAsynch);
+ nsAccEvent::eCoalesceFromSameSubtree,
+ isAsynch);
// Check to see change occured in an ARIA menu, and fire
// an EVENT_MENUPOPUP_START if it did.
nsRoleMapEntry *roleMapEntry = nsAccUtils::GetRoleMapEntry(childNode);
if (roleMapEntry && roleMapEntry->role == nsIAccessibleRole::ROLE_MENUPOPUP) {
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_MENUPOPUP_START,
- childNode, eRemoveDupes, isAsynch);
+ childNode, nsAccEvent::eRemoveDupes,
+ isAsynch);
}
// Check to see if change occured inside an alert, and fire an EVENT_ALERT if it did
nsIContent *ancestor = aChild;
while (PR_TRUE) {
if (roleMapEntry && roleMapEntry->role == nsIAccessibleRole::ROLE_ALERT) {
nsCOMPtr<nsIDOMNode> alertNode(do_QueryInterface(ancestor));
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_ALERT, alertNode,
- eRemoveDupes, isAsynch);
+ nsAccEvent::eRemoveDupes, isAsynch);
break;
}
ancestor = ancestor->GetParent();
nsCOMPtr<nsIDOMNode> ancestorNode = do_QueryInterface(ancestor);
if (!ancestorNode) {
break;
}
roleMapEntry = nsAccUtils::GetRoleMapEntry(ancestorNode);
@@ -1969,19 +1910,20 @@ NS_IMETHODIMP nsDocAccessible::Invalidat
}
if (!isShowing) {
// Fire an event so the assistive technology knows the children have changed
// This is only used by older MSAA clients. Newer ones should derive this
// from SHOW and HIDE so that they don't fetch extra objects
if (childAccessible) {
nsCOMPtr<nsIAccessibleEvent> reorderEvent =
- new nsAccEvent(nsIAccessibleEvent::EVENT_REORDER, containerAccessible, isAsynch);
+ new nsAccEvent(nsIAccessibleEvent::EVENT_REORDER, containerAccessible,
+ isAsynch, nsAccEvent::eCoalesceFromSameSubtree);
NS_ENSURE_TRUE(reorderEvent, NS_ERROR_OUT_OF_MEMORY);
- FireDelayedAccessibleEvent(reorderEvent, eCoalesceFromSameSubtree);
+ FireDelayedAccessibleEvent(reorderEvent);
}
}
return NS_OK;
}
NS_IMETHODIMP
nsDocAccessible::GetAccessibleInParentChain(nsIDOMNode *aNode,
@@ -2047,23 +1989,24 @@ nsDocAccessible::FireShowHideEvents(nsID
if (accessible) {
// Found an accessible, so fire the show/hide on it and don't
// look further into this subtree
PRBool isAsynch = aEventType == nsIAccessibleEvent::EVENT_ASYNCH_HIDE ||
aEventType == nsIAccessibleEvent::EVENT_ASYNCH_SHOW;
nsCOMPtr<nsIAccessibleEvent> event =
- new nsAccEvent(aEventType, accessible, isAsynch);
+ new nsAccEvent(aEventType, accessible, isAsynch,
+ nsAccEvent::eCoalesceFromSameSubtree);
NS_ENSURE_TRUE(event, NS_ERROR_OUT_OF_MEMORY);
if (aForceIsFromUserInput) {
nsAccEvent::PrepareForEvent(event, aForceIsFromUserInput);
}
if (aDelay) {
- return FireDelayedAccessibleEvent(event, eCoalesceFromSameSubtree);
+ return FireDelayedAccessibleEvent(event);
}
return FireAccessibleEvent(event);
}
// Could not find accessible to show hide yet, so fire on any
// accessible descendants in this subtree
nsCOMPtr<nsIContent> content(do_QueryInterface(aDOMNode));
PRUint32 count = content->GetChildCount();
Index: accessible/src/base/nsDocAccessible.h
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsDocAccessible.h,v
retrieving revision 1.76
diff -u -p -8 -r1.76 nsDocAccessible.h
--- accessible/src/base/nsDocAccessible.h 26 Feb 2008 14:19:52 -0000 1.76
+++ accessible/src/base/nsDocAccessible.h 13 Mar 2008 02:36:01 -0000
@@ -96,46 +96,40 @@ class nsDocAccessible : public nsHyperTe
NS_IMETHOD Init();
// nsPIAccessNode
NS_IMETHOD_(nsIFrame *) GetFrame(void);
// nsIAccessibleText
NS_IMETHOD GetAssociatedEditor(nsIEditor **aEditor);
- enum EDupeEventRule { eAllowDupes, eCoalesceFromSameSubtree, eRemoveDupes };
-
/**
* Non-virtual method to fire a delayed event after a 0 length timeout
*
* @param aEvent - the nsIAccessibleEvent event type
* @param aDOMNode - DOM node the accesible event should be fired for
* @param aAllowDupes - eAllowDupes: more than one event of the same type is allowed.
* eCoalesceFromSameSubtree: if two events are in the same subtree,
* only the event on ancestor is used
* eRemoveDupes (default): events of the same type are discarded
* (the last one is used)
*
* @param aIsAsynch - set to PR_TRUE if this is not being called from code
* synchronous with a DOM event
*/
nsresult FireDelayedToolkitEvent(PRUint32 aEvent, nsIDOMNode *aDOMNode,
- EDupeEventRule aAllowDupes = eRemoveDupes,
+ nsAccEvent::EEventRule aAllowDupes = nsAccEvent::eRemoveDupes,
PRBool aIsAsynch = PR_FALSE);
/**
* Fire accessible event in timeout.
*
* @param aEvent - the event to fire
- * @param aAllowDupes - if false then delayed events of the same type and
- * for the same DOM node in the event queue won't
- * be fired.
*/
- nsresult FireDelayedAccessibleEvent(nsIAccessibleEvent *aEvent,
- EDupeEventRule aAllowDupes = eRemoveDupes);
+ nsresult FireDelayedAccessibleEvent(nsIAccessibleEvent *aEvent);
void ShutdownChildDocuments(nsIDocShellTreeItem *aStart);
protected:
virtual void GetBoundsRect(nsRect& aRect, nsIFrame** aRelativeFrame);
virtual nsresult AddEventListeners();
virtual nsresult RemoveEventListeners();
void AddScrollListener();
Index: accessible/src/base/nsRootAccessible.cpp
===================================================================
RCS file: /cvsroot/mozilla/accessible/accessible/src/base/nsRootAccessible.cpp,v
retrieving revision 1.261
diff -u -p -8 -r1.261 nsRootAccessible.cpp
--- accessible/src/base/nsRootAccessible.cpp 6 Mar 2008 03:43:51 -0000 1.261
+++ accessible/src/base/nsRootAccessible.cpp 13 Mar 2008 02:36:02 -0000
@@ -403,18 +403,17 @@ void nsRootAccessible::TryFireEarlyLoadE
return;
}
}
nsCOMPtr<nsIDocShellTreeItem> rootContentTreeItem;
treeItem->GetSameTypeRootTreeItem(getter_AddRefs(rootContentTreeItem));
NS_ASSERTION(rootContentTreeItem, "No root content tree item");
if (rootContentTreeItem == treeItem) {
// No frames or iframes, so we can fire the doc load finished event early
- FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_INTERNAL_LOAD, aDocNode,
- eRemoveDupes);
+ FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_INTERNAL_LOAD, aDocNode);
}
}
PRBool nsRootAccessible::FireAccessibleFocusEvent(nsIAccessible *aAccessible,
nsIDOMNode *aNode,
nsIDOMEvent *aFocusEvent,
PRBool aForceEvent,
PRBool aIsAsynch)
@@ -498,19 +497,20 @@ PRBool nsRootAccessible::FireAccessibleF
nsAccUtils::FireAccEvent(nsIAccessibleEvent::EVENT_MENU_START, menuBarAccessible);
}
}
}
}
}
else if (mCurrentARIAMenubar) {
nsCOMPtr<nsIAccessibleEvent> menuEndEvent =
- new nsAccEvent(nsIAccessibleEvent::EVENT_MENU_END, mCurrentARIAMenubar, PR_FALSE);
+ new nsAccEvent(nsIAccessibleEvent::EVENT_MENU_END, mCurrentARIAMenubar,
+ PR_FALSE, nsAccEvent::eAllowDupes);
if (menuEndEvent) {
- FireDelayedAccessibleEvent(menuEndEvent, eAllowDupes);
+ FireDelayedAccessibleEvent(menuEndEvent);
}
mCurrentARIAMenubar = nsnull;
}
NS_IF_RELEASE(gLastFocusedNode);
gLastFocusedNode = finalFocusNode;
NS_IF_ADDREF(gLastFocusedNode);
@@ -531,17 +531,18 @@ PRBool nsRootAccessible::FireAccessibleF
// and that's what we care about
// Make sure we never fire focus for the nsRootAccessible (mDOMNode)
return PR_FALSE;
}
}
FireDelayedToolkitEvent(nsIAccessibleEvent::EVENT_FOCUS,
- finalFocusNode, eRemoveDupes, aIsAsynch);
+ finalFocusNode, nsAccEvent::eRemoveDupes,
+ aIsAsynch);
return PR_TRUE;
}
void nsRootAccessible::FireCurrentFocusEvent()
{
nsCOMPtr<nsIDOMNode> focusedNode = GetCurrentFocus();
if (!focusedNode) {
Index: .cvsignore
===================================================================
RCS file: /cvs/extras/rpms/xulrunner/devel/.cvsignore,v
retrieving revision 1.40
retrieving revision 1.41
diff -u -r1.40 -r1.41
--- .cvsignore 16 Mar 2008 02:24:20 -0000 1.40
+++ .cvsignore 17 Mar 2008 03:27:56 -0000 1.41
@@ -1 +1 @@
-mozilla-20080315.tar.bz2
+mozilla-20080316.tar.bz2
Index: sources
===================================================================
RCS file: /cvs/extras/rpms/xulrunner/devel/sources,v
retrieving revision 1.41
retrieving revision 1.42
diff -u -r1.41 -r1.42
--- sources 16 Mar 2008 02:24:20 -0000 1.41
+++ sources 17 Mar 2008 03:27:56 -0000 1.42
@@ -1 +1 @@
-d5302f5a63f722a4bfb4cb3566c1d70e mozilla-20080315.tar.bz2
+c9e524654747ccfa7ce396244e08e674 mozilla-20080316.tar.bz2
Index: xulrunner.spec
===================================================================
RCS file: /cvs/extras/rpms/xulrunner/devel/xulrunner.spec,v
retrieving revision 1.96
retrieving revision 1.97
diff -u -r1.96 -r1.97
--- xulrunner.spec 16 Mar 2008 02:24:20 -0000 1.96
+++ xulrunner.spec 17 Mar 2008 03:27:56 -0000 1.97
@@ -7,14 +7,14 @@
%define version_internal 1.9pre
%if ! %{official_branding}
-%define cvsdate 20080315
+%define cvsdate 20080316
%define nightly .cvs%{cvsdate}
%endif
Summary: XUL Runtime for Gecko Applications
Name: xulrunner
Version: 1.9
-Release: 0.42%{?nightly}%{?dist}
+Release: 0.43%{?nightly}%{?dist}
URL: http://www.mozilla.org/projects/xulrunner/
License: MPLv1.1 or GPLv2+ or LGPLv2+
Group: Applications/Internet
@@ -41,6 +41,7 @@
# local bugfixes
Patch41: firefox-2.0.0.4-undo-uriloader.patch
Patch42: firefox-1.1-uriloader.patch
+Patch43: xulrunner-a11y.patch
# font system fixes
@@ -125,6 +126,8 @@
%patch5 -p1
%patch6 -p1 -b .ver
+%patch43 -p0 -b .a11y
+
%patch107 -p1 -b .pk
@@ -407,6 +410,10 @@
#---------------------------------------------------------------------
%changelog
+* Sat Mar 16 2008 Christopher Aillon <caillon at redhat.com> 1.9-0.43
+- Update to latest trunk (2008-03-16)
+- Add patch to negate a11y slowdown on some pages (#431162)
+
* Sat Mar 15 2008 Christopher Aillon <caillon at redhat.com> 1.9-0.42
- Update to latest trunk (2008-03-15)
More information about the fedora-extras-commits
mailing list