Bug 1721537 - Split out WindowRenderer base class from LayerManager. r=miko

Depends on D120439

Differential Revision: https://phabricator.services.mozilla.com/D120440
This commit is contained in:
Matt Woodrow 2021-07-22 22:58:57 +00:00
Родитель da45121505
Коммит 912b7f8ef1
46 изменённых файлов: 650 добавлений и 546 удалений

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

@ -736,8 +736,8 @@ void KeyframeEffect::ResetPartialPrerendered() {
return;
}
if (layers::LayerManager* layerManager = widget->GetLayerManager()) {
layerManager->RemovePartialPrerenderedAnimation(
if (WindowRenderer* windowRenderer = widget->GetWindowRenderer()) {
windowRenderer->RemovePartialPrerenderedAnimation(
mAnimation->IdOnCompositor(), mAnimation);
}
}

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

@ -6674,23 +6674,21 @@ nsIWidget* nsContentUtils::WidgetForContent(const nsIContent* aContent) {
return nullptr;
}
already_AddRefed<LayerManager> nsContentUtils::LayerManagerForContent(
WindowRenderer* nsContentUtils::WindowRendererForContent(
const nsIContent* aContent) {
nsIWidget* widget = nsContentUtils::WidgetForContent(aContent);
if (widget) {
RefPtr<LayerManager> manager = widget->GetLayerManager();
return manager.forget();
return widget->GetWindowRenderer();
}
return nullptr;
}
already_AddRefed<LayerManager> nsContentUtils::LayerManagerForDocument(
WindowRenderer* nsContentUtils::WindowRendererForDocument(
const Document* aDoc) {
nsIWidget* widget = nsContentUtils::WidgetForDocument(aDoc);
if (widget) {
RefPtr<LayerManager> manager = widget->GetLayerManager();
return manager.forget();
return widget->GetWindowRenderer();
}
return nullptr;

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

@ -207,9 +207,7 @@ class DataSourceSurface;
enum class SurfaceFormat : int8_t;
} // namespace gfx
namespace layers {
class LayerManager;
} // namespace layers
class WindowRenderer;
} // namespace mozilla
@ -2349,29 +2347,29 @@ class nsContentUtils {
static nsIWidget* WidgetForContent(const nsIContent* aContent);
/**
* Returns a layer manager to use for the given document. Basically we
* Returns a window renderer to use for the given document. Basically we
* look up the document hierarchy for the first document which has
* a presentation with an associated widget, and use that widget's
* layer manager.
* window renderer.
*
* You should probably use LayerManagerForContent() instead of this, unless
* You should probably use WindowRendererForContent() instead of this, unless
* you have a good reason to do otherwise.
*
* @param aDoc the document for which to return a layer manager.
* @param aDoc the document for which to return a window renderer.
* @param aAllowRetaining an outparam that states whether the returned
* layer manager should be used for retained layers
*/
static already_AddRefed<mozilla::layers::LayerManager>
LayerManagerForDocument(const Document* aDoc);
static mozilla::WindowRenderer* WindowRendererForDocument(
const Document* aDoc);
/**
* Returns a layer manager to use for the given content. Unlike
* LayerManagerForDocument(), this returns the correct layer manager for
* Returns a window renderer to use for the given content. Unlike
* WindowRendererForDocument(), this returns the correct window renderer for
* content in popups.
*
* You should probably use this instead of LayerManagerForDocument().
* You should probably use this instead of WindowRendererForDocument().
*/
static already_AddRefed<mozilla::layers::LayerManager> LayerManagerForContent(
static mozilla::WindowRenderer* WindowRendererForContent(
const nsIContent* aContent);
/**

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

@ -294,10 +294,10 @@ LayerTransactionChild* nsDOMWindowUtils::GetLayerTransaction() {
nsIWidget* widget = GetWidget();
if (!widget) return nullptr;
LayerManager* manager = widget->GetLayerManager();
if (!manager) return nullptr;
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return nullptr;
ShadowLayerForwarder* forwarder = manager->AsShadowForwarder();
ShadowLayerForwarder* forwarder = renderer->AsShadowForwarder();
return forwarder && forwarder->HasShadowManager()
? forwarder->GetShadowManager()
: nullptr;
@ -305,9 +305,9 @@ LayerTransactionChild* nsDOMWindowUtils::GetLayerTransaction() {
WebRenderBridgeChild* nsDOMWindowUtils::GetWebRenderBridge() {
if (nsIWidget* widget = GetWidget()) {
if (LayerManager* lm = widget->GetLayerManager()) {
if (WebRenderLayerManager* wrlm = lm->AsWebRenderLayerManager()) {
return wrlm->WrBridge();
if (WindowRenderer* renderer = widget->GetWindowRenderer()) {
if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
return wr->WrBridge();
}
}
}
@ -316,8 +316,8 @@ WebRenderBridgeChild* nsDOMWindowUtils::GetWebRenderBridge() {
CompositorBridgeChild* nsDOMWindowUtils::GetCompositorBridge() {
if (nsIWidget* widget = GetWidget()) {
if (LayerManager* lm = widget->GetLayerManager()) {
if (CompositorBridgeChild* cbc = lm->GetCompositorBridgeChild()) {
if (WindowRenderer* renderer = widget->GetWindowRenderer()) {
if (CompositorBridgeChild* cbc = renderer->GetCompositorBridgeChild()) {
return cbc;
}
}
@ -328,8 +328,8 @@ CompositorBridgeChild* nsDOMWindowUtils::GetCompositorBridge() {
NS_IMETHODIMP
nsDOMWindowUtils::SyncFlushCompositor() {
if (nsIWidget* widget = GetWidget()) {
if (LayerManager* lm = widget->GetLayerManager()) {
if (KnowsCompositor* kc = lm->AsKnowsCompositor()) {
if (WindowRenderer* renderer = widget->GetWindowRenderer()) {
if (KnowsCompositor* kc = renderer->AsKnowsCompositor()) {
kc->SyncWithCompositor();
}
}
@ -412,7 +412,7 @@ nsDOMWindowUtils::UpdateLayerTree() {
presShell->Paint(
view, view->GetBounds(),
PaintFlags::PaintLayers | PaintFlags::PaintSyncDecodeImages);
presShell->GetLayerManager()->WaitOnTransactionProcessed();
presShell->GetWindowRenderer()->WaitOnTransactionProcessed();
}
}
return NS_OK;
@ -533,14 +533,10 @@ nsDOMWindowUtils::SetDisplayPortForElement(float aXPx, float aYPx,
rootFrame == nsLayoutUtils::GetDisplayRootFrame(rootFrame)) {
nsCOMPtr<nsIWidget> widget = GetWidget();
if (widget) {
LayerManager* manager = widget->GetLayerManager();
manager->BeginTransaction();
using PaintFrameFlags = nsLayoutUtils::PaintFrameFlags;
nsLayoutUtils::PaintFrame(nullptr, rootFrame, nsRegion(),
NS_RGB(255, 255, 255),
nsDisplayListBuilderMode::Painting,
PaintFrameFlags::WidgetLayers |
PaintFrameFlags::ExistingTransaction);
nsLayoutUtils::PaintFrame(
nullptr, rootFrame, nsRegion(), NS_RGB(255, 255, 255),
nsDisplayListBuilderMode::Painting, PaintFrameFlags::WidgetLayers);
}
}
}
@ -2545,10 +2541,10 @@ nsDOMWindowUtils::GetLayerManagerType(nsAString& aType) {
nsCOMPtr<nsIWidget> widget = GetWidget();
if (!widget) return NS_ERROR_FAILURE;
LayerManager* mgr = widget->GetLayerManager();
if (!mgr) return NS_ERROR_FAILURE;
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return NS_ERROR_FAILURE;
mgr->GetBackendName(aType);
renderer->GetBackendName(aType);
return NS_OK;
}
@ -2558,10 +2554,10 @@ nsDOMWindowUtils::GetLayerManagerRemote(bool* retval) {
nsCOMPtr<nsIWidget> widget = GetWidget();
if (!widget) return NS_ERROR_FAILURE;
LayerManager* mgr = widget->GetLayerManager();
if (!mgr) return NS_ERROR_FAILURE;
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return NS_ERROR_FAILURE;
*retval = !!mgr->AsKnowsCompositor();
*retval = !!renderer->AsKnowsCompositor();
return NS_OK;
}
@ -2572,13 +2568,13 @@ nsDOMWindowUtils::GetUsingAdvancedLayers(bool* retval) {
return NS_ERROR_FAILURE;
}
LayerManager* mgr = widget->GetLayerManager();
if (!mgr) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_ERROR_FAILURE;
}
*retval = false;
if (KnowsCompositor* fwd = mgr->AsKnowsCompositor()) {
if (KnowsCompositor* fwd = renderer->AsKnowsCompositor()) {
*retval = fwd->GetTextureFactoryIdentifier().mUsingAdvancedLayers;
}
return NS_OK;
@ -2688,8 +2684,8 @@ nsDOMWindowUtils::StartFrameTimeRecording(uint32_t* startIndex) {
nsCOMPtr<nsIWidget> widget = GetWidget();
if (!widget) return NS_ERROR_FAILURE;
LayerManager* mgr = widget->GetLayerManager();
if (!mgr) return NS_ERROR_FAILURE;
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return NS_ERROR_FAILURE;
const uint32_t kRecordingMinSize = 60 * 10; // 10 seconds @60 fps.
const uint32_t kRecordingMaxSize = 60 * 60 * 60; // One hour
@ -2697,7 +2693,7 @@ nsDOMWindowUtils::StartFrameTimeRecording(uint32_t* startIndex) {
Preferences::GetUint("toolkit.framesRecording.bufferSize", uint32_t(0));
bufferSize = std::min(bufferSize, kRecordingMaxSize);
bufferSize = std::max(bufferSize, kRecordingMinSize);
*startIndex = mgr->StartFrameTimeRecording(bufferSize);
*startIndex = renderer->StartFrameTimeRecording(bufferSize);
return NS_OK;
}
@ -2708,10 +2704,10 @@ nsDOMWindowUtils::StopFrameTimeRecording(uint32_t startIndex,
nsCOMPtr<nsIWidget> widget = GetWidget();
if (!widget) return NS_ERROR_FAILURE;
LayerManager* mgr = widget->GetLayerManager();
if (!mgr) return NS_ERROR_FAILURE;
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return NS_ERROR_FAILURE;
mgr->StopFrameTimeRecording(startIndex, frameIntervals);
renderer->StopFrameTimeRecording(startIndex, frameIntervals);
return NS_OK;
}
@ -2814,19 +2810,19 @@ nsDOMWindowUtils::SetAsyncScrollOffset(Element* aElement, float aX, float aY) {
if (!widget) {
return NS_ERROR_FAILURE;
}
LayerManager* manager = widget->GetLayerManager();
if (!manager) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_ERROR_FAILURE;
}
if (WebRenderLayerManager* wrlm = manager->AsWebRenderLayerManager()) {
WebRenderBridgeChild* wrbc = wrlm->WrBridge();
if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
WebRenderBridgeChild* wrbc = wr->WrBridge();
if (!wrbc) {
return NS_ERROR_UNEXPECTED;
}
wrbc->SendSetAsyncScrollOffset(viewId, aX, aY);
return NS_OK;
}
ShadowLayerForwarder* forwarder = manager->AsShadowForwarder();
ShadowLayerForwarder* forwarder = renderer->AsShadowForwarder();
if (!forwarder || !forwarder->HasShadowManager()) {
return NS_ERROR_UNEXPECTED;
}
@ -2847,19 +2843,19 @@ nsDOMWindowUtils::SetAsyncZoom(Element* aRootElement, float aValue) {
if (!widget) {
return NS_ERROR_FAILURE;
}
LayerManager* manager = widget->GetLayerManager();
if (!manager) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_ERROR_FAILURE;
}
if (WebRenderLayerManager* wrlm = manager->AsWebRenderLayerManager()) {
WebRenderBridgeChild* wrbc = wrlm->WrBridge();
if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
WebRenderBridgeChild* wrbc = wr->WrBridge();
if (!wrbc) {
return NS_ERROR_UNEXPECTED;
}
wrbc->SendSetAsyncZoom(viewId, aValue);
return NS_OK;
}
ShadowLayerForwarder* forwarder = manager->AsShadowForwarder();
ShadowLayerForwarder* forwarder = renderer->AsShadowForwarder();
if (!forwarder || !forwarder->HasShadowManager()) {
return NS_ERROR_UNEXPECTED;
}
@ -2879,13 +2875,13 @@ nsDOMWindowUtils::FlushApzRepaints(bool* aOutResult) {
*aOutResult = false;
return NS_OK;
}
LayerManager* manager = widget->GetLayerManager();
if (!manager) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
*aOutResult = false;
return NS_OK;
}
if (WebRenderLayerManager* wrlm = manager->AsWebRenderLayerManager()) {
WebRenderBridgeChild* wrbc = wrlm->WrBridge();
if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
WebRenderBridgeChild* wrbc = wr->WrBridge();
if (!wrbc) {
return NS_ERROR_UNEXPECTED;
}
@ -2893,7 +2889,7 @@ nsDOMWindowUtils::FlushApzRepaints(bool* aOutResult) {
*aOutResult = true;
return NS_OK;
}
ShadowLayerForwarder* forwarder = manager->AsShadowForwarder();
ShadowLayerForwarder* forwarder = renderer->AsShadowForwarder();
if (!forwarder || !forwarder->HasShadowManager()) {
*aOutResult = false;
return NS_OK;
@ -3227,7 +3223,9 @@ nsDOMWindowUtils::LeafLayersPartitionWindow(bool* aResult) {
#ifdef DEBUG
nsIWidget* widget = GetWidget();
if (!widget) return NS_ERROR_FAILURE;
LayerManager* manager = widget->GetLayerManager();
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) return NS_ERROR_FAILURE;
LayerManager* manager = renderer->AsLayerManager();
if (!manager) return NS_ERROR_FAILURE;
nsPresContext* presContext = GetPresContext();
if (!presContext) return NS_ERROR_FAILURE;
@ -4206,16 +4204,16 @@ NS_IMETHODIMP
nsDOMWindowUtils::GetContentAPZTestData(
JSContext* aContext, JS::MutableHandleValue aOutContentTestData) {
if (nsIWidget* widget = GetWidget()) {
RefPtr<LayerManager> lm = widget->GetLayerManager();
if (!lm) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_OK;
}
if (ClientLayerManager* clm = lm->AsClientLayerManager()) {
if (ClientLayerManager* clm = renderer->AsClientLayerManager()) {
if (!clm->GetAPZTestData().ToJS(aOutContentTestData, aContext)) {
return NS_ERROR_FAILURE;
}
} else if (WebRenderLayerManager* wrlm = lm->AsWebRenderLayerManager()) {
if (!wrlm->GetAPZTestData().ToJS(aOutContentTestData, aContext)) {
} else if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
if (!wr->GetAPZTestData().ToJS(aOutContentTestData, aContext)) {
return NS_ERROR_FAILURE;
}
}
@ -4228,18 +4226,18 @@ NS_IMETHODIMP
nsDOMWindowUtils::GetCompositorAPZTestData(
JSContext* aContext, JS::MutableHandleValue aOutCompositorTestData) {
if (nsIWidget* widget = GetWidget()) {
RefPtr<LayerManager> lm = widget->GetLayerManager();
if (!lm) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_OK;
}
APZTestData compositorSideData;
if (ClientLayerManager* clm = lm->AsClientLayerManager()) {
if (ClientLayerManager* clm = renderer->AsClientLayerManager()) {
clm->GetCompositorSideAPZTestData(&compositorSideData);
} else if (WebRenderLayerManager* wrlm = lm->AsWebRenderLayerManager()) {
if (!wrlm->WrBridge()) {
} else if (WebRenderLayerManager* wr = renderer->AsWebRender()) {
if (!wr->WrBridge()) {
return NS_ERROR_UNEXPECTED;
}
if (!wrlm->WrBridge()->SendGetAPZTestData(&compositorSideData)) {
if (!wr->WrBridge()->SendGetAPZTestData(&compositorSideData)) {
return NS_ERROR_FAILURE;
}
}
@ -4290,13 +4288,13 @@ nsDOMWindowUtils::GetFrameUniformityTestData(
return NS_ERROR_NOT_AVAILABLE;
}
RefPtr<LayerManager> manager = widget->GetLayerManager();
if (!manager) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer) {
return NS_ERROR_NOT_AVAILABLE;
}
FrameUniformityData outData;
manager->GetFrameUniformity(&outData);
renderer->GetFrameUniformity(&outData);
outData.ToJS(aOutFrameUniformity, aContext);
return NS_OK;
}

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

@ -1412,13 +1412,13 @@ void CanvasRenderingContext2D::RegisterAllocation() {
}
}
static already_AddRefed<LayerManager> LayerManagerFromCanvasElement(
static WindowRenderer* WindowRendererFromCanvasElement(
nsINode* aCanvasElement) {
if (!aCanvasElement) {
return nullptr;
}
return nsContentUtils::LayerManagerForDocument(aCanvasElement->OwnerDoc());
return nsContentUtils::WindowRendererForDocument(aCanvasElement->OwnerDoc());
}
bool CanvasRenderingContext2D::TrySharedTarget(
@ -1441,15 +1441,14 @@ bool CanvasRenderingContext2D::TrySharedTarget(
return false;
}
RefPtr<LayerManager> layerManager =
LayerManagerFromCanvasElement(mCanvasElement);
WindowRenderer* renderer = WindowRendererFromCanvasElement(mCanvasElement);
if (!layerManager) {
if (!renderer) {
return false;
}
aOutProvider = layerManager->CreatePersistentBufferProvider(
GetSize(), GetSurfaceFormat());
aOutProvider =
renderer->CreatePersistentBufferProvider(GetSize(), GetSurfaceFormat());
if (!aOutProvider) {
return false;

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

@ -1293,9 +1293,9 @@ already_AddRefed<SourceSurface> HTMLCanvasElement::GetSurfaceSnapshot(
layers::LayersBackend HTMLCanvasElement::GetCompositorBackendType() const {
nsIWidget* docWidget = nsContentUtils::WidgetForDocument(OwnerDoc());
if (docWidget) {
layers::LayerManager* layerManager = docWidget->GetLayerManager();
if (layerManager) {
return layerManager->GetCompositorBackendType();
WindowRenderer* renderer = docWidget->GetWindowRenderer();
if (renderer) {
return renderer->GetCompositorBackendType();
}
}

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

@ -2643,7 +2643,8 @@ mozilla::ipc::IPCResult BrowserChild::RecvRenderLayers(
if (mCompositorOptions) {
MOZ_ASSERT(mPuppetWidget);
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
// We send the current layer observer epoch to the compositor so that
@ -2812,7 +2813,7 @@ void BrowserChild::InitRenderingState(
// layers. CreateRemoteLayerManager will destroy us if we manage to get a
// remote layer manager though, so that's fine.
MOZ_ASSERT(!mPuppetWidget->HasLayerManager() ||
mPuppetWidget->GetLayerManager()->GetBackendType() ==
mPuppetWidget->GetWindowRenderer()->GetBackendType() ==
layers::LayersBackend::LAYERS_BASIC);
bool success = false;
if (mLayersConnected == Some(true)) {
@ -2825,7 +2826,8 @@ void BrowserChild::InitRenderingState(
ImageBridgeChild::IdentifyCompositorTextureHost(mTextureFactoryIdentifier);
gfx::VRManagerChild::IdentifyTextureHost(mTextureFactoryIdentifier);
InitAPZState();
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
lm->SetLayersObserverEpoch(mLayersObserverEpoch);
} else {
@ -3121,7 +3123,8 @@ void BrowserChild::DidComposite(mozilla::layers::TransactionId aTransactionId,
const TimeStamp& aCompositeStart,
const TimeStamp& aCompositeEnd) {
MOZ_ASSERT(mPuppetWidget);
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
lm->DidComposite(aTransactionId, aCompositeStart, aCompositeEnd);
@ -3153,7 +3156,8 @@ void BrowserChild::DidRequestComposite(const TimeStamp& aCompositeReqStart,
void BrowserChild::ClearCachedResources() {
MOZ_ASSERT(mPuppetWidget);
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
lm->ClearCachedResources();
@ -3168,7 +3172,8 @@ void BrowserChild::ClearCachedResources() {
void BrowserChild::InvalidateLayers() {
MOZ_ASSERT(mPuppetWidget);
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
FrameLayerBuilder::InvalidateAllLayers(lm);
@ -3225,7 +3230,8 @@ void BrowserChild::ReinitRendering() {
gfx::VRManagerChild::IdentifyTextureHost(mTextureFactoryIdentifier);
InitAPZState();
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
lm->SetLayersObserverEpoch(mLayersObserverEpoch);
@ -3236,7 +3242,8 @@ void BrowserChild::ReinitRendering() {
void BrowserChild::ReinitRenderingForDeviceReset() {
InvalidateLayers();
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
if (WebRenderLayerManager* wlm = lm->AsWebRenderLayerManager()) {
wlm->DoDestroy(/* aIsSync */ true);
} else if (ClientLayerManager* clm = lm->AsClientLayerManager()) {
@ -3276,7 +3283,8 @@ BrowserChild::OnHideTooltip() {
void BrowserChild::NotifyJankedAnimations(
const nsTArray<uint64_t>& aJankedAnimations) {
MOZ_ASSERT(mPuppetWidget);
RefPtr<LayerManager> lm = mPuppetWidget->GetLayerManager();
RefPtr<LayerManager> lm =
mPuppetWidget->GetWindowRenderer()->AsLayerManager();
MOZ_ASSERT(lm);
lm->UpdatePartialPrerenderedAnimations(aJankedAnimations);
}

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

@ -973,10 +973,10 @@ void MediaDecoder::DurationChanged() {
already_AddRefed<KnowsCompositor> MediaDecoder::GetCompositor() {
MediaDecoderOwner* owner = GetOwner();
Document* ownerDoc = owner ? owner->GetDocument() : nullptr;
RefPtr<LayerManager> layerManager =
ownerDoc ? nsContentUtils::LayerManagerForDocument(ownerDoc) : nullptr;
WindowRenderer* renderer =
ownerDoc ? nsContentUtils::WindowRendererForDocument(ownerDoc) : nullptr;
RefPtr<KnowsCompositor> knows =
layerManager ? layerManager->AsKnowsCompositor() : nullptr;
renderer ? renderer->AsKnowsCompositor() : nullptr;
return knows ? knows->GetForMedia().forget() : nullptr;
}

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

@ -572,12 +572,11 @@ already_AddRefed<layers::KnowsCompositor> MediaCapabilities::GetCompositor() {
if (NS_WARN_IF(!doc)) {
return nullptr;
}
RefPtr<layers::LayerManager> layerManager =
nsContentUtils::LayerManagerForDocument(doc);
if (NS_WARN_IF(!layerManager)) {
WindowRenderer* renderer = nsContentUtils::WindowRendererForDocument(doc);
if (NS_WARN_IF(!renderer)) {
return nullptr;
}
RefPtr<layers::KnowsCompositor> knows = layerManager->AsKnowsCompositor();
RefPtr<layers::KnowsCompositor> knows = renderer->AsKnowsCompositor();
if (NS_WARN_IF(!knows)) {
return nullptr;
}

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

@ -204,11 +204,9 @@ void AnimationInfo::EnumerateGenerationOnFrame(
}
}
RefPtr<LayerManager> layerManager =
nsContentUtils::LayerManagerForContent(aContent);
WindowRenderer* renderer = nsContentUtils::WindowRendererForContent(aContent);
if (layerManager &&
layerManager->GetBackendType() == layers::LayersBackend::LAYERS_WR) {
if (renderer && renderer->AsWebRender()) {
// In case of continuation, nsDisplayItem uses its last continuation, so we
// have to use the last continuation frame here.
if (nsLayoutUtils::IsFirstContinuationOrIBSplitSibling(aFrame)) {

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

@ -122,28 +122,6 @@ already_AddRefed<DrawTarget> LayerManager::CreateDrawTarget(
aFormat);
}
already_AddRefed<PersistentBufferProvider>
LayerManager::CreatePersistentBufferProvider(
const mozilla::gfx::IntSize& aSize, mozilla::gfx::SurfaceFormat aFormat) {
RefPtr<PersistentBufferProviderBasic> bufferProvider;
// If we are using remote canvas we don't want to use acceleration in
// non-remote layer managers, so we always use the fallback software one.
if (!gfxPlatform::UseRemoteCanvas() ||
!gfxPlatform::IsBackendAccelerated(
gfxPlatform::GetPlatform()->GetPreferredCanvasBackend())) {
bufferProvider = PersistentBufferProviderBasic::Create(
aSize, aFormat,
gfxPlatform::GetPlatform()->GetPreferredCanvasBackend());
}
if (!bufferProvider) {
bufferProvider = PersistentBufferProviderBasic::Create(
aSize, aFormat, gfxPlatform::GetPlatform()->GetFallbackCanvasBackend());
}
return bufferProvider.forget();
}
already_AddRefed<ImageContainer> LayerManager::CreateImageContainer(
ImageContainer::Mode flag) {
RefPtr<ImageContainer> container = new ImageContainer(flag);
@ -180,44 +158,5 @@ void LayerManager::PayloadPresented(const TimeStamp& aTimeStamp) {
RecordCompositionPayloadsPresented(aTimeStamp, mPayload);
}
void LayerManager::AddPartialPrerenderedAnimation(
uint64_t aCompositorAnimationId, dom::Animation* aAnimation) {
mPartialPrerenderedAnimations.InsertOrUpdate(aCompositorAnimationId,
RefPtr{aAnimation});
aAnimation->SetPartialPrerendered(aCompositorAnimationId);
}
void LayerManager::RemovePartialPrerenderedAnimation(
uint64_t aCompositorAnimationId, dom::Animation* aAnimation) {
MOZ_ASSERT(aAnimation);
#ifdef DEBUG
RefPtr<dom::Animation> animation;
if (mPartialPrerenderedAnimations.Remove(aCompositorAnimationId,
getter_AddRefs(animation)) &&
// It may be possible that either animation's effect has already been
// nulled out via Animation::SetEffect() so ignore such cases.
aAnimation->GetEffect() && aAnimation->GetEffect()->AsKeyframeEffect() &&
animation->GetEffect() && animation->GetEffect()->AsKeyframeEffect()) {
MOZ_ASSERT(EffectSet::GetEffectSetForEffect(
aAnimation->GetEffect()->AsKeyframeEffect()) ==
EffectSet::GetEffectSetForEffect(
animation->GetEffect()->AsKeyframeEffect()));
}
#else
mPartialPrerenderedAnimations.Remove(aCompositorAnimationId);
#endif
aAnimation->ResetPartialPrerendered();
}
void LayerManager::UpdatePartialPrerenderedAnimations(
const nsTArray<uint64_t>& aJankedAnimations) {
for (uint64_t id : aJankedAnimations) {
RefPtr<dom::Animation> animation;
if (mPartialPrerenderedAnimations.Remove(id, getter_AddRefs(animation))) {
animation->UpdatePartialPrerendered();
}
}
}
} // namespace layers
} // namespace mozilla

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

@ -14,6 +14,7 @@
#include <utility> // for forward
#include "FrameMetrics.h" // for ScrollUpdatesMap
#include "ImageContainer.h" // for ImageContainer, ImageContainer::Mode, ImageContainer::SYNCHRONOUS
#include "WindowRenderer.h"
#include "mozilla/AlreadyAddRefed.h" // for already_AddRefed
#include "mozilla/Maybe.h" // for Maybe
#include "mozilla/RefPtr.h" // for RefPtr
@ -94,62 +95,6 @@ class DidCompositeObserver {
virtual void DidComposite() = 0;
};
class FrameRecorder {
public:
/**
* Record (and return) frame-intervals and paint-times for frames which were
* presented between calling StartFrameTimeRecording and
* StopFrameTimeRecording.
*
* - Uses a cyclic buffer and serves concurrent consumers, so if Stop is
* called too late
* (elements were overwritten since Start), result is considered invalid
* and hence empty.)
* - Buffer is capable of holding 10 seconds @ 60fps (or more if frames were
* less frequent).
* Can be changed (up to 1 hour) via pref:
* toolkit.framesRecording.bufferSize.
* - Note: the first frame-interval may be longer than expected because last
* frame
* might have been presented some time before calling
* StartFrameTimeRecording.
*/
/**
* Returns a handle which represents current recording start position.
*/
virtual uint32_t StartFrameTimeRecording(int32_t aBufferSize);
/**
* Clears, then populates aFrameIntervals with the recorded frame timing
* data. The array will be empty if data was overwritten since
* aStartIndex was obtained.
*/
virtual void StopFrameTimeRecording(uint32_t aStartIndex,
nsTArray<float>& aFrameIntervals);
void RecordFrame();
private:
struct FramesTimingRecording {
// Stores state and data for frame intervals and paint times recording.
// see LayerManager::StartFrameTimeRecording() at Layers.cpp for more
// details.
FramesTimingRecording()
: mNextIndex(0),
mLatestStartIndex(0),
mCurrentRunStartIndex(0),
mIsPaused(true) {}
nsTArray<float> mIntervals;
TimeStamp mLastFrameTime;
uint32_t mNextIndex;
uint32_t mLatestStartIndex;
uint32_t mCurrentRunStartIndex;
bool mIsPaused;
};
FramesTimingRecording mRecording;
};
/*
* Motivation: For truly smooth animation and video playback, we need to
* be able to compose frames and render them on a dedicated thread (i.e.
@ -198,7 +143,7 @@ class FrameRecorder {
* Layers are refcounted. The layer manager holds a reference to the
* root layer, and each container layer holds a reference to its children.
*/
class LayerManager : public FrameRecorder {
class LayerManager : public WindowRenderer {
NS_INLINE_DECL_REFCOUNTING(LayerManager)
protected:
@ -218,14 +163,10 @@ class LayerManager : public FrameRecorder {
virtual void Destroy();
bool IsDestroyed() { return mDestroyed; }
virtual ShadowLayerForwarder* AsShadowForwarder() { return nullptr; }
virtual KnowsCompositor* AsKnowsCompositor() { return nullptr; }
virtual LayerManager* AsLayerManager() override { return this; }
virtual LayerManagerComposite* AsLayerManagerComposite() { return nullptr; }
virtual ClientLayerManager* AsClientLayerManager() { return nullptr; }
virtual BasicLayerManager* AsBasicLayerManager() { return nullptr; }
virtual HostLayerManager* AsHostLayerManager() { return nullptr; }
@ -238,13 +179,6 @@ class LayerManager : public FrameRecorder {
virtual bool IsWidgetLayerManager() { return true; }
virtual bool IsInactiveLayerManager() { return false; }
/**
* Start a new transaction. Nested transactions are not allowed so
* there must be no transaction currently in progress.
* This transaction will update the state of the window from which
* this LayerManager was obtained.
*/
virtual bool BeginTransaction(const nsCString& aURL = nsCString()) = 0;
/**
* Start a new transaction. Nested transactions are not allowed so
* there must be no transaction currently in progress.
@ -255,31 +189,11 @@ class LayerManager : public FrameRecorder {
virtual bool BeginTransactionWithTarget(
gfxContext* aTarget, const nsCString& aURL = nsCString()) = 0;
enum EndTransactionFlags {
END_DEFAULT = 0,
END_NO_IMMEDIATE_REDRAW = 1 << 0, // Do not perform the drawing phase
END_NO_COMPOSITE =
1 << 1, // Do not composite after drawing painted layer contents.
END_NO_REMOTE_COMPOSITE = 1 << 2 // Do not schedule a composition with a
// remote Compositor, if one exists.
};
FrameLayerBuilder* GetLayerBuilder() {
return reinterpret_cast<FrameLayerBuilder*>(
GetUserData(&gLayerManagerLayerBuilder));
}
/**
* Attempts to end an "empty transaction". There must have been no
* changes to the layer tree since the BeginTransaction().
* It's possible for this to fail; PaintedLayers may need to be updated
* due to VRAM data being lost, for example. In such cases this method
* returns false, and the caller must proceed with a normal layer tree
* update and EndTransaction.
*/
virtual bool EndEmptyTransaction(
EndTransactionFlags aFlags = END_DEFAULT) = 0;
/**
* Function called to draw the contents of each PaintedLayer.
* aRegionToDraw contains the region that needs to be drawn.
@ -466,20 +380,6 @@ class LayerManager : public FrameRecorder {
static already_AddRefed<ImageContainer> CreateImageContainer(
ImageContainer::Mode flag = ImageContainer::SYNCHRONOUS);
/**
* Type of layer manager his is. This is to be used sparsely in order to
* avoid a lot of Layers backend specific code. It should be used only when
* Layers backend specific functionality is necessary.
*/
virtual LayersBackend GetBackendType() = 0;
/**
* Type of layers backend that will be used to composite this layer tree.
* When compositing is done remotely, then this returns the layers type
* of the compositor.
*/
virtual LayersBackend GetCompositorBackendType() { return GetBackendType(); }
/**
* Creates a DrawTarget which is optimized for inter-operating with this
* layer manager.
@ -503,14 +403,6 @@ class LayerManager : public FrameRecorder {
virtual already_AddRefed<mozilla::gfx::DrawTarget> CreateDrawTarget(
const mozilla::gfx::IntSize& aSize, mozilla::gfx::SurfaceFormat aFormat);
/**
* Creates a PersistentBufferProvider for use with canvas which is optimized
* for inter-operating with this layermanager.
*/
virtual already_AddRefed<PersistentBufferProvider>
CreatePersistentBufferProvider(const mozilla::gfx::IntSize& aSize,
mozilla::gfx::SurfaceFormat aFormat);
virtual bool CanUseCanvasLayerForSize(const gfx::IntSize& aSize) {
return true;
}
@ -521,11 +413,6 @@ class LayerManager : public FrameRecorder {
*/
virtual int32_t GetMaxTextureSize() const = 0;
/**
* Return the name of the layer manager's backend.
*/
virtual void GetBackendName(nsAString& aName) = 0;
/**
* This setter can be used anytime. The user data for all keys is
* initially null. Ownership pases to the layer manager.
@ -583,28 +470,8 @@ class LayerManager : public FrameRecorder {
*/
virtual void SetFocusTarget(const FocusTarget& aFocusTarget) {}
/**
* Make sure that the previous transaction has been entirely
* completed.
*
* Note: This may sychronously wait on a remote compositor
* to complete rendering.
*/
virtual void FlushRendering() {}
/**
* Make sure that the previous transaction has been
* received. This will synchronsly wait on a remote compositor. */
virtual void WaitOnTransactionProcessed() {}
virtual void SendInvalidRegion(const nsIntRegion& aRegion) {}
/**
* Checks if we need to invalidate the OS widget to trigger
* painting when updating this layer manager.
*/
virtual bool NeedsWidgetInvalidation() { return true; }
virtual const char* Name() const { return "???"; }
/**
@ -650,7 +517,6 @@ class LayerManager : public FrameRecorder {
virtual bool IsCompositingCheap() { return true; }
bool IsInTransaction() const { return mInTransaction; }
virtual void GetFrameUniformity(FrameUniformityData* aOutData) {}
virtual void SetRegionToClear(const nsIntRegion& aRegion) {
mRegionToClear = aRegion;
@ -696,8 +562,6 @@ class LayerManager : public FrameRecorder {
virtual TransactionId GetLastTransactionId() { return TransactionId{0}; }
virtual CompositorBridgeChild* GetCompositorBridgeChild() { return nullptr; }
void RegisterPayload(const CompositionPayload& aPayload) {
mPayload.AppendElement(aPayload);
MOZ_ASSERT(mPayload.Length() < 10000);
@ -712,13 +576,6 @@ class LayerManager : public FrameRecorder {
void SetContainsSVG(bool aContainsSVG) { mContainsSVG = aContainsSVG; }
void AddPartialPrerenderedAnimation(uint64_t aCompositorAnimationId,
dom::Animation* aAnimation);
void RemovePartialPrerenderedAnimation(uint64_t aCompositorAnimationId,
dom::Animation* aAnimation);
void UpdatePartialPrerenderedAnimations(
const nsTArray<uint64_t>& aJankedAnimations);
protected:
RefPtr<Layer> mRoot;
gfx::UserData mUserData;
@ -756,12 +613,6 @@ class LayerManager : public FrameRecorder {
// IMPORTANT: Clients should take care to clear this or risk it slowly
// growing out of control.
nsTArray<CompositionPayload> mPayload;
// Transform animations which are not fully pre-rendered because it's on a
// large frame. We need to update the pre-rendered area once after we tried
// to composite area which is outside of the pre-rendered area on the
// compositor.
nsRefPtrHashtable<nsUint64HashKey, dom::Animation>
mPartialPrerenderedAnimations;
public:
/*
@ -771,7 +622,7 @@ class LayerManager : public FrameRecorder {
*/
virtual bool AddPendingScrollUpdateForNextTransaction(
ScrollableLayerGuid::ViewID aScrollId,
const ScrollPositionUpdate& aUpdateInfo);
const ScrollPositionUpdate& aUpdateInfo) override;
Maybe<nsTArray<ScrollPositionUpdate>> GetPendingScrollInfoUpdate(
ScrollableLayerGuid::ViewID aScrollId);
std::unordered_set<ScrollableLayerGuid::ViewID>

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

@ -1217,103 +1217,6 @@ void RefLayer::FillSpecificAttributes(SpecificLayerAttributes& aAttrs) {
mRemoteDocumentSize);
}
/**
* StartFrameTimeRecording, together with StopFrameTimeRecording
* enable recording of frame intervals.
*
* To allow concurrent consumers, a cyclic array is used which serves all
* consumers, practically stateless with regard to consumers.
*
* To save resources, the buffer is allocated on first call to
* StartFrameTimeRecording and recording is paused if no consumer which called
* StartFrameTimeRecording is able to get valid results (because the cyclic
* buffer was overwritten since that call).
*
* To determine availability of the data upon StopFrameTimeRecording:
* - mRecording.mNextIndex increases on each RecordFrame, and never resets.
* - Cyclic buffer position is realized as mNextIndex % bufferSize.
* - StartFrameTimeRecording returns mNextIndex. When StopFrameTimeRecording is
* called, the required start index is passed as an arg, and we're able to
* calculate the required length. If this length is bigger than bufferSize, it
* means data was overwritten. otherwise, we can return the entire sequence.
* - To determine if we need to pause, mLatestStartIndex is updated to
* mNextIndex on each call to StartFrameTimeRecording. If this index gets
* overwritten, it means that all earlier start indices obtained via
* StartFrameTimeRecording were also overwritten, hence, no point in
* recording, so pause.
* - mCurrentRunStartIndex indicates the oldest index of the recording after
* which the recording was not paused. If StopFrameTimeRecording is invoked
* with a start index older than this, it means that some frames were not
* recorded, so data is invalid.
*/
uint32_t FrameRecorder::StartFrameTimeRecording(int32_t aBufferSize) {
if (mRecording.mIsPaused) {
mRecording.mIsPaused = false;
if (!mRecording.mIntervals.Length()) { // Initialize recording buffers
mRecording.mIntervals.SetLength(aBufferSize);
}
// After being paused, recent values got invalid. Update them to now.
mRecording.mLastFrameTime = TimeStamp::Now();
// Any recording which started before this is invalid, since we were paused.
mRecording.mCurrentRunStartIndex = mRecording.mNextIndex;
}
// If we'll overwrite this index, there are no more consumers with aStartIndex
// for which we're able to provide the full recording, so no point in keep
// recording.
mRecording.mLatestStartIndex = mRecording.mNextIndex;
return mRecording.mNextIndex;
}
void FrameRecorder::RecordFrame() {
if (!mRecording.mIsPaused) {
TimeStamp now = TimeStamp::Now();
uint32_t i = mRecording.mNextIndex % mRecording.mIntervals.Length();
mRecording.mIntervals[i] =
static_cast<float>((now - mRecording.mLastFrameTime).ToMilliseconds());
mRecording.mNextIndex++;
mRecording.mLastFrameTime = now;
if (mRecording.mNextIndex >
(mRecording.mLatestStartIndex + mRecording.mIntervals.Length())) {
// We've just overwritten the most recent recording start -> pause.
mRecording.mIsPaused = true;
}
}
}
void FrameRecorder::StopFrameTimeRecording(uint32_t aStartIndex,
nsTArray<float>& aFrameIntervals) {
uint32_t bufferSize = mRecording.mIntervals.Length();
uint32_t length = mRecording.mNextIndex - aStartIndex;
if (mRecording.mIsPaused || length > bufferSize ||
aStartIndex < mRecording.mCurrentRunStartIndex) {
// aStartIndex is too old. Also if aStartIndex was issued before
// mRecordingNextIndex overflowed (uint32_t)
// and stopped after the overflow (would happen once every 828 days of
// constant 60fps).
length = 0;
}
if (!length) {
aFrameIntervals.Clear();
return; // empty recording, return empty arrays.
}
// Set length in advance to avoid possibly repeated reallocations
aFrameIntervals.SetLength(length);
uint32_t cyclicPos = aStartIndex % bufferSize;
for (uint32_t i = 0; i < length; i++, cyclicPos++) {
if (cyclicPos == bufferSize) {
cyclicPos = 0;
}
aFrameIntervals[i] = mRecording.mIntervals[cyclicPos];
}
}
static void PrintInfo(std::stringstream& aStream, HostLayer* aLayerComposite);
#ifdef MOZ_DUMP_PAINTING

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

@ -688,19 +688,19 @@ static void SendLayersDependentApzcTargetConfirmation(
return;
}
LayerManager* lm = ps->GetLayerManager();
if (!lm) {
WindowRenderer* renderer = ps->GetWindowRenderer();
if (!renderer) {
return;
}
if (WebRenderLayerManager* wrlm = lm->AsWebRenderLayerManager()) {
if (WebRenderLayerManager* wrlm = renderer->AsWebRender()) {
if (WebRenderBridgeChild* wrbc = wrlm->WrBridge()) {
wrbc->SendSetConfirmedTargetAPZC(aInputBlockId, aTargets);
}
return;
}
ShadowLayerForwarder* lf = lm->AsShadowForwarder();
ShadowLayerForwarder* lf = renderer->AsShadowForwarder();
if (!lf) {
return;
}

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

@ -24,6 +24,7 @@
#include "mozilla/webrender/WebRenderTypes.h"
#include "mozilla/webrender/WebRenderAPI.h"
#include "nsTArrayForwardDeclare.h"
#include "WindowRenderer.h"
namespace mozilla {
@ -64,7 +65,7 @@ struct CompositorAnimationIdsForEpoch {
class WebRenderBridgeParent final : public PWebRenderBridgeParent,
public CompositorVsyncSchedulerOwner,
public CompositableParentManager,
public layers::FrameRecorder {
public FrameRecorder {
public:
WebRenderBridgeParent(CompositorBridgeParentBase* aCompositorBridge,
const wr::PipelineId& aPipelineId,

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

@ -72,6 +72,7 @@ class WebRenderLayerManager final : public LayerManager {
public:
KnowsCompositor* AsKnowsCompositor() override;
WebRenderLayerManager* AsWebRender() override { return this; }
WebRenderLayerManager* AsWebRenderLayerManager() override { return this; }
CompositorBridgeChild* GetCompositorBridgeChild() override;

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

@ -212,13 +212,13 @@ static nscoord GetMaxDisplayPortSize(nsIContent* aContent,
if (!widget) {
return safeMaximum;
}
LayerManager* lm = widget->GetLayerManager();
if (!lm) {
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer || !renderer->AsLayerManager()) {
return safeMaximum;
}
nsPresContext* presContext = frame->PresContext();
int32_t maxSizeInDevPixels = lm->GetMaxTextureSize();
int32_t maxSizeInDevPixels = renderer->AsLayerManager()->GetMaxTextureSize();
if (maxSizeInDevPixels < 0 || maxSizeInDevPixels == INT_MAX) {
return safeMaximum;
}

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

@ -4565,11 +4565,11 @@ nsresult PresShell::RenderDocument(const nsRect& aRect,
nsView* view = rootFrame->GetView();
if (view && view->GetWidget() &&
nsLayoutUtils::GetDisplayRootFrame(rootFrame) == rootFrame) {
LayerManager* layerManager = view->GetWidget()->GetLayerManager();
WindowRenderer* renderer = view->GetWidget()->GetWindowRenderer();
// ClientLayerManagers or WebRenderLayerManagers in content processes
// don't support taking snapshots.
if (layerManager &&
(!layerManager->AsKnowsCompositor() || XRE_IsParentProcess())) {
if (renderer &&
(!renderer->AsKnowsCompositor() || XRE_IsParentProcess())) {
flags |= PaintFrameFlags::WidgetLayers;
}
}
@ -5351,13 +5351,13 @@ struct PaintParams {
nscolor mBackgroundColor;
};
LayerManager* PresShell::GetLayerManager() {
WindowRenderer* PresShell::GetWindowRenderer() {
NS_ASSERTION(mViewManager, "Should have view manager");
nsView* rootView = mViewManager->GetRootView();
if (rootView) {
if (nsIWidget* widget = rootView->GetWidget()) {
return widget->GetLayerManager();
return widget->GetWindowRenderer();
}
}
return nullptr;
@ -5429,9 +5429,9 @@ void PresShell::SetRenderingState(const RenderingState& aState) {
if (mRenderingStateFlags != aState.mRenderingStateFlags) {
// Rendering state changed in a way that forces us to flush any
// retained layers we might already have.
LayerManager* manager = GetLayerManager();
if (manager) {
FrameLayerBuilder::InvalidateAllLayers(manager);
WindowRenderer* renderer = GetWindowRenderer();
if (renderer && renderer->AsLayerManager()) {
FrameLayerBuilder::InvalidateAllLayers(renderer->AsLayerManager());
}
}
@ -6271,9 +6271,10 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
nsIFrame* frame = aViewToPaint->GetFrame();
LayerManager* layerManager = aViewToPaint->GetWidget()->GetLayerManager();
NS_ASSERTION(layerManager, "Must be in paint event");
bool shouldInvalidate = layerManager->NeedsWidgetInvalidation();
WindowRenderer* renderer = aViewToPaint->GetWidget()->GetWindowRenderer();
NS_ASSERTION(renderer, "Must be in paint event");
LayerManager* layerManager = renderer->AsLayerManager();
bool shouldInvalidate = renderer->NeedsWidgetInvalidation();
nsAutoNotifyDidPaint notifyDidPaint(this, aFlags);
@ -6285,17 +6286,21 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
MOZ_LOG(gLog, LogLevel::Debug,
("PresShell::Paint, first paint, this=%p", this));
layerManager->SetIsFirstPaint();
if (layerManager) {
layerManager->SetIsFirstPaint();
}
mIsFirstPaint = false;
}
if (!layerManager->BeginTransaction(url)) {
if (!renderer->BeginTransaction(url)) {
return;
}
// Send an updated focus target with this transaction. Be sure to do this
// before we paint in the case this is an empty transaction.
layerManager->SetFocusTarget(mAPZFocusTarget);
if (layerManager) {
layerManager->SetFocusTarget(mAPZFocusTarget);
}
if (frame) {
// Try to do an empty transaction, if the frame tree does not
@ -6306,7 +6311,7 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
// that will cause us to forget to update the real layer manager!
if (!(aFlags & PaintFlags::PaintLayers)) {
if (layerManager->EndEmptyTransaction()) {
if (renderer->EndEmptyTransaction()) {
return;
}
NS_WARNING("Must complete empty transaction when compositing!");
@ -6321,22 +6326,23 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
: 0;
bool computeInvalidRect =
computeInvalidFunc ||
(layerManager->GetBackendType() == LayersBackend::LAYERS_BASIC);
(renderer->GetBackendType() == LayersBackend::LAYERS_BASIC);
UniquePtr<LayerProperties> props;
// For WR, the layermanager has no root layer. We want to avoid
// calling ComputeDifferences in that case because it assumes non-null
// and crashes.
if (computeInvalidRect && layerManager->GetRoot()) {
if (computeInvalidRect && layerManager && layerManager->GetRoot()) {
props = LayerProperties::CloneFrom(layerManager->GetRoot());
}
MaybeSetupTransactionIdAllocator(layerManager, presContext);
if (layerManager) {
MaybeSetupTransactionIdAllocator(layerManager, presContext);
}
if (layerManager->EndEmptyTransaction(
(aFlags & PaintFlags::PaintComposite)
? LayerManager::END_DEFAULT
: LayerManager::END_NO_COMPOSITE)) {
if (renderer->EndEmptyTransaction((aFlags & PaintFlags::PaintComposite)
? LayerManager::END_DEFAULT
: LayerManager::END_NO_COMPOSITE)) {
nsIntRegion invalid;
bool areaOverflowed = false;
if (props) {
@ -6344,7 +6350,7 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
computeInvalidFunc)) {
areaOverflowed = true;
}
} else {
} else if (layerManager) {
LayerProperties::ClearInvalidations(layerManager->GetRoot());
}
if (props && !areaOverflowed) {
@ -6391,7 +6397,7 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
flags |= PaintFrameFlags::Compressed;
mNextPaintCompressed = false;
}
if (layerManager->GetBackendType() == layers::LayersBackend::LAYERS_WR) {
if (renderer->GetBackendType() == layers::LayersBackend::LAYERS_WR) {
flags |= PaintFrameFlags::ForWebRender;
}
@ -6402,6 +6408,12 @@ void PresShell::Paint(nsView* aViewToPaint, const nsRegion& aDirtyRegion,
return;
}
if (!layerManager) {
// TODO: Once we support WindowRenderers that aren't a LayerManager,
// then we need to handle this single color case for them.
return;
}
if (layerManager->GetBackendType() == layers::LayersBackend::LAYERS_WR) {
nsPresContext* pc = GetPresContext();
LayoutDeviceRect bounds = LayoutDeviceRect::FromAppUnits(

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

@ -912,10 +912,10 @@ class PresShell final : public nsStubDocumentObserver,
already_AddRefed<nsIContent> GetFocusedContentInOurWindow() const;
/**
* Get the layer manager for the widget of the root view, if it has
* Get the window renderer for the widget of the root view, if it has
* one.
*/
LayerManager* GetLayerManager();
WindowRenderer* GetWindowRenderer();
/**
* Return true iff there is a widget rendering this presShell and that

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

@ -2435,9 +2435,9 @@ void nsRefreshDriver::Tick(VsyncId aId, TimeStamp aNowTime,
// Forward our composition payloads to the layer manager.
if (!mCompositionPayloads.IsEmpty()) {
nsIWidget* widget = mPresContext->GetRootWidget();
layers::LayerManager* lm = widget ? widget->GetLayerManager() : nullptr;
if (lm) {
lm->RegisterPayloads(mCompositionPayloads);
WindowRenderer* renderer = widget ? widget->GetWindowRenderer() : nullptr;
if (renderer && renderer->AsLayerManager()) {
renderer->AsLayerManager()->RegisterPayloads(mCompositionPayloads);
}
mCompositionPayloads.Clear();
}

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

@ -3089,8 +3089,9 @@ void ScrollFrameHelper::ScrollToImpl(nsPoint aPt, const nsRect& aRange,
PAINT_SKIP_LOG("Skipping due to APZ scroll\n");
} else if (mScrollableByAPZ) {
nsIWidget* widget = presContext->GetNearestWidget();
LayerManager* manager = widget ? widget->GetLayerManager() : nullptr;
if (manager) {
WindowRenderer* renderer =
widget ? widget->GetWindowRenderer() : nullptr;
if (renderer) {
mozilla::layers::ScrollableLayerGuid::ViewID id;
bool success = nsLayoutUtils::FindIDFor(content, &id);
MOZ_ASSERT(success); // we have a displayport, we better have an ID
@ -3100,7 +3101,7 @@ void ScrollFrameHelper::ScrollToImpl(nsPoint aPt, const nsRect& aRange,
// might still get squashed into a full transaction if something
// happens to trigger one.
MOZ_ASSERT(!mScrollUpdates.IsEmpty());
success = manager->AddPendingScrollUpdateForNextTransaction(
success = renderer->AddPendingScrollUpdateForNextTransaction(
id, mScrollUpdates.LastElement());
if (success) {
schedulePaint = false;

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

@ -32,12 +32,18 @@ namespace layout {
static already_AddRefed<LayerManager> GetLayerManager(
BrowserParent* aBrowserParent) {
RefPtr<LayerManager> lm;
if (Element* element = aBrowserParent->GetOwnerElement()) {
if (RefPtr<LayerManager> lm =
nsContentUtils::LayerManagerForContent(element)) {
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();
}
return nsContentUtils::LayerManagerForDocument(element->OwnerDoc());
}
return nullptr;
}

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

@ -0,0 +1,170 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* 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 "WindowRenderer.h"
#include "mozilla/dom/Animation.h" // for Animation
#include "mozilla/layers/PersistentBufferProvider.h" // for PersistentBufferProviderBasic, PersistentBufferProvider (ptr only)
namespace mozilla {
/**
* StartFrameTimeRecording, together with StopFrameTimeRecording
* enable recording of frame intervals.
*
* To allow concurrent consumers, a cyclic array is used which serves all
* consumers, practically stateless with regard to consumers.
*
* To save resources, the buffer is allocated on first call to
* StartFrameTimeRecording and recording is paused if no consumer which called
* StartFrameTimeRecording is able to get valid results (because the cyclic
* buffer was overwritten since that call).
*
* To determine availability of the data upon StopFrameTimeRecording:
* - mRecording.mNextIndex increases on each RecordFrame, and never resets.
* - Cyclic buffer position is realized as mNextIndex % bufferSize.
* - StartFrameTimeRecording returns mNextIndex. When StopFrameTimeRecording is
* called, the required start index is passed as an arg, and we're able to
* calculate the required length. If this length is bigger than bufferSize, it
* means data was overwritten. otherwise, we can return the entire sequence.
* - To determine if we need to pause, mLatestStartIndex is updated to
* mNextIndex on each call to StartFrameTimeRecording. If this index gets
* overwritten, it means that all earlier start indices obtained via
* StartFrameTimeRecording were also overwritten, hence, no point in
* recording, so pause.
* - mCurrentRunStartIndex indicates the oldest index of the recording after
* which the recording was not paused. If StopFrameTimeRecording is invoked
* with a start index older than this, it means that some frames were not
* recorded, so data is invalid.
*/
uint32_t FrameRecorder::StartFrameTimeRecording(int32_t aBufferSize) {
if (mRecording.mIsPaused) {
mRecording.mIsPaused = false;
if (!mRecording.mIntervals.Length()) { // Initialize recording buffers
mRecording.mIntervals.SetLength(aBufferSize);
}
// After being paused, recent values got invalid. Update them to now.
mRecording.mLastFrameTime = TimeStamp::Now();
// Any recording which started before this is invalid, since we were paused.
mRecording.mCurrentRunStartIndex = mRecording.mNextIndex;
}
// If we'll overwrite this index, there are no more consumers with aStartIndex
// for which we're able to provide the full recording, so no point in keep
// recording.
mRecording.mLatestStartIndex = mRecording.mNextIndex;
return mRecording.mNextIndex;
}
void FrameRecorder::RecordFrame() {
if (!mRecording.mIsPaused) {
TimeStamp now = TimeStamp::Now();
uint32_t i = mRecording.mNextIndex % mRecording.mIntervals.Length();
mRecording.mIntervals[i] =
static_cast<float>((now - mRecording.mLastFrameTime).ToMilliseconds());
mRecording.mNextIndex++;
mRecording.mLastFrameTime = now;
if (mRecording.mNextIndex >
(mRecording.mLatestStartIndex + mRecording.mIntervals.Length())) {
// We've just overwritten the most recent recording start -> pause.
mRecording.mIsPaused = true;
}
}
}
void FrameRecorder::StopFrameTimeRecording(uint32_t aStartIndex,
nsTArray<float>& aFrameIntervals) {
uint32_t bufferSize = mRecording.mIntervals.Length();
uint32_t length = mRecording.mNextIndex - aStartIndex;
if (mRecording.mIsPaused || length > bufferSize ||
aStartIndex < mRecording.mCurrentRunStartIndex) {
// aStartIndex is too old. Also if aStartIndex was issued before
// mRecordingNextIndex overflowed (uint32_t)
// and stopped after the overflow (would happen once every 828 days of
// constant 60fps).
length = 0;
}
if (!length) {
aFrameIntervals.Clear();
return; // empty recording, return empty arrays.
}
// Set length in advance to avoid possibly repeated reallocations
aFrameIntervals.SetLength(length);
uint32_t cyclicPos = aStartIndex % bufferSize;
for (uint32_t i = 0; i < length; i++, cyclicPos++) {
if (cyclicPos == bufferSize) {
cyclicPos = 0;
}
aFrameIntervals[i] = mRecording.mIntervals[cyclicPos];
}
}
already_AddRefed<PersistentBufferProvider>
WindowRenderer::CreatePersistentBufferProvider(
const mozilla::gfx::IntSize& aSize, mozilla::gfx::SurfaceFormat aFormat) {
RefPtr<PersistentBufferProviderBasic> bufferProvider;
// If we are using remote canvas we don't want to use acceleration in
// non-remote layer managers, so we always use the fallback software one.
if (!gfxPlatform::UseRemoteCanvas() ||
!gfxPlatform::IsBackendAccelerated(
gfxPlatform::GetPlatform()->GetPreferredCanvasBackend())) {
bufferProvider = PersistentBufferProviderBasic::Create(
aSize, aFormat,
gfxPlatform::GetPlatform()->GetPreferredCanvasBackend());
}
if (!bufferProvider) {
bufferProvider = PersistentBufferProviderBasic::Create(
aSize, aFormat, gfxPlatform::GetPlatform()->GetFallbackCanvasBackend());
}
return bufferProvider.forget();
}
void WindowRenderer::AddPartialPrerenderedAnimation(
uint64_t aCompositorAnimationId, dom::Animation* aAnimation) {
mPartialPrerenderedAnimations.InsertOrUpdate(aCompositorAnimationId,
RefPtr{aAnimation});
aAnimation->SetPartialPrerendered(aCompositorAnimationId);
}
void WindowRenderer::RemovePartialPrerenderedAnimation(
uint64_t aCompositorAnimationId, dom::Animation* aAnimation) {
MOZ_ASSERT(aAnimation);
#ifdef DEBUG
RefPtr<dom::Animation> animation;
if (mPartialPrerenderedAnimations.Remove(aCompositorAnimationId,
getter_AddRefs(animation)) &&
// It may be possible that either animation's effect has already been
// nulled out via Animation::SetEffect() so ignore such cases.
aAnimation->GetEffect() && aAnimation->GetEffect()->AsKeyframeEffect() &&
animation->GetEffect() && animation->GetEffect()->AsKeyframeEffect()) {
MOZ_ASSERT(EffectSet::GetEffectSetForEffect(
aAnimation->GetEffect()->AsKeyframeEffect()) ==
EffectSet::GetEffectSetForEffect(
animation->GetEffect()->AsKeyframeEffect()));
}
#else
mPartialPrerenderedAnimations.Remove(aCompositorAnimationId);
#endif
aAnimation->ResetPartialPrerendered();
}
void WindowRenderer::UpdatePartialPrerenderedAnimations(
const nsTArray<uint64_t>& aJankedAnimations) {
for (uint64_t id : aJankedAnimations) {
RefPtr<dom::Animation> animation;
if (mPartialPrerenderedAnimations.Remove(id, getter_AddRefs(animation))) {
animation->UpdatePartialPrerendered();
}
}
}
} // namespace mozilla

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

@ -0,0 +1,210 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* 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/. */
#ifndef MOZILLA_PAINTING_WINDOWRENDERER_H
#define MOZILLA_PAINTING_WINDOWRENDERER_H
#include "mozilla/layers/LayersTypes.h"
#include "mozilla/dom/Animation.h" // for Animation
#include "mozilla/layers/ScrollableLayerGuid.h" // for ScrollableLayerGuid, ScrollableLayerGuid::ViewID
#include "nsRefPtrHashtable.h" // for nsRefPtrHashtable
namespace mozilla {
namespace layers {
class LayerManager;
class WebRenderLayerManager;
class KnowsCompositor;
class ShadowLayerForwarder;
class CompositorBridgeChild;
class ClientLayerManager;
class FrameUniformityData;
class PersistentBufferProvider;
} // namespace layers
class FrameRecorder {
public:
/**
* Record (and return) frame-intervals and paint-times for frames which were
* presented between calling StartFrameTimeRecording and
* StopFrameTimeRecording.
*
* - Uses a cyclic buffer and serves concurrent consumers, so if Stop is
* called too late
* (elements were overwritten since Start), result is considered invalid
* and hence empty.)
* - Buffer is capable of holding 10 seconds @ 60fps (or more if frames were
* less frequent).
* Can be changed (up to 1 hour) via pref:
* toolkit.framesRecording.bufferSize.
* - Note: the first frame-interval may be longer than expected because last
* frame
* might have been presented some time before calling
* StartFrameTimeRecording.
*/
/**
* Returns a handle which represents current recording start position.
*/
virtual uint32_t StartFrameTimeRecording(int32_t aBufferSize);
/**
* Clears, then populates aFrameIntervals with the recorded frame timing
* data. The array will be empty if data was overwritten since
* aStartIndex was obtained.
*/
virtual void StopFrameTimeRecording(uint32_t aStartIndex,
nsTArray<float>& aFrameIntervals);
void RecordFrame();
private:
struct FramesTimingRecording {
// Stores state and data for frame intervals and paint times recording.
// see LayerManager::StartFrameTimeRecording() at Layers.cpp for more
// details.
FramesTimingRecording()
: mNextIndex(0),
mLatestStartIndex(0),
mCurrentRunStartIndex(0),
mIsPaused(true) {}
nsTArray<float> mIntervals;
TimeStamp mLastFrameTime;
uint32_t mNextIndex;
uint32_t mLatestStartIndex;
uint32_t mCurrentRunStartIndex;
bool mIsPaused;
};
FramesTimingRecording mRecording;
};
class WindowRenderer : public FrameRecorder {
public:
// Cast to implementation types.
virtual layers::LayerManager* AsLayerManager() { return nullptr; }
virtual layers::WebRenderLayerManager* AsWebRender() { return nullptr; }
// Required functionality
/**
* Start a new transaction. Nested transactions are not allowed so
* there must be no transaction currently in progress.
* This transaction will update the state of the window from which
* this LayerManager was obtained.
*/
virtual bool BeginTransaction(const nsCString& aURL = nsCString()) = 0;
enum EndTransactionFlags {
END_DEFAULT = 0,
END_NO_IMMEDIATE_REDRAW = 1 << 0, // Do not perform the drawing phase
END_NO_COMPOSITE =
1 << 1, // Do not composite after drawing painted layer contents.
END_NO_REMOTE_COMPOSITE = 1 << 2 // Do not schedule a composition with a
// remote Compositor, if one exists.
};
/**
* Attempts to end an "empty transaction". There must have been no
* changes to the layer tree since the BeginTransaction().
* It's possible for this to fail; PaintedLayers may need to be updated
* due to VRAM data being lost, for example. In such cases this method
* returns false, and the caller must proceed with a normal layer tree
* update and EndTransaction.
*/
virtual bool EndEmptyTransaction(
EndTransactionFlags aFlags = END_DEFAULT) = 0;
/**
* Type of layer manager this is. This is to be used sparsely in order to
* avoid a lot of Layers backend specific code. It should be used only when
* Layers backend specific functionality is necessary.
*/
virtual layers::LayersBackend GetBackendType() = 0;
/**
* Type of layers backend that will be used to composite this layer tree.
* When compositing is done remotely, then this returns the layers type
* of the compositor.
*/
virtual layers::LayersBackend GetCompositorBackendType() {
return GetBackendType();
}
/**
* Checks if we need to invalidate the OS widget to trigger
* painting when updating this renderer.
*/
virtual bool NeedsWidgetInvalidation() { return true; }
/**
* Make sure that the previous transaction has been entirely
* completed.
*
* Note: This may sychronously wait on a remote compositor
* to complete rendering.
*/
virtual void FlushRendering() {}
/**
* Make sure that the previous transaction has been
* received. This will synchronsly wait on a remote compositor.
*/
virtual void WaitOnTransactionProcessed() {}
/**
* Return the name of the layer manager's backend.
*/
virtual void GetBackendName(nsAString& aName) = 0;
virtual void GetFrameUniformity(layers::FrameUniformityData* aOutData) {}
virtual bool AddPendingScrollUpdateForNextTransaction(
layers::ScrollableLayerGuid::ViewID aScrollId,
const ScrollPositionUpdate& aUpdateInfo) {
return false;
}
/**
* Creates a PersistentBufferProvider for use with canvas which is optimized
* for inter-operating with this layermanager.
*/
virtual already_AddRefed<layers::PersistentBufferProvider>
CreatePersistentBufferProvider(const mozilla::gfx::IntSize& aSize,
mozilla::gfx::SurfaceFormat aFormat);
// Helper wrappers around cast to impl and then cast again.
virtual layers::KnowsCompositor* AsKnowsCompositor() { return nullptr; }
virtual layers::ShadowLayerForwarder* AsShadowForwarder() { return nullptr; }
virtual layers::CompositorBridgeChild* GetCompositorBridgeChild() {
return nullptr;
}
virtual layers::ClientLayerManager* AsClientLayerManager() { return nullptr; }
// Provided functionality
void AddPartialPrerenderedAnimation(uint64_t aCompositorAnimationId,
dom::Animation* aAnimation);
void RemovePartialPrerenderedAnimation(uint64_t aCompositorAnimationId,
dom::Animation* aAnimation);
void UpdatePartialPrerenderedAnimations(
const nsTArray<uint64_t>& aJankedAnimations);
protected:
// Transform animations which are not fully pre-rendered because it's on a
// large frame. We need to update the pre-rendered area once after we tried
// to composite area which is outside of the pre-rendered area on the
// compositor.
nsRefPtrHashtable<nsUint64HashKey, dom::Animation>
mPartialPrerenderedAnimations;
};
} // namespace mozilla
#endif /* MOZILLA_PAINTING_WINDOWRENDERER_H */

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

@ -27,6 +27,7 @@ EXPORTS += [
"RetainedDisplayListBuilder.h",
"RetainedDisplayListHelpers.h",
"TransformClipNode.h",
"WindowRenderer.h",
]
EXPORTS.mozilla += [
@ -51,6 +52,7 @@ UNIFIED_SOURCES += [
"nsImageRenderer.cpp",
"PaintTracker.cpp",
"RetainedDisplayListBuilder.cpp",
"WindowRenderer.cpp",
]
include("/ipc/chromium/chromium-config.mozbuild")

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

@ -2294,7 +2294,10 @@ LayerManager* nsDisplayListBuilder::GetWidgetLayerManager(nsView** aView) {
}
nsIWidget* window = RootReferenceFrame()->GetNearestWidget();
if (window) {
return window->GetLayerManager();
WindowRenderer* renderer = window->GetWindowRenderer();
if (renderer) {
return renderer->AsLayerManager();
}
}
return nullptr;
}
@ -6455,8 +6458,8 @@ bool nsDisplayOwnLayer::CreateWebRenderCommands(
return true;
}
bool nsDisplayOwnLayer::UpdateScrollData(
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
bool nsDisplayOwnLayer::UpdateScrollData(WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
bool isRelevantToApz =
(IsScrollThumbLayer() || IsScrollbarContainer() || IsZoomingLayer() ||
(IsFixedPositionLayer() && HasDynamicToolbar()) ||
@ -6757,8 +6760,7 @@ bool nsDisplayFixedPosition::CreateWebRenderCommands(
}
bool nsDisplayFixedPosition::UpdateScrollData(
WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
if (aLayerData) {
if (!mIsFixedBackground) {
aLayerData->SetFixedPositionSides(
@ -7139,8 +7141,7 @@ void nsDisplayStickyPosition::CalculateLayerScrollRanges(
}
bool nsDisplayStickyPosition::UpdateScrollData(
WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
bool hasDynamicToolbar = HasDynamicToolbar();
if (aLayerData && hasDynamicToolbar) {
StickyScrollContainer* stickyScrollContainer = GetStickyScrollContainer();
@ -7226,8 +7227,7 @@ UniquePtr<ScrollMetadata> nsDisplayScrollInfoLayer::ComputeScrollMetadata(
}
bool nsDisplayScrollInfoLayer::UpdateScrollData(
WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
if (aLayerData) {
UniquePtr<ScrollMetadata> metadata = ComputeScrollMetadata(
aData->GetBuilder(), aData->GetManager(), ContainerLayerParameters());
@ -7331,8 +7331,7 @@ bool nsDisplayZoom::ComputeVisibility(nsDisplayListBuilder* aBuilder,
nsDisplayAsyncZoom::nsDisplayAsyncZoom(
nsDisplayListBuilder* aBuilder, nsIFrame* aFrame, nsDisplayList* aList,
const ActiveScrolledRoot* aActiveScrolledRoot,
FrameMetrics::ViewID aViewID)
const ActiveScrolledRoot* aActiveScrolledRoot, FrameMetrics::ViewID aViewID)
: nsDisplayOwnLayer(aBuilder, aFrame, aList, aActiveScrolledRoot),
mViewID(aViewID) {
MOZ_COUNT_CTOR(nsDisplayAsyncZoom);
@ -7377,8 +7376,7 @@ already_AddRefed<Layer> nsDisplayAsyncZoom::BuildLayer(
}
bool nsDisplayAsyncZoom::UpdateScrollData(
WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
bool ret = nsDisplayOwnLayer::UpdateScrollData(aData, aLayerData);
MOZ_ASSERT(ret);
if (aLayerData) {
@ -8143,8 +8141,7 @@ bool nsDisplayTransform::CreateWebRenderCommands(
}
bool nsDisplayTransform::UpdateScrollData(
WebRenderScrollData* aData,
WebRenderLayerScrollData* aLayerData) {
WebRenderScrollData* aData, WebRenderLayerScrollData* aLayerData) {
if (!mFrame->ChildrenHavePerspective()) {
// This case is handled in CreateWebRenderCommands by stashing the transform
// on the stacking context.

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

@ -9,6 +9,7 @@
#include "mozilla/Attributes.h"
#include "FrameLayerBuilder.h"
#include "ImgDrawResult.h"
#include "nsRect.h"
#include "nsColor.h"
#include "gfxRect.h"

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

@ -1177,7 +1177,9 @@ void nsWebBrowser::WindowDeactivated() {
bool nsWebBrowser::PaintWindow(nsIWidget* aWidget,
LayoutDeviceIntRegion aRegion) {
LayerManager* layerManager = aWidget->GetLayerManager();
WindowRenderer* renderer = aWidget->GetWindowRenderer();
NS_ASSERTION(renderer, "Must be in paint event");
LayerManager* layerManager = renderer->AsLayerManager();
NS_ASSERTION(layerManager, "Must be in paint event");
layerManager->BeginTransaction();

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

@ -329,9 +329,9 @@ void nsViewManager::Refresh(nsView* aView,
printf_stderr("--COMPOSITE-- %p\n", presShell.get());
}
#endif
LayerManager* manager = widget->GetLayerManager();
if (!manager->NeedsWidgetInvalidation()) {
manager->FlushRendering();
WindowRenderer* renderer = widget->GetWindowRenderer();
if (!renderer->NeedsWidgetInvalidation()) {
renderer->FlushRendering();
} else {
presShell->Paint(aView, damageRegion, PaintFlags::PaintComposite);
}
@ -619,9 +619,9 @@ void nsViewManager::InvalidateViews(nsView* aView) {
void nsViewManager::WillPaintWindow(nsIWidget* aWidget) {
if (aWidget) {
nsView* view = nsView::GetViewFor(aWidget);
LayerManager* manager = aWidget->GetLayerManager();
WindowRenderer* renderer = aWidget->GetWindowRenderer();
if (view &&
(view->ForcedRepaint() || !manager->NeedsWidgetInvalidation())) {
(view->ForcedRepaint() || !renderer->NeedsWidgetInvalidation())) {
ProcessPendingUpdates();
// Re-get the view pointer here since the ProcessPendingUpdates might have
// destroyed it during CallWillPaintOnObservers.

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

@ -117,7 +117,7 @@ void PuppetWidget::InfallibleCreate(nsIWidget* aParent,
PuppetWidget* parent = static_cast<PuppetWidget*>(aParent);
if (parent) {
parent->SetChild(this);
mLayerManager = parent->GetLayerManager();
mLayerManager = parent->GetWindowRenderer()->AsLayerManager();
} else {
Resize(mBounds.X(), mBounds.Y(), mBounds.Width(), mBounds.Height(), false);
}
@ -585,7 +585,7 @@ bool PuppetWidget::GetEditCommands(NativeKeyBindingsType aType,
return true;
}
LayerManager* PuppetWidget::GetLayerManager() {
WindowRenderer* PuppetWidget::GetWindowRenderer() {
if (!mLayerManager) {
if (XRE_IsParentProcess()) {
// On the parent process there is no CompositorBridgeChild which confuses

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

@ -171,7 +171,7 @@ class PuppetWidget : public nsBaseWidget,
return eTransparencyTransparent;
}
virtual LayerManager* GetLayerManager() override;
virtual WindowRenderer* GetWindowRenderer() override;
// This is used for creating remote layer managers and for re-creating
// them after a compositor reset. The lambda aInitializeFunc is used to

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

@ -2176,7 +2176,7 @@ nsresult nsWindow::MakeFullScreen(bool aFullScreen, nsIScreen*) {
return NS_OK;
}
mozilla::layers::LayerManager* nsWindow::GetLayerManager() {
mozilla::WindowRenderer* nsWindow::GetWindowRenderer() {
if (mLayerManager) {
return mLayerManager;
}
@ -2571,7 +2571,7 @@ bool nsWindow::WidgetPaintsBackground() {
bool nsWindow::NeedsPaint() {
auto lvs(mLayerViewSupport.Access());
if (!lvs || lvs->CompositorPaused() || !GetLayerManager(nullptr)) {
if (!lvs || lvs->CompositorPaused() || !GetWindowRenderer()) {
return false;
}

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

@ -55,7 +55,7 @@ class nsWindow final : public nsBaseWidget {
virtual ~nsWindow();
public:
using nsBaseWidget::GetLayerManager;
using nsBaseWidget::GetWindowRenderer;
nsWindow();
@ -178,7 +178,7 @@ class nsWindow final : public nsBaseWidget {
const InputContextAction& aAction) override;
virtual InputContext GetInputContext() override;
LayerManager* GetLayerManager() override;
WindowRenderer* GetWindowRenderer() override;
virtual bool NeedsPaint() override;

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

@ -1203,7 +1203,7 @@ void nsChildView::Invalidate(const LayoutDeviceIntRect& aRect) {
if (!mView || !mVisible) return;
NS_ASSERTION(GetLayerManager()->GetBackendType() != LayersBackend::LAYERS_CLIENT,
NS_ASSERTION(GetWindowRenderer()->GetBackendType() != LayersBackend::LAYERS_CLIENT,
"Shouldn't need to invalidate with accelerated OMTC layers!");
EnsureContentLayerForMainThreadPainting();
@ -1348,12 +1348,12 @@ bool nsChildView::PaintWindowInDrawTarget(gfx::DrawTarget* aDT,
targetContext->Clip();
nsAutoRetainCocoaObject kungFuDeathGrip(mView);
if (GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_BASIC) {
if (GetWindowRenderer()->GetBackendType() == LayersBackend::LAYERS_BASIC) {
nsBaseWidget::AutoLayerManagerSetup setupLayerManager(this, targetContext,
BufferMode::BUFFER_NONE);
return PaintWindow(aRegion);
}
if (GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_CLIENT) {
if (GetWindowRenderer()->GetBackendType() == LayersBackend::LAYERS_CLIENT) {
// We only need this so that we actually get DidPaintWindow fired
return PaintWindow(aRegion);
}
@ -1399,7 +1399,7 @@ void nsChildView::PaintWindowInContentLayer() {
void nsChildView::HandleMainThreadCATransaction() {
WillPaintWindow();
if (GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_BASIC) {
if (GetWindowRenderer()->GetBackendType() == LayersBackend::LAYERS_BASIC) {
// We're in BasicLayers mode, i.e. main thread software compositing.
// Composite the window into our layer's surface.
PaintWindowInContentLayer();

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

@ -296,7 +296,7 @@ class nsCocoaWindow final : public nsBaseWidget, public nsPIWidgetCocoa {
virtual void Invalidate(const LayoutDeviceIntRect& aRect) override;
virtual nsresult ConfigureChildren(const nsTArray<Configuration>& aConfigurations) override;
virtual LayerManager* GetLayerManager() override;
virtual WindowRenderer* GetWindowRenderer() override;
virtual nsresult DispatchEvent(mozilla::WidgetGUIEvent* aEvent, nsEventStatus& aStatus) override;
virtual void CaptureRollupEvents(nsIRollupListener* aListener, bool aDoCapture) override;
[[nodiscard]] virtual nsresult GetAttention(int32_t aCycleCount) override;

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

@ -1035,9 +1035,9 @@ nsresult nsCocoaWindow::ConfigureChildren(const nsTArray<Configuration>& aConfig
return NS_OK;
}
LayerManager* nsCocoaWindow::GetLayerManager() {
WindowRenderer* nsCocoaWindow::GetWindowRenderer() {
if (mPopupContentView) {
return mPopupContentView->GetLayerManager();
return mPopupContentView->GetWindowRenderer();
}
return nullptr;
}

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

@ -3382,11 +3382,15 @@ gboolean nsWindow::OnExposeEvent(cairo_t* cr) {
LayoutDeviceIntRegion region = exposeRegion;
region.ScaleRoundOut(scale, scale);
if (GetLayerManager()->AsKnowsCompositor() && mCompositorSession) {
WindowRenderer* renderer = GetWindowRenderer();
LayerManager* layerManager = renderer->AsLayerManager();
KnowsCompositor* knowsCompositor = renderer->AsKnowsCompositor();
if (knowsCompositor && layerManager && mCompositorSession) {
// We need to paint to the screen even if nothing changed, since if we
// don't have a compositing window manager, our pixels could be stale.
GetLayerManager()->SetNeedsComposite(true);
GetLayerManager()->SendInvalidRegion(region.ToUnknownRegion());
layerManager->SetNeedsComposite(true);
layerManager->SendInvalidRegion(region.ToUnknownRegion());
}
RefPtr<nsWindow> strongThis(this);
@ -3406,10 +3410,9 @@ gboolean nsWindow::OnExposeEvent(cairo_t* cr) {
if (!listener) return FALSE;
}
if (GetLayerManager()->AsKnowsCompositor() &&
GetLayerManager()->NeedsComposite()) {
GetLayerManager()->ScheduleComposite();
GetLayerManager()->SetNeedsComposite(false);
if (knowsCompositor && layerManager && layerManager->NeedsComposite()) {
layerManager->ScheduleComposite();
layerManager->SetNeedsComposite(false);
}
// Our bounds may have changed after calling WillPaintWindow. Clip
@ -3460,8 +3463,8 @@ gboolean nsWindow::OnExposeEvent(cairo_t* cr) {
}
// If this widget uses OMTC...
if (GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_CLIENT ||
GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_WR) {
if (renderer->GetBackendType() == LayersBackend::LAYERS_CLIENT ||
renderer->GetBackendType() == LayersBackend::LAYERS_WR) {
listener->PaintWindow(this, region);
// Re-get the listener since the will paint notification might have
@ -3526,7 +3529,7 @@ gboolean nsWindow::OnExposeEvent(cairo_t* cr) {
bool painted = false;
{
if (GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_BASIC) {
if (renderer->GetBackendType() == LayersBackend::LAYERS_BASIC) {
if (GetTransparencyMode() == eTransparencyTransparent &&
layerBuffering == BufferMode::BUFFER_NONE && mHasAlphaVisual) {
// If our draw target is unbuffered and we use an alpha channel,
@ -3668,7 +3671,7 @@ gboolean nsWindow::OnConfigureEvent(GtkWidget* aWidget,
// frame, and its contents might be incorrect. See bug 1280653 comment 7
// and comment 10. Specifically we must ensure we recomposite the frame
// as soon as possible to avoid the corrupted frame being displayed.
GetLayerManager()->FlushRendering();
GetWindowRenderer()->FlushRendering();
return FALSE;
}
@ -8276,7 +8279,7 @@ nsresult nsWindow::BeginResizeDrag(WidgetGUIEvent* aEvent, int32_t aHorizontal,
return NS_OK;
}
nsIWidget::LayerManager* nsWindow::GetLayerManager() {
nsIWidget::WindowRenderer* nsWindow::GetWindowRenderer() {
if (mIsDestroyed) {
// Prevent external code from triggering the re-creation of the
// LayerManager/Compositor during shutdown. Just return what we currently
@ -8284,7 +8287,7 @@ nsIWidget::LayerManager* nsWindow::GetLayerManager() {
return mLayerManager;
}
return nsBaseWidget::GetLayerManager();
return nsBaseWidget::GetWindowRenderer();
}
void nsWindow::SetCompositorWidgetDelegate(CompositorWidgetDelegate* delegate) {

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

@ -598,7 +598,7 @@ class nsWindow final : public nsBaseWidget {
void DispatchMissedButtonReleases(GdkEventCrossing* aGdkEvent);
// nsBaseWidget
virtual LayerManager* GetLayerManager() override;
virtual WindowRenderer* GetWindowRenderer() override;
void SetCompositorWidgetDelegate(CompositorWidgetDelegate* delegate) override;

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

@ -250,8 +250,8 @@ LayoutDeviceIntPoint HeadlessWidget::WidgetToScreenOffset() {
return mTopLevel->GetBounds().TopLeft();
}
LayerManager* HeadlessWidget::GetLayerManager() {
return nsBaseWidget::GetLayerManager();
WindowRenderer* HeadlessWidget::GetWindowRenderer() {
return nsBaseWidget::GetWindowRenderer();
}
void HeadlessWidget::SetCompositorWidgetDelegate(

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

@ -100,7 +100,7 @@ class HeadlessWidget : public nsBaseWidget {
}
virtual InputContext GetInputContext() override { return mInputContext; }
virtual LayerManager* GetLayerManager() override;
virtual WindowRenderer* GetWindowRenderer() override;
void SetCompositorWidgetDelegate(CompositorWidgetDelegate* delegate) override;

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

@ -884,7 +884,9 @@ nsBaseWidget::AutoLayerManagerSetup::AutoLayerManagerSetup(
nsBaseWidget* aWidget, gfxContext* aTarget, BufferMode aDoubleBuffering,
ScreenRotation aRotation)
: mWidget(aWidget) {
LayerManager* lm = mWidget->GetLayerManager();
LayerManager* lm = mWidget->GetWindowRenderer()
? mWidget->GetWindowRenderer()->AsLayerManager()
: nullptr;
NS_ASSERTION(
!lm || lm->GetBackendType() == LayersBackend::LAYERS_BASIC,
"AutoLayerManagerSetup instantiated for non-basic layer backend!");
@ -1505,7 +1507,7 @@ bool nsBaseWidget::ShouldUseOffMainThreadCompositing() {
return gfxPlatform::UsesOffMainThreadCompositing();
}
LayerManager* nsBaseWidget::GetLayerManager() {
WindowRenderer* nsBaseWidget::GetWindowRenderer() {
if (!mLayerManager) {
if (!mShutdownObserver) {
// We are shutting down, do not try to re-create a LayerManager

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

@ -218,7 +218,7 @@ class nsBaseWidget : public nsIWidget, public nsSupportsWeakReference {
nsIScreen* aScreen = nullptr) override;
void InfallibleMakeFullScreen(bool aFullScreen, nsIScreen* aScreen = nullptr);
LayerManager* GetLayerManager() override;
WindowRenderer* GetWindowRenderer() override;
// A remote compositor session tied to this window has been lost and IPC
// messages will no longer work. The widget must clean up any lingering

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

@ -74,6 +74,7 @@ namespace dom {
class BrowserChild;
enum class CallerType : uint32_t;
} // namespace dom
class WindowRenderer;
namespace layers {
class AsyncDragMetrics;
class Compositor;
@ -377,6 +378,7 @@ class nsIWidget : public nsISupports {
typedef mozilla::layers::AsyncDragMetrics AsyncDragMetrics;
typedef mozilla::layers::FrameMetrics FrameMetrics;
typedef mozilla::layers::LayerManager LayerManager;
typedef mozilla::WindowRenderer WindowRenderer;
typedef mozilla::layers::LayerManagerComposite LayerManagerComposite;
typedef mozilla::layers::LayersBackend LayersBackend;
typedef mozilla::layers::PLayerTransactionChild PLayerTransactionChild;
@ -1294,7 +1296,7 @@ class nsIWidget : public nsISupports {
* Return the widget's LayerManager. The layer tree for that
* LayerManager is what gets rendered to the widget.
*/
virtual LayerManager* GetLayerManager() = 0;
virtual WindowRenderer* GetWindowRenderer() = 0;
/**
* Called before each layer manager transaction to allow any preparation

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

@ -4074,13 +4074,13 @@ bool nsWindow::HasPendingInputEvent() {
/**************************************************************
*
* SECTION: nsIWidget::GetLayerManager
* SECTION: nsIWidget::GetWindowRenderer
*
* Get the layer manager associated with this widget.
* Get the window renderer associated with this widget.
*
**************************************************************/
LayerManager* nsWindow::GetLayerManager() {
WindowRenderer* nsWindow::GetWindowRenderer() {
if (mLayerManager) {
return mLayerManager;
}
@ -4205,7 +4205,8 @@ nsresult nsWindow::OnDefaultButtonLoaded(
void nsWindow::UpdateThemeGeometries(
const nsTArray<ThemeGeometry>& aThemeGeometries) {
RefPtr<LayerManager> layerManager = GetLayerManager();
RefPtr<LayerManager> layerManager =
GetWindowRenderer() ? GetWindowRenderer()->AsLayerManager() : nullptr;
if (!layerManager) {
return;
}
@ -7329,7 +7330,8 @@ nsresult nsWindow::ConfigureChildren(
w->Move(configuration.mBounds.X(), configuration.mBounds.Y());
if (gfxWindowsPlatform::GetPlatform()->IsDirect2DBackend() ||
GetLayerManager()->GetBackendType() != LayersBackend::LAYERS_BASIC) {
GetWindowRenderer()->GetBackendType() !=
LayersBackend::LAYERS_BASIC) {
// XXX - Workaround for Bug 587508. This will invalidate the part of the
// plugin window that might be touched by moving content somehow. The
// underlying problem should be found and fixed!
@ -7775,8 +7777,8 @@ void nsWindow::SetWindowTranslucencyInner(nsTransparencyMode aMode) {
// Clear window by transparent black when compositor window is used in GPU
// process and non-client area rendering by DWM is enabled.
// It is for showing non-client area rendering. See nsWindow::UpdateGlass().
if (HasGlass() && GetLayerManager()->AsKnowsCompositor() &&
GetLayerManager()->AsKnowsCompositor()->GetUseCompositorWnd()) {
if (HasGlass() && GetWindowRenderer()->AsKnowsCompositor() &&
GetWindowRenderer()->AsKnowsCompositor()->GetUseCompositorWnd()) {
HDC hdc;
RECT rect;
hdc = ::GetWindowDC(mWnd);

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

@ -210,7 +210,7 @@ class nsWindow final : public nsWindowBase {
bool aDoCapture) override;
[[nodiscard]] virtual nsresult GetAttention(int32_t aCycleCount) override;
virtual bool HasPendingInputEvent() override;
virtual LayerManager* GetLayerManager() override;
virtual WindowRenderer* GetWindowRenderer() override;
void SetCompositorWidgetDelegate(CompositorWidgetDelegate* delegate) override;
[[nodiscard]] virtual nsresult OnDefaultButtonLoaded(
const LayoutDeviceIntRect& aButtonRect) override;

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

@ -169,11 +169,14 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t aNestingLevel) {
return true;
}
WindowRenderer* renderer = GetWindowRenderer();
KnowsCompositor* knowsCompositor = renderer->AsKnowsCompositor();
LayerManager* layerManager = renderer->AsLayerManager();
// Clear window by transparent black when compositor window is used in GPU
// process and non-client area rendering by DWM is enabled.
// It is for showing non-client area rendering. See nsWindow::UpdateGlass().
if (HasGlass() && GetLayerManager()->AsKnowsCompositor() &&
GetLayerManager()->AsKnowsCompositor()->GetUseCompositorWnd()) {
if (HasGlass() && knowsCompositor && knowsCompositor->GetUseCompositorWnd()) {
HDC hdc;
RECT rect;
hdc = ::GetWindowDC(mWnd);
@ -184,17 +187,16 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t aNestingLevel) {
ReleaseDC(mWnd, hdc);
}
if (GetLayerManager()->AsKnowsCompositor() &&
if (knowsCompositor && layerManager &&
!mBounds.IsEqualEdges(mLastPaintBounds)) {
// Do an early async composite so that we at least have something on the
// screen in the right place, even if the content is out of date.
GetLayerManager()->ScheduleComposite();
layerManager->ScheduleComposite();
}
mLastPaintBounds = mBounds;
#ifdef MOZ_XUL
if (!aDC &&
(GetLayerManager()->GetBackendType() == LayersBackend::LAYERS_BASIC) &&
if (!aDC && (renderer->GetBackendType() == LayersBackend::LAYERS_BASIC) &&
(eTransparencyTransparent == mTransparencyMode)) {
// For layered translucent windows all drawing should go to memory DC and no
// WM_PAINT messages are normally generated. To support asynchronous
@ -233,11 +235,11 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t aNestingLevel) {
#endif
LayoutDeviceIntRegion region = GetRegionToPaint(forceRepaint, ps, hDC);
if (GetLayerManager()->AsKnowsCompositor()) {
if (knowsCompositor && layerManager) {
// We need to paint to the screen even if nothing changed, since if we
// don't have a compositing window manager, our pixels could be stale.
GetLayerManager()->SetNeedsComposite(true);
GetLayerManager()->SendInvalidRegion(region.ToUnknownRegion());
layerManager->SetNeedsComposite(true);
layerManager->SendInvalidRegion(region.ToUnknownRegion());
}
RefPtr<nsWindow> strongThis(this);
@ -252,10 +254,9 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t aNestingLevel) {
return false;
}
if (GetLayerManager()->AsKnowsCompositor() &&
GetLayerManager()->NeedsComposite()) {
GetLayerManager()->ScheduleComposite();
GetLayerManager()->SetNeedsComposite(false);
if (knowsCompositor && layerManager && layerManager->NeedsComposite()) {
layerManager->ScheduleComposite();
layerManager->SetNeedsComposite(false);
}
bool result = true;
@ -268,7 +269,7 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t aNestingLevel) {
(int32_t)mWnd);
#endif // WIDGET_DEBUG_OUTPUT
switch (GetLayerManager()->GetBackendType()) {
switch (renderer->GetBackendType()) {
case LayersBackend::LAYERS_BASIC: {
RefPtr<gfxASurface> targetSurface;