diff --git a/docshell/shistory/SessionHistoryEntry.cpp b/docshell/shistory/SessionHistoryEntry.cpp index ed4eb23a020b..bc10824e5bbd 100644 --- a/docshell/shistory/SessionHistoryEntry.cpp +++ b/docshell/shistory/SessionHistoryEntry.cpp @@ -1376,8 +1376,12 @@ void SessionHistoryEntry::SetFrameLoader(nsFrameLoader* aFrameLoader) { MOZ_RELEASE_ASSERT(!aFrameLoader || mozilla::BFCacheInParent()); SharedInfo()->SetFrameLoader(aFrameLoader); if (aFrameLoader) { - if (BrowserParent* bp = aFrameLoader->GetBrowserParent()) { - bp->Deactivated(); + if (BrowsingContext* bc = aFrameLoader->GetMaybePendingBrowsingContext()) { + bc->PreOrderWalk([&](BrowsingContext* aContext) { + if (BrowserParent* bp = aContext->Canonical()->GetBrowserParent()) { + bp->Deactivated(); + } + }); } // When a new frameloader is stored, try to evict some older diff --git a/dom/ipc/BrowserParent.cpp b/dom/ipc/BrowserParent.cpp index f3964f2ce1d7..1c4dfe2b4de1 100644 --- a/dom/ipc/BrowserParent.cpp +++ b/dom/ipc/BrowserParent.cpp @@ -235,7 +235,8 @@ BrowserParent::BrowserParent(ContentParent* aManager, const TabId& aTabId, mHasPresented(false), mIsReadyToHandleInputEvents(false), mIsMouseEnterIntoWidgetEventSuppressed(false), - mLockedNativePointer(false) { + mLockedNativePointer(false), + mShowingTooltip(false) { MOZ_ASSERT(aManager); // When the input event queue is disabled, we don't need to handle the case // that some input events are dispatched before PBrowserConstructor. @@ -597,6 +598,10 @@ void BrowserParent::RemoveWindowListeners() { } void BrowserParent::Deactivated() { + if (mShowingTooltip) { + // Reuse the normal tooltip hiding method. + mozilla::Unused << RecvHideTooltip(); + } UnlockNativePointer(); UnsetTopLevelWebFocus(this); UnsetLastMouseRemoteTarget(this); @@ -2296,11 +2301,16 @@ mozilla::ipc::IPCResult BrowserParent::RecvShowTooltip( nsCOMPtr el = do_QueryInterface(flo); if (!el) return IPC_OK(); - xulBrowserWindow->ShowTooltip(aX, aY, aTooltip, aDirection, el); + if (NS_SUCCEEDED( + xulBrowserWindow->ShowTooltip(aX, aY, aTooltip, aDirection, el))) { + mShowingTooltip = true; + } return IPC_OK(); } mozilla::ipc::IPCResult BrowserParent::RecvHideTooltip() { + mShowingTooltip = false; + nsCOMPtr xulBrowserWindow = GetXULBrowserWindow(); if (!xulBrowserWindow) { return IPC_OK(); diff --git a/dom/ipc/BrowserParent.h b/dom/ipc/BrowserParent.h index 15e9bded7fa5..e502d710ff3f 100644 --- a/dom/ipc/BrowserParent.h +++ b/dom/ipc/BrowserParent.h @@ -973,6 +973,9 @@ class BrowserParent final : public PBrowserParent, // True after RecvLockNativePointer has been called and until // UnlockNativePointer has been called. bool mLockedNativePointer : 1; + + // True between ShowTooltip and HideTooltip messages. + bool mShowingTooltip : 1; }; struct MOZ_STACK_CLASS BrowserParent::AutoUseNewTab final { diff --git a/dom/ipc/tests/browser.ini b/dom/ipc/tests/browser.ini index 3dc10c4cdd38..b8df267075b8 100644 --- a/dom/ipc/tests/browser.ini +++ b/dom/ipc/tests/browser.ini @@ -23,6 +23,7 @@ skip-if = verify apple_silicon # crash [browser_domainPolicy.js] +[browser_hide_tooltip.js] [browser_memory_distribution_telemetry.js] skip-if = true !e10s # This is an e10s only probe, but the test is currently broken. See Bug 1449991 diff --git a/dom/ipc/tests/browser_hide_tooltip.js b/dom/ipc/tests/browser_hide_tooltip.js new file mode 100644 index 000000000000..c4ea349885db --- /dev/null +++ b/dom/ipc/tests/browser_hide_tooltip.js @@ -0,0 +1,38 @@ +/* Any copyright is dedicated to the Public Domain. + http://creativecommons.org/publicdomain/zero/1.0/ */ + +"use strict"; + +add_task(async function test_hiding_tooltip() { + let page1 = "data:text/html,page 1"; + let page2 = "data:text/html,page 2"; + + let tab = await BrowserTestUtils.openNewForegroundTab({ + gBrowser, + opening: page1, + }); + + let popup = new Promise(function(resolve) { + window.addEventListener("popupshown", resolve, { once: true }); + }); + // Fire a mousemove to trigger the tooltip. + EventUtils.synthesizeMouseAtCenter(gBrowser.selectedBrowser, { + type: "mousemove", + }); + await popup; + + let hiding = new Promise(function(resolve) { + window.addEventListener("popuphiding", resolve, { once: true }); + }); + let loaded = BrowserTestUtils.browserLoaded( + gBrowser.selectedBrowser, + false, + page2 + ); + BrowserTestUtils.loadURI(gBrowser, page2); + await loaded; + await hiding; + + ok(true, "Should have hidden the tooltip"); + BrowserTestUtils.removeTab(tab); +});