gecko-dev/layout/ipc/RemoteLayerTreeOwner.cpp

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

141 строка
4.3 KiB
C++
Исходник Обычный вид История

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
2012-05-21 15:12:37 +04:00
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "base/basictypes.h"
#include "mozilla/PresShell.h"
#include "mozilla/dom/ContentParent.h"
#include "mozilla/dom/BrowserParent.h"
#include "mozilla/layers/CompositorBridgeParent.h"
#include "mozilla/layers/CompositorTypes.h"
#include "mozilla/layers/LayerTransactionParent.h"
#include "nsFrameLoader.h"
#include "nsStyleStructInlines.h"
#include "nsSubDocumentFrame.h"
#include "RemoteLayerTreeOwner.h"
#include "mozilla/gfx/GPUProcessManager.h"
#include "mozilla/layers/CompositorBridgeChild.h"
#include "mozilla/layers/WebRenderLayerManager.h"
#include "mozilla/layers/WebRenderScrollData.h"
#include "mozilla/webrender/WebRenderAPI.h"
#include "mozilla/dom/EffectsInfo.h"
using namespace mozilla::dom;
using namespace mozilla::gfx;
using namespace mozilla::layers;
namespace mozilla {
namespace layout {
static already_AddRefed<LayerManager> GetLayerManager(
BrowserParent* aBrowserParent) {
RefPtr<LayerManager> lm;
if (Element* element = aBrowserParent->GetOwnerElement()) {
if (WindowRenderer* renderer =
nsContentUtils::WindowRendererForContent(element)) {
lm = renderer->AsLayerManager();
return lm.forget();
}
if (WindowRenderer* renderer =
nsContentUtils::WindowRendererForDocument(element->OwnerDoc())) {
lm = renderer->AsLayerManager();
return lm.forget();
}
}
Bug 1500257 part 7 - Modify RenderFrame to hold onto TabParent instead of nsFrameLoader. r=aosmond A TabParent for a remote subframe will have the same owner content as the top-level remote browser. This means that 'TabParent::GetFrameLoader()' will return the frame loader of the top-level remote browser. This is fine for getting the layer manager and compositor for connecting layer trees, but the frame loader is also used to acquire a TabParent for its process ID. This is incorrect in the remote subframe case, and will lead to the compositor rejecting layer transactions for the remote subframe because it will only accept them from the top-level remote browser's process. This commit switches RenderFrame to just hold on to TabParent, and acquire the nsFrameLoader as necessary. Another change is to RenderFrame::SetOwnerContent. Previously this method would take the new owner content and check an assertion. I don't see much value in the assertion, so I've removed it. Additionally, now that we acquire the owner content, and therefore the layer manager, from TabParent, we need to ensure that RenderFrame::SetOwnerContent is ran after the TabParent has had it's owner content updated. So the callsite has been moved into TabParent. This resolved a test failure with frame loader swapping. Differential Revision: https://phabricator.services.mozilla.com/D17447 --HG-- extra : source : 4c85fb68f2ed297828bf4646301c2d80d1c8e0a1 extra : intermediate-source : 62ad54fb95eb76f88865f43da1a5d556421e7884 extra : histedit_source : 6b7085118bca83433b26fcec3983a385bd536672
2019-01-23 18:52:30 +03:00
return nullptr;
}
RemoteLayerTreeOwner::RemoteLayerTreeOwner()
: mLayersId{0},
mBrowserParent(nullptr),
mLayerManager(nullptr),
mInitialized(false),
mLayersConnected(false) {}
RemoteLayerTreeOwner::~RemoteLayerTreeOwner() = default;
bool RemoteLayerTreeOwner::Initialize(BrowserParent* aBrowserParent) {
if (mInitialized || !aBrowserParent) {
return false;
}
mBrowserParent = aBrowserParent;
RefPtr<LayerManager> lm = GetLayerManager(mBrowserParent);
PCompositorBridgeChild* compositor =
lm ? lm->GetCompositorBridgeChild() : nullptr;
mTabProcessId = mBrowserParent->Manager()->OtherPid();
// Our remote frame will push layers updates to the compositor,
// and we'll keep an indirect reference to that tree.
GPUProcessManager* gpm = GPUProcessManager::Get();
mLayersConnected = gpm->AllocateAndConnectLayerTreeId(
compositor, mTabProcessId, &mLayersId, &mCompositorOptions);
mInitialized = true;
return true;
}
void RemoteLayerTreeOwner::Destroy() {
if (mLayersId.IsValid()) {
GPUProcessManager::Get()->UnmapLayerTreeId(mLayersId, mTabProcessId);
}
mBrowserParent = nullptr;
mLayerManager = nullptr;
}
void RemoteLayerTreeOwner::EnsureLayersConnected(
CompositorOptions* aCompositorOptions) {
RefPtr<LayerManager> lm = GetLayerManager(mBrowserParent);
if (!lm) {
return;
}
if (!lm->GetCompositorBridgeChild()) {
return;
}
mLayersConnected = lm->GetCompositorBridgeChild()->SendNotifyChildRecreated(
mLayersId, &mCompositorOptions);
*aCompositorOptions = mCompositorOptions;
}
LayerManager* RemoteLayerTreeOwner::AttachLayerManager() {
RefPtr<LayerManager> lm;
if (mBrowserParent) {
lm = GetLayerManager(mBrowserParent);
}
// Perhaps the document containing this frame currently has no presentation?
if (lm && lm->GetCompositorBridgeChild() && lm != mLayerManager) {
mLayersConnected =
lm->GetCompositorBridgeChild()->SendAdoptChild(mLayersId);
FrameLayerBuilder::InvalidateAllLayers(lm);
}
mLayerManager = std::move(lm);
return mLayerManager;
}
void RemoteLayerTreeOwner::OwnerContentChanged() {
Unused << AttachLayerManager();
}
void RemoteLayerTreeOwner::GetTextureFactoryIdentifier(
TextureFactoryIdentifier* aTextureFactoryIdentifier) const {
RefPtr<LayerManager> lm =
mBrowserParent ? GetLayerManager(mBrowserParent) : nullptr;
// Perhaps the document containing this frame currently has no presentation?
if (lm) {
*aTextureFactoryIdentifier = lm->GetTextureFactoryIdentifier();
} else {
*aTextureFactoryIdentifier = TextureFactoryIdentifier();
}
}
} // namespace layout
} // namespace mozilla