Bug 291071. Dialog to set Firefox as default browser confused screen reader because of incorrect focus events. r=timeless, sr=neil, a=shaver

This commit is contained in:
aaronleventhal%moonset.net 2005-06-01 14:14:29 +00:00
Родитель 5f35bd596e
Коммит 1d3788c303
5 изменённых файлов: 46 добавлений и 23 удалений

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

@ -189,20 +189,6 @@ NS_IMETHODIMP nsAccessibilityService::OnStateChange(nsIWebProgress *aWebProgress
return NS_OK; // Not interested in frames or iframes, just the root content
}
if (nsAccessNode::gLastFocusedNode) {
nsCOMPtr<nsIDocShellTreeItem> focusedDocShellTreeItem =
nsAccessNode::GetDocShellTreeItemFor(nsAccessNode::gLastFocusedNode);
NS_ENSURE_TRUE(focusedDocShellTreeItem, NS_ERROR_FAILURE);
nsCOMPtr<nsIDocShellTreeItem> focusedRootTreeItem;
focusedDocShellTreeItem->GetSameTypeRootTreeItem(getter_AddRefs(focusedRootTreeItem));
if (focusedRootTreeItem != sameTypeRoot) {
// Load is not occuring in the currently focused tab, so don't fire
// doc load event there, otherwise assistive technology may become confused
return NS_OK;
}
}
// Get the accessible for the new document.
// If it not created yet this will create it & cache it, as well as
// set up event listeners so that MSAA/ATK toolkit and internal

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

@ -121,7 +121,6 @@ class nsDocAccessible : public nsBlockAccessible,
nsCOMPtr<nsITimer> mFireEventTimer;
nsCOMPtr<nsIEditor> mEditor; // Editor, if there is one
PRUint16 mScrollPositionChangedTicks; // Used for tracking scroll events
PRPackedBool mIsNewDocument;
nsCOMArray<nsIAccessibleEvent> mEventsToFire;
};

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

@ -232,9 +232,6 @@ nsresult nsRootAccessible::AddEventListeners()
nsresult rv = target->AddEventListener(NS_LITERAL_STRING("focus"), NS_STATIC_CAST(nsIDOMFocusListener*, this), PR_TRUE);
NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register listener");
// Fire accessible focus event for pre-existing focus
FireCurrentFocusEvent();
// capture Form change events
rv = target->AddEventListener(NS_LITERAL_STRING("select"), NS_STATIC_CAST(nsIDOMFormListener*, this), PR_TRUE);
NS_ASSERTION(NS_SUCCEEDED(rv), "failed to register listener");
@ -293,6 +290,14 @@ nsresult nsRootAccessible::AddEventListeners()
if (!mCaretAccessible)
mCaretAccessible = new nsCaretAccessible(mDOMNode, mWeakShell, this);
// Fire accessible focus event for pre-existing focus, but wait until all internal
// focus events are finished for window initialization.
mFireFocusTimer = do_CreateInstance("@mozilla.org/timer;1");
if (mFireFocusTimer) {
mFireFocusTimer->InitWithFuncCallback(FireFocusCallback, this,
0, nsITimer::TYPE_ONE_SHOT);
}
return nsDocAccessible::AddEventListeners();
}
@ -863,6 +868,13 @@ void nsRootAccessible::GetTargetNode(nsIDOMEvent *aEvent, nsIDOMNode **aTargetNo
}
}
void nsRootAccessible::FireFocusCallback(nsITimer *aTimer, void *aClosure)
{
nsRootAccessible *rootAccessible = NS_STATIC_CAST(nsRootAccessible*, aClosure);
NS_ASSERTION(rootAccessible, "How did we get here without a root accessible?");
rootAccessible->FireCurrentFocusEvent();
}
// ------- nsIDOMFocusListener Methods (1) -------------
NS_IMETHODIMP nsRootAccessible::Focus(nsIDOMEvent* aEvent)
@ -936,6 +948,10 @@ NS_IMETHODIMP nsRootAccessible::Shutdown()
mMenuAccessible = nsnull;
mCaretAccessible = nsnull;
mAccService = nsnull;
if (mFireEventTimer) {
mFireFocusTimer->Cancel();
mFireFocusTimer = nsnull;
}
return nsDocAccessibleWrap::Shutdown();
}

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

@ -47,6 +47,7 @@
#include "nsIDOMFormListener.h"
#include "nsIDOMXULListener.h"
#include "nsIAccessibleCaret.h"
#include "nsITimer.h"
class nsIAccessibleEventListener;
@ -100,6 +101,10 @@ class nsRootAccessible : public nsDocAccessibleWrap,
void ShutdownAll();
private:
nsCOMPtr<nsITimer> mFireFocusTimer;
static void FireFocusCallback(nsITimer *aTimer, void *aClosure);
protected:
nsresult AddEventListeners();
nsresult RemoveEventListeners();

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

@ -345,14 +345,31 @@ void nsDocAccessibleWrap::DocLoadCallback(nsITimer *aTimer, void *aClosure)
// Doc has finished loading, fire "load finished" event
// By using short timer we can wait for MS Windows to make the window visible,
// which it does asynchronously. This avoids confusing the screen reader with a
// hidden window.
// hidden window. Waiting also allows us to see of the document has focus,
// which is important because we only fire doc loaded events for focused documents.
nsDocAccessibleWrap *docAcc =
NS_REINTERPRET_CAST(nsDocAccessibleWrap*, aClosure);
if (docAcc) {
docAcc->FireToolkitEvent(nsIAccessibleEvent::EVENT_STATE_CHANGE,
docAcc, nsnull);
docAcc->FireAnchorJumpEvent();
if (!docAcc) {
return;
}
// Fire doc finished event
nsCOMPtr<nsIDOMNode> docDomNode;
docAcc->GetDOMNode(getter_AddRefs(docDomNode));
nsCOMPtr<nsIDocument> doc(do_QueryInterface(docDomNode));
if (doc) {
nsCOMPtr<nsISupports> container = doc->GetContainer();
nsCOMPtr<nsIDocShell> docShell = do_QueryInterface(container);
if (docShell) {
PRBool hasFocus;
docShell->GetHasFocus(&hasFocus);
if (hasFocus) {
docAcc->FireToolkitEvent(nsIAccessibleEvent::EVENT_STATE_CHANGE,
docAcc, nsnull);
docAcc->FireAnchorJumpEvent();
}
}
}
}