summaryrefslogtreecommitdiff
path: root/services
diff options
context:
space:
mode:
Diffstat (limited to 'services')
-rw-r--r--services/surfaceflinger/BufferStateLayer.cpp20
-rw-r--r--services/surfaceflinger/BufferStateLayer.h2
-rw-r--r--services/surfaceflinger/Layer.h3
-rw-r--r--services/surfaceflinger/SurfaceFlinger.cpp5
4 files changed, 28 insertions, 2 deletions
diff --git a/services/surfaceflinger/BufferStateLayer.cpp b/services/surfaceflinger/BufferStateLayer.cpp
index 7a5b20d78e..24b35997b9 100644
--- a/services/surfaceflinger/BufferStateLayer.cpp
+++ b/services/surfaceflinger/BufferStateLayer.cpp
@@ -284,6 +284,17 @@ bool BufferStateLayer::setCrop(const Rect& crop) {
return true;
}
+bool BufferStateLayer::setBufferCrop(const Rect& bufferCrop) {
+ if (mCurrentState.bufferCrop == bufferCrop) return false;
+
+ mCurrentState.sequence++;
+ mCurrentState.bufferCrop = bufferCrop;
+
+ mCurrentState.modified = true;
+ setTransactionFlags(eTransactionNeeded);
+ return true;
+}
+
bool BufferStateLayer::setMatrix(const layer_state_t::matrix22_t& matrix,
bool allowNonRectPreservingTransforms) {
if (mCurrentState.transform.dsdx() == matrix.dsdx &&
@@ -809,10 +820,15 @@ uint32_t BufferStateLayer::getEffectiveScalingMode() const {
}
Rect BufferStateLayer::computeBufferCrop(const State& s) {
- if (s.buffer) {
+ if (s.buffer && !s.bufferCrop.isEmpty()) {
+ Rect bufferCrop;
+ s.buffer->getBuffer()->getBounds().intersect(s.bufferCrop, &bufferCrop);
+ return bufferCrop;
+ } else if (s.buffer) {
return s.buffer->getBuffer()->getBounds();
+ } else {
+ return s.bufferCrop;
}
- return Rect::INVALID_RECT;
}
sp<Layer> BufferStateLayer::createClone() {
diff --git a/services/surfaceflinger/BufferStateLayer.h b/services/surfaceflinger/BufferStateLayer.h
index af4fcae7ba..570a41afc3 100644
--- a/services/surfaceflinger/BufferStateLayer.h
+++ b/services/surfaceflinger/BufferStateLayer.h
@@ -88,6 +88,8 @@ public:
FloatRect computeSourceBounds(const FloatRect& parentBounds) const override;
void setAutoRefresh(bool autoRefresh) override;
+ bool setBufferCrop(const Rect& bufferCrop) override;
+
// -----------------------------------------------------------------------
// -----------------------------------------------------------------------
diff --git a/services/surfaceflinger/Layer.h b/services/surfaceflinger/Layer.h
index 688a2c3aff..a83408b7f0 100644
--- a/services/surfaceflinger/Layer.h
+++ b/services/surfaceflinger/Layer.h
@@ -274,6 +274,8 @@ public:
// Stretch effect to apply to this layer
StretchEffect stretchEffect;
+
+ Rect bufferCrop;
};
/*
@@ -885,6 +887,7 @@ public:
bool setStretchEffect(const StretchEffect& effect);
StretchEffect getStretchEffect() const;
+ virtual bool setBufferCrop(const Rect& /* bufferCrop */) { return false; }
virtual std::atomic<int32_t>* getPendingBufferCounter() { return nullptr; }
virtual std::string getPendingBufferCounterName() { return ""; }
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index b04868225e..2dace92eaa 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -4033,6 +4033,11 @@ uint32_t SurfaceFlinger::setClientStateLocked(
flags |= eTraversalNeeded;
}
}
+ if (what & layer_state_t::eBufferCropChanged) {
+ if (layer->setBufferCrop(s.bufferCrop)) {
+ flags |= eTraversalNeeded;
+ }
+ }
// This has to happen after we reparent children because when we reparent to null we remove
// child layers from current state and remove its relative z. If the children are reparented in
// the same transaction, then we have to make sure we reparent the children first so we do not