Bug 1456588 part 4. Change nsFocusManager guts to make it clearer that the focused thing is always an Element. r=enndeakin

I couldn't find a good way to make this incremental without adding QIs and
AsElement() in various places....
This commit is contained in:
Boris Zbarsky 2018-04-26 10:37:47 -04:00
Родитель b3b21fd3fa
Коммит 01c62fd5cb
9 изменённых файлов: 46 добавлений и 46 удалений

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

@ -302,7 +302,7 @@ GetCurrentWindow(nsIContent* aContent)
}
// static
nsIContent*
Element*
nsFocusManager::GetFocusedDescendant(nsPIDOMWindowOuter* aWindow,
SearchRange aSearchRange,
nsPIDOMWindowOuter** aFocusedWindow)
@ -311,7 +311,7 @@ nsFocusManager::GetFocusedDescendant(nsPIDOMWindowOuter* aWindow,
*aFocusedWindow = nullptr;
nsIContent* currentContent = nullptr;
Element* currentContent = nullptr;
nsPIDOMWindowOuter* window = aWindow;
for (;;) {
*aFocusedWindow = window;
@ -349,7 +349,7 @@ nsFocusManager::GetFocusedDescendant(nsPIDOMWindowOuter* aWindow,
}
// static
nsIContent*
Element*
nsFocusManager::GetRedirectedFocus(nsIContent* aContent)
{
// For input number, redirect focus to our anonymous text control.
@ -365,7 +365,7 @@ nsFocusManager::GetRedirectedFocus(nsIContent* aContent)
if (numberControlFrame) {
HTMLInputElement* textControl =
numberControlFrame->GetAnonTextControl();
return static_cast<nsIContent*>(textControl);
return textControl;
}
}
}
@ -392,13 +392,13 @@ nsFocusManager::GetRedirectedFocus(nsIContent* aContent)
if (children) {
nsIContent* child = children->Item(0);
if (child && child->IsXULElement(nsGkAtoms::slider))
return child;
return child->AsElement();
}
}
}
if (inputField) {
nsCOMPtr<nsIContent> retval = do_QueryInterface(inputField);
nsCOMPtr<Element> retval = do_QueryInterface(inputField);
return retval;
}
}
@ -527,14 +527,12 @@ nsFocusManager::SetFocus(Element* aElement, uint32_t aFlags)
}
NS_IMETHODIMP
nsFocusManager::ElementIsFocusable(nsIDOMElement* aElement, uint32_t aFlags,
nsFocusManager::ElementIsFocusable(Element* aElement, uint32_t aFlags,
bool* aIsFocusable)
{
NS_ENSURE_TRUE(aElement, NS_ERROR_INVALID_ARG);
nsCOMPtr<nsIContent> aContent = do_QueryInterface(aElement);
*aIsFocusable = CheckIfFocusable(aContent, aFlags) != nullptr;
*aIsFocusable = CheckIfFocusable(aElement, aFlags) != nullptr;
return NS_OK;
}
@ -762,7 +760,7 @@ nsFocusManager::WindowRaised(mozIDOMWindowProxy* aWindow)
// retrieve the last focused element within the window that was raised
nsCOMPtr<nsPIDOMWindowOuter> currentWindow;
nsCOMPtr<nsIContent> currentFocus =
RefPtr<Element> currentFocus =
GetFocusedDescendant(window, eIncludeAllDescendants,
getter_AddRefs(currentWindow));
@ -936,7 +934,7 @@ nsFocusManager::WindowShown(mozIDOMWindowProxy* aWindow, bool aNeedsFocus)
if (aNeedsFocus) {
nsCOMPtr<nsPIDOMWindowOuter> currentWindow;
nsCOMPtr<nsIContent> currentFocus =
RefPtr<Element> currentFocus =
GetFocusedDescendant(window, eIncludeAllDescendants,
getter_AddRefs(currentWindow));
if (currentWindow)
@ -1229,7 +1227,7 @@ nsFocusManager::SetFocusInner(Element* aNewContent, int32_t aFlags,
bool aFocusChanged, bool aAdjustWidget)
{
// if the element is not focusable, just return and leave the focus as is
nsCOMPtr<nsIContent> contentToFocus = CheckIfFocusable(aNewContent, aFlags);
RefPtr<Element> contentToFocus = CheckIfFocusable(aNewContent, aFlags);
if (!contentToFocus)
return;
@ -1580,17 +1578,18 @@ nsFocusManager::IsNonFocusableRoot(nsIContent* aContent)
nsContentUtils::IsUserFocusIgnored(aContent));
}
nsIContent*
nsFocusManager::CheckIfFocusable(nsIContent* aContent, uint32_t aFlags)
Element*
nsFocusManager::CheckIfFocusable(Element* aContent, uint32_t aFlags)
{
if (!aContent)
return nullptr;
// this is a special case for some XUL elements or input number, where an
// anonymous child is actually focusable and not the element itself.
nsCOMPtr<nsIContent> redirectedFocus = GetRedirectedFocus(aContent);
if (redirectedFocus)
RefPtr<Element> redirectedFocus = GetRedirectedFocus(aContent);
if (redirectedFocus) {
return CheckIfFocusable(redirectedFocus, aFlags);
}
nsCOMPtr<nsIDocument> doc = aContent->GetComposedDoc();
// can't focus elements that are not in documents
@ -1610,8 +1609,9 @@ nsFocusManager::CheckIfFocusable(nsIContent* aContent, uint32_t aFlags)
// the root content can always be focused,
// except in userfocusignored context.
if (aContent == doc->GetRootElement())
if (aContent == doc->GetRootElement()) {
return nsContentUtils::IsUserFocusIgnored(aContent) ? nullptr : aContent;
}
// cannot focus content in print preview mode. Only the root can be focused.
nsPresContext* presContext = shell->GetPresContext();
@ -1834,7 +1834,7 @@ nsFocusManager::Blur(nsPIDOMWindowOuter* aWindowToClear,
void
nsFocusManager::Focus(nsPIDOMWindowOuter* aWindow,
nsIContent* aContent,
Element* aContent,
uint32_t aFlags,
bool aIsNewDocument,
bool aFocusChanged,

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

@ -143,9 +143,10 @@ public:
// Return focused content in aWindow or one of visible sub windows.
eIncludeVisibleDescendants,
};
static nsIContent* GetFocusedDescendant(nsPIDOMWindowOuter* aWindow,
SearchRange aSearchRange,
nsPIDOMWindowOuter** aFocusedWindow);
static mozilla::dom::Element*
GetFocusedDescendant(nsPIDOMWindowOuter* aWindow,
SearchRange aSearchRange,
nsPIDOMWindowOuter** aFocusedWindow);
/**
* Returns the content node that focus will be redirected to if aContent was
@ -157,7 +158,7 @@ public:
* XXXndeakin this should be removed eventually but I want to do that as
* followup work.
*/
static nsIContent* GetRedirectedFocus(nsIContent* aContent);
static mozilla::dom::Element* GetRedirectedFocus(nsIContent* aContent);
/**
* Returns an InputContextAction cause for aFlags.
@ -245,7 +246,8 @@ protected:
* frame, so only the IsFocusable method on the content node must be
* true.
*/
nsIContent* CheckIfFocusable(nsIContent* aContent, uint32_t aFlags);
mozilla::dom::Element* CheckIfFocusable(mozilla::dom::Element* aContent,
uint32_t aFlags);
/**
* Blurs the currently focused element. Returns false if another element was
@ -303,7 +305,7 @@ protected:
* If aAdjustWidget is false, don't change the widget focus state.
*/
void Focus(nsPIDOMWindowOuter* aWindow,
nsIContent* aContent,
mozilla::dom::Element* aContent,
uint32_t aFlags,
bool aIsNewDocument,
bool aFocusChanged,

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

@ -4652,7 +4652,7 @@ static bool ShouldShowFocusRingIfFocusedByMouse(nsIContent* aNode)
}
void
nsGlobalWindowInner::SetFocusedNode(nsIContent* aNode,
nsGlobalWindowInner::SetFocusedNode(Element* aNode,
uint32_t aFocusMethod,
bool aNeedsFocus)
{

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

@ -1197,7 +1197,7 @@ public:
bool IsInModalState();
virtual void SetFocusedNode(nsIContent* aNode,
virtual void SetFocusedNode(mozilla::dom::Element* aNode,
uint32_t aFocusMethod = 0,
bool aNeedsFocus = false) override;

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

@ -6624,7 +6624,7 @@ nsGlobalWindowOuter::SetChromeEventHandler(EventTarget* aChromeEventHandler)
}
void
nsGlobalWindowOuter::SetFocusedNode(nsIContent* aNode,
nsGlobalWindowOuter::SetFocusedNode(Element* aNode,
uint32_t aFocusMethod,
bool aNeedsFocus)
{
@ -6676,13 +6676,12 @@ nsGlobalWindowOuter::SetKeyboardIndicators(UIStateChangeType aShowAccelerators,
bool newShouldShowFocusRing = ShouldShowFocusRing();
if (mInnerWindow && nsGlobalWindowInner::Cast(mInnerWindow)->mHasFocus &&
mInnerWindow->mFocusedNode &&
oldShouldShowFocusRing != newShouldShowFocusRing &&
mInnerWindow->mFocusedNode->IsElement()) {
oldShouldShowFocusRing != newShouldShowFocusRing) {
// Update focusedNode's state.
if (newShouldShowFocusRing) {
mInnerWindow->mFocusedNode->AsElement()->AddStates(NS_EVENT_STATE_FOCUSRING);
mInnerWindow->mFocusedNode->AddStates(NS_EVENT_STATE_FOCUSRING);
} else {
mInnerWindow->mFocusedNode->AsElement()->RemoveStates(NS_EVENT_STATE_FOCUSRING);
mInnerWindow->mFocusedNode->RemoveStates(NS_EVENT_STATE_FOCUSRING);
}
}
}
@ -7257,13 +7256,12 @@ nsGlobalWindowOuter::RestoreWindowState(nsISupports *aState)
// if a link is focused, refocus with the FLAG_SHOWRING flag set. This makes
// it easy to tell which link was last clicked when going back a page.
nsIContent* focusedNode = inner->GetFocusedNode();
Element* focusedNode = inner->GetFocusedNode();
if (nsContentUtils::ContentIsLink(focusedNode)) {
nsIFocusManager* fm = nsFocusManager::GetFocusManager();
if (fm) {
// This AsElement() will go away in a few changesets once we
// convert nsPIDOMWindowInner::mFocusedNode to Element.
RefPtr<Element> focusedElement = focusedNode->AsElement();
// XXXbz Do we need the stack strong ref here?
RefPtr<Element> focusedElement = focusedNode;
fm->SetFocus(focusedElement, nsIFocusManager::FLAG_NOSCROLL |
nsIFocusManager::FLAG_SHOWRING);
}

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

@ -979,7 +979,7 @@ public:
nsIntSize DevToCSSIntPixels(nsIntSize px);
nsIntSize CSSToDevIntPixels(nsIntSize px);
virtual void SetFocusedNode(nsIContent* aNode,
virtual void SetFocusedNode(mozilla::dom::Element* aNode,
uint32_t aFocusMethod = 0,
bool aNeedsFocus = false) override;

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

@ -484,8 +484,8 @@ public:
* DO NOT CALL EITHER OF THESE METHODS DIRECTLY. USE THE FOCUS MANAGER
* INSTEAD.
*/
inline nsIContent* GetFocusedNode() const;
virtual void SetFocusedNode(nsIContent* aNode,
inline mozilla::dom::Element* GetFocusedNode() const;
virtual void SetFocusedNode(mozilla::dom::Element* aNode,
uint32_t aFocusMethod = 0,
bool aNeedsFocus = false) = 0;
@ -659,8 +659,8 @@ protected:
nsCOMPtr<nsPIDOMWindowOuter> mOuterWindow;
// the element within the document that is currently focused when this
// window is active
nsCOMPtr<nsIContent> mFocusedNode;
// window is active.
RefPtr<mozilla::dom::Element> mFocusedNode;
// The AudioContexts created for the current document, if any.
nsTArray<mozilla::dom::AudioContext*> mAudioContexts; // Weak
@ -973,8 +973,8 @@ public:
* DO NOT CALL EITHER OF THESE METHODS DIRECTLY. USE THE FOCUS MANAGER
* INSTEAD.
*/
inline nsIContent* GetFocusedNode() const;
virtual void SetFocusedNode(nsIContent* aNode,
inline mozilla::dom::Element* GetFocusedNode() const;
virtual void SetFocusedNode(mozilla::dom::Element* aNode,
uint32_t aFocusMethod = 0,
bool aNeedsFocus = false) = 0;

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

@ -89,13 +89,13 @@ nsPIDOMWindowInner::GetDocShell() const
return mOuterWindow ? mOuterWindow->GetDocShell() : nullptr;
}
nsIContent*
mozilla::dom::Element*
nsPIDOMWindowOuter::GetFocusedNode() const
{
return mInnerWindow ? mInnerWindow->GetFocusedNode() : nullptr;
}
nsIContent*
mozilla::dom::Element*
nsPIDOMWindowInner::GetFocusedNode() const
{
return mFocusedNode;

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

@ -143,7 +143,7 @@ interface nsIFocusManager : nsISupports
/***
* Check if given element is focusable.
*/
boolean elementIsFocusable(in nsIDOMElement aElement, in unsigned long aFlags);
boolean elementIsFocusable(in Element aElement, in unsigned long aFlags);
/*
* Raise the window when switching focus