diff options
-rw-r--r-- | libs/ui/Rect.cpp | 8 | ||||
-rw-r--r-- | libs/ui/include/ui/Rect.h | 7 | ||||
-rw-r--r-- | services/surfaceflinger/Layer.cpp | 27 |
3 files changed, 34 insertions, 8 deletions
diff --git a/libs/ui/Rect.cpp b/libs/ui/Rect.cpp index d8702e5755..045db31087 100644 --- a/libs/ui/Rect.cpp +++ b/libs/ui/Rect.cpp @@ -72,6 +72,14 @@ Rect& Rect::offsetBy(int32_t x, int32_t y) { return *this; } +Rect& Rect::inset(int32_t left, int32_t top, int32_t right, int32_t bottom) { + this->left += left; + this->top += top; + this->right -= right; + this->bottom -= bottom; + return *this; +} + const Rect Rect::operator +(const Point& rhs) const { const Rect result(left + rhs.x, top + rhs.y, right + rhs.x, bottom + rhs.y); return result; diff --git a/libs/ui/include/ui/Rect.h b/libs/ui/include/ui/Rect.h index 0bec0b7f78..9edb510ee9 100644 --- a/libs/ui/include/ui/Rect.h +++ b/libs/ui/include/ui/Rect.h @@ -120,7 +120,7 @@ public: right = rb.x; bottom = rb.y; } - + // the following 4 functions return the 4 corners of the rect as Point Point leftTop() const { return Point(left, top); @@ -175,6 +175,11 @@ public: Rect& offsetTo(int32_t x, int32_t y); Rect& offsetBy(int32_t x, int32_t y); + /** + * Insets the rectangle on all sides specified by the insets. + */ + Rect& inset(int32_t left, int32_t top, int32_t right, int32_t bottom); + bool intersect(const Rect& with, Rect* result) const; // Create a new Rect by transforming this one using a graphics HAL diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp index 15e416ac2a..f53ffae570 100644 --- a/services/surfaceflinger/Layer.cpp +++ b/services/surfaceflinger/Layer.cpp @@ -2121,10 +2121,6 @@ bool Layer::isRemovedFromCurrentState() const { InputWindowInfo Layer::fillInputInfo(const Rect& screenBounds) { InputWindowInfo info = mDrawingState.inputInfo; - info.frameLeft = screenBounds.left + info.surfaceInset; - info.frameTop = screenBounds.top + info.surfaceInset; - info.frameRight = screenBounds.right - info.surfaceInset; - info.frameBottom = screenBounds.bottom - info.surfaceInset; ui::Transform t = getTransform(); const float xScale = t.sx(); @@ -2135,9 +2131,26 @@ InputWindowInfo Layer::fillInputInfo(const Rect& screenBounds) { info.touchableRegion.scaleSelf(xScale, yScale); } - info.touchableRegion = info.touchableRegion.translate( - screenBounds.left, - screenBounds.top); + // Transform layer size to screen space and inset it by surface insets. + Rect layerBounds = getCroppedBufferSize(getDrawingState()); + layerBounds = t.transform(layerBounds); + layerBounds.inset(info.surfaceInset, info.surfaceInset, info.surfaceInset, info.surfaceInset); + + // Intersect with screen bounds to shrink the frame by the surface insets. The surface insets + // are not set on the screen bounds directly since the surface inset region may already be + // cropped by a parent layer. + Rect frame; + screenBounds.intersect(layerBounds, &frame); + + info.frameLeft = frame.left; + info.frameTop = frame.top; + info.frameRight = frame.right; + info.frameBottom = frame.bottom; + + // Position the touchable region relative to frame screen location and restrict it to frame + // bounds. + info.touchableRegion = info.touchableRegion.translate(info.frameLeft, info.frameTop); + info.touchableRegion = info.touchableRegion.intersect(frame); info.visible = isVisible(); return info; } |