Introduce pointer capture API.

This depends on I4189eb4d93f50c2865b7a325727be5ceebcc71f8 of
frameworks/native.

Bug: 5452473
Change-Id: Ie21e521f3e5c581f976dc0feb5d84bfa48b046cd
diff --git a/libs/input/PointerController.cpp b/libs/input/PointerController.cpp
index 529849e..212c6a0 100644
--- a/libs/input/PointerController.cpp
+++ b/libs/input/PointerController.cpp
@@ -90,6 +90,7 @@
     mLocked.lastFrameUpdatedTime = 0;
 
     mLocked.buttonState = 0;
+    mLocked.iconDetached = false;
 
     mPolicy->loadPointerIcon(&mLocked.pointerIcon);
 
@@ -184,6 +185,10 @@
 }
 
 void PointerController::setPositionLocked(float x, float y) {
+    if (mLocked.iconDetached) {
+        return;
+    }
+
     float minX, minY, maxX, maxY;
     if (getBoundsLocked(&minX, &minY, &maxX, &maxY)) {
         if (x <= minX) {
@@ -217,6 +222,10 @@
     // Remove the inactivity timeout, since we are fading now.
     removeInactivityTimeoutLocked();
 
+    if (mLocked.iconDetached) {
+        return;
+    }
+
     // Start fading.
     if (transition == TRANSITION_IMMEDIATE) {
         mLocked.pointerFadeDirection = 0;
@@ -234,6 +243,10 @@
     // Always reset the inactivity timer.
     resetInactivityTimeoutLocked();
 
+    if (mLocked.iconDetached) {
+        return;
+    }
+
     // Start unfading.
     if (transition == TRANSITION_IMMEDIATE) {
         mLocked.pointerFadeDirection = 0;
@@ -349,6 +362,22 @@
     updatePointerLocked();
 }
 
+void PointerController::detachPointerIcon(bool detached) {
+    AutoMutex _l(mLock);
+
+    if (mLocked.iconDetached == detached) {
+        return;
+    }
+
+    mLocked.iconDetached = detached;
+    if (detached) {
+        mLocked.pointerFadeDirection = -1;
+    } else {
+        mLocked.pointerFadeDirection = 1;
+    }
+    startAnimationLocked();
+}
+
 void PointerController::setDisplayViewport(int32_t width, int32_t height, int32_t orientation) {
     AutoMutex _l(mLock);