Bug 1591523 - Add NativeLayerRoot::SetLayers. r=jrmuizel

This allows us to somewhat cheaply swap out the entire set of layers.
It also means that clearing the array of layers no longer has quadratic complexity;
in the past, you would do this by calling RemoveLayer once per layer, and RemoveLayer
does a linear scan through the array.

Differential Revision: https://phabricator.services.mozilla.com/D50725

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Markus Stange 2019-10-29 20:31:44 +00:00
parent f2c9430255
commit e2f8c029aa
3 changed files with 25 additions and 0 deletions

View File

@ -36,6 +36,7 @@ class NativeLayerRoot {
virtual already_AddRefed<NativeLayer> CreateLayer() = 0; virtual already_AddRefed<NativeLayer> CreateLayer() = 0;
virtual void AppendLayer(NativeLayer* aLayer) = 0; virtual void AppendLayer(NativeLayer* aLayer) = 0;
virtual void RemoveLayer(NativeLayer* aLayer) = 0; virtual void RemoveLayer(NativeLayer* aLayer) = 0;
virtual void SetLayers(const nsTArray<RefPtr<NativeLayer>>& aLayers) = 0;
protected: protected:
virtual ~NativeLayerRoot() {} virtual ~NativeLayerRoot() {}

View File

@ -66,6 +66,7 @@ class NativeLayerRootCA : public NativeLayerRoot {
already_AddRefed<NativeLayer> CreateLayer() override; already_AddRefed<NativeLayer> CreateLayer() override;
void AppendLayer(NativeLayer* aLayer) override; void AppendLayer(NativeLayer* aLayer) override;
void RemoveLayer(NativeLayer* aLayer) override; void RemoveLayer(NativeLayer* aLayer) override;
void SetLayers(const nsTArray<RefPtr<NativeLayer>>& aLayers) override;
protected: protected:
explicit NativeLayerRootCA(CALayer* aLayer); explicit NativeLayerRootCA(CALayer* aLayer);

View File

@ -80,6 +80,29 @@ void NativeLayerRootCA::RemoveLayer(NativeLayer* aLayer) {
mMutated = true; mMutated = true;
} }
void NativeLayerRootCA::SetLayers(const nsTArray<RefPtr<NativeLayer>>& aLayers) {
MutexAutoLock lock(mMutex);
// Ideally, we'd just be able to do mSublayers = std::move(aLayers).
// However, aLayers has a different type: it carries NativeLayer objects, whereas mSublayers
// carries NativeLayerCA objects, so we have to downcast all the elements first. There's one other
// reason to look at all the elements in aLayers first: We need to make sure any new layers know
// about our current backing scale.
nsTArray<RefPtr<NativeLayerCA>> layersCA(aLayers.Length());
for (auto& layer : aLayers) {
RefPtr<NativeLayerCA> layerCA = layer->AsNativeLayerCA();
MOZ_RELEASE_ASSERT(layerCA);
layerCA->SetBackingScale(mBackingScale);
layersCA.AppendElement(std::move(layerCA));
}
if (layersCA != mSublayers) {
mSublayers = std::move(layersCA);
mMutated = true;
}
}
// Must be called within a current CATransaction on the transaction's thread. // Must be called within a current CATransaction on the transaction's thread.
void NativeLayerRootCA::ApplyChanges() { void NativeLayerRootCA::ApplyChanges() {
MutexAutoLock lock(mMutex); MutexAutoLock lock(mMutex);