1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8 # include "mozilla/a11y/DocAccessible.h"
9 # include "mozilla/a11y/DocManager.h"
10 # include "mozilla/a11y/OuterDocAccessible.h"
12 #include "mozilla/dom/BrowserBridgeChild.h"
13 #include "mozilla/dom/BrowserBridgeHost.h"
14 #include "mozilla/dom/BrowsingContext.h"
15 #include "mozilla/dom/MozFrameLoaderOwnerBinding.h"
16 #include "mozilla/PresShell.h"
17 #include "nsFocusManager.h"
18 #include "nsFrameLoader.h"
19 #include "nsFrameLoaderOwner.h"
20 #include "nsObjectLoadingContent.h"
21 #include "nsQueryObject.h"
22 #include "nsSubDocumentFrame.h"
25 using namespace mozilla::ipc
;
27 mozilla::LazyLogModule
gBrowserChildFocusLog("BrowserChildFocus");
29 #define LOGBROWSERCHILDFOCUS(args) \
30 MOZ_LOG(gBrowserChildFocusLog, mozilla::LogLevel::Debug, args)
32 namespace mozilla::dom
{
34 BrowserBridgeChild::BrowserBridgeChild(BrowsingContext
* aBrowsingContext
,
35 TabId aId
, const LayersId
& aLayersId
)
36 : mId
{aId
}, mLayersId
{aLayersId
}, mBrowsingContext(aBrowsingContext
) {}
38 BrowserBridgeChild::~BrowserBridgeChild() {}
40 already_AddRefed
<BrowserBridgeHost
> BrowserBridgeChild::FinishInit(
41 nsFrameLoader
* aFrameLoader
) {
42 MOZ_DIAGNOSTIC_ASSERT(!mFrameLoader
);
43 mFrameLoader
= aFrameLoader
;
45 RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent();
46 Document
* doc
= owner
->OwnerDoc();
47 doc
->OOPChildLoadStarted(this);
49 #if defined(ACCESSIBILITY)
50 if (a11y::DocAccessible
* docAcc
= a11y::GetExistingDocAccessible(doc
)) {
51 if (a11y::LocalAccessible
* ownerAcc
= docAcc
->GetAccessible(owner
)) {
52 if (a11y::OuterDocAccessible
* outerAcc
= ownerAcc
->AsOuterDoc()) {
53 outerAcc
->SendEmbedderAccessible(this);
57 #endif // defined(ACCESSIBILITY)
59 return MakeAndAddRef
<BrowserBridgeHost
>(this);
62 nsILoadContext
* BrowserBridgeChild::GetLoadContext() {
63 return mBrowsingContext
;
66 void BrowserBridgeChild::NavigateByKey(bool aForward
,
67 bool aForDocumentNavigation
) {
68 Unused
<< SendNavigateByKey(aForward
, aForDocumentNavigation
);
71 void BrowserBridgeChild::Activate(uint64_t aActionId
) {
73 ("BrowserBridgeChild::Activate actionid: %" PRIu64
, aActionId
));
74 Unused
<< SendActivate(aActionId
);
77 void BrowserBridgeChild::Deactivate(bool aWindowLowering
, uint64_t aActionId
) {
78 Unused
<< SendDeactivate(aWindowLowering
, aActionId
);
82 BrowserBridgeChild
* BrowserBridgeChild::GetFrom(nsFrameLoader
* aFrameLoader
) {
86 return aFrameLoader
->GetBrowserBridgeChild();
90 BrowserBridgeChild
* BrowserBridgeChild::GetFrom(nsIContent
* aContent
) {
91 RefPtr
<nsFrameLoaderOwner
> loaderOwner
= do_QueryObject(aContent
);
95 RefPtr
<nsFrameLoader
> frameLoader
= loaderOwner
->GetFrameLoader();
96 return GetFrom(frameLoader
);
99 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvRequestFocus(
100 const bool& aCanRaise
, const CallerType aCallerType
) {
101 // Adapted from BrowserParent
102 RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent();
106 nsContentUtils::RequestFrameFocus(*owner
, aCanRaise
, aCallerType
);
110 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvMoveFocus(
111 const bool& aForward
, const bool& aForDocumentNavigation
) {
112 // Adapted from BrowserParent
113 RefPtr
<nsFocusManager
> fm
= nsFocusManager::GetFocusManager();
118 RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent();
123 RefPtr
<Element
> dummy
;
127 ? (aForDocumentNavigation
128 ? static_cast<uint32_t>(nsIFocusManager::MOVEFOCUS_FORWARDDOC
)
129 : static_cast<uint32_t>(nsIFocusManager::MOVEFOCUS_FORWARD
))
130 : (aForDocumentNavigation
131 ? static_cast<uint32_t>(nsIFocusManager::MOVEFOCUS_BACKWARDDOC
)
132 : static_cast<uint32_t>(nsIFocusManager::MOVEFOCUS_BACKWARD
));
133 fm
->MoveFocus(nullptr, owner
, type
, nsIFocusManager::FLAG_BYKEY
,
134 getter_AddRefs(dummy
));
138 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvMaybeFireEmbedderLoadEvents(
139 EmbedderElementEventType aFireEventAtEmbeddingElement
) {
140 RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent();
145 if (aFireEventAtEmbeddingElement
== EmbedderElementEventType::LoadEvent
) {
146 nsEventStatus status
= nsEventStatus_eIgnore
;
147 WidgetEvent
event(/* aIsTrusted = */ true, eLoad
);
148 event
.mFlags
.mBubbles
= false;
149 event
.mFlags
.mCancelable
= false;
150 EventDispatcher::Dispatch(owner
, nullptr, &event
, nullptr, &status
);
151 } else if (aFireEventAtEmbeddingElement
==
152 EmbedderElementEventType::ErrorEvent
) {
153 mFrameLoader
->FireErrorEvent();
156 UnblockOwnerDocsLoadEvent();
161 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvScrollRectIntoView(
162 const nsRect
& aRect
, const ScrollAxis
& aVertical
,
163 const ScrollAxis
& aHorizontal
, const ScrollFlags
& aScrollFlags
,
164 const int32_t& aAppUnitsPerDevPixel
) {
165 RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent();
170 nsIFrame
* frame
= owner
->GetPrimaryFrame();
175 nsSubDocumentFrame
* subdocumentFrame
= do_QueryFrame(frame
);
176 if (!subdocumentFrame
) {
180 nsPoint extraOffset
= subdocumentFrame
->GetExtraOffset();
182 int32_t parentAPD
= frame
->PresContext()->AppUnitsPerDevPixel();
184 aRect
.ScaleToOtherAppUnitsRoundOut(aAppUnitsPerDevPixel
, parentAPD
);
186 RefPtr
<PresShell
> presShell
= frame
->PresShell();
187 presShell
->ScrollFrameIntoView(frame
, Some(rect
), aVertical
, aHorizontal
,
192 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvSubFrameCrashed() {
193 if (RefPtr
<nsFrameLoaderOwner
> frameLoaderOwner
=
194 do_QueryObject(mFrameLoader
->GetOwnerContent())) {
195 frameLoaderOwner
->SubframeCrashed();
200 void BrowserBridgeChild::ActorDestroy(ActorDestroyReason aWhy
) {
202 mFrameLoader
->DestroyComplete();
205 if (!mBrowsingContext
) {
206 // This BBC was never valid, skip teardown.
210 // Ensure we unblock our document's 'load' event (in case the OOP-iframe has
211 // been removed before it finished loading, or its subprocess crashed):
212 UnblockOwnerDocsLoadEvent();
215 void BrowserBridgeChild::UnblockOwnerDocsLoadEvent() {
216 if (!mHadInitialLoad
) {
217 mHadInitialLoad
= true;
219 if (Document
* doc
= mBrowsingContext
->GetParent()->GetExtantDocument()) {
220 doc
->OOPChildLoadDone(this);
225 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvIntrinsicSizeOrRatioChanged(
226 const Maybe
<IntrinsicSize
>& aIntrinsicSize
,
227 const Maybe
<AspectRatio
>& aIntrinsicRatio
) {
228 if (RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent()) {
229 if (nsCOMPtr
<nsIObjectLoadingContent
> olc
= do_QueryInterface(owner
)) {
230 static_cast<nsObjectLoadingContent
*>(olc
.get())
231 ->SubdocumentIntrinsicSizeOrRatioChanged(aIntrinsicSize
,
238 mozilla::ipc::IPCResult
BrowserBridgeChild::RecvImageLoadComplete(
239 const nsresult
& aResult
) {
240 if (RefPtr
<Element
> owner
= mFrameLoader
->GetOwnerContent()) {
241 if (nsCOMPtr
<nsIObjectLoadingContent
> olc
= do_QueryInterface(owner
)) {
242 static_cast<nsObjectLoadingContent
*>(olc
.get())
243 ->SubdocumentImageLoadComplete(aResult
);
249 } // namespace mozilla::dom