Merge changes I4cbf9376,Ief2111ec into sc-dev am: dec5d61e3a am: 89e4a33931

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/15096008

Change-Id: I7e58fa8a3f20db68b2840265ed0b3baa8a088b8d
diff --git a/packages/SystemUI/res/layout/global_screenshot.xml b/packages/SystemUI/res/layout/global_screenshot.xml
index 93bd581..c92b10c 100644
--- a/packages/SystemUI/res/layout/global_screenshot.xml
+++ b/packages/SystemUI/res/layout/global_screenshot.xml
@@ -19,12 +19,15 @@
     android:id="@+id/global_screenshot_frame"
     android:theme="@style/Screenshot"
     android:layout_width="match_parent"
-    android:layout_height="match_parent">
+    android:layout_height="match_parent"
+    android:importantForAccessibility="no">
     <ImageView
         android:id="@+id/screenshot_scrolling_scrim"
         android:layout_width="match_parent"
         android:layout_height="match_parent"
-        android:visibility="gone"/>
+        android:visibility="gone"
+        android:clickable="true"
+        android:importantForAccessibility="no"/>
     <ImageView
         android:id="@+id/global_screenshot_actions_background"
         android:layout_height="@dimen/screenshot_bg_protection_height"
diff --git a/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotController.java b/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotController.java
index 2e13836..24cca91 100644
--- a/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotController.java
+++ b/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotController.java
@@ -486,9 +486,24 @@
     private void takeScreenshotInternal(Consumer<Uri> finisher, Rect crop) {
         // copy the input Rect, since SurfaceControl.screenshot can mutate it
         Rect screenRect = new Rect(crop);
+        Bitmap screenshot = captureScreenshot(crop);
+
+        if (screenshot == null) {
+            Log.e(TAG, "takeScreenshotInternal: Screenshot bitmap was null");
+            mNotificationsController.notifyScreenshotError(
+                    R.string.screenshot_failed_to_capture_text);
+            if (mCurrentRequestCallback != null) {
+                mCurrentRequestCallback.reportError();
+            }
+            return;
+        }
+
+        saveScreenshot(screenshot, finisher, screenRect, Insets.NONE, true);
+    }
+
+    private Bitmap captureScreenshot(Rect crop) {
         int width = crop.width();
         int height = crop.height();
-
         Bitmap screenshot = null;
         final Display display = getDefaultDisplay();
         final DisplayAddress address = display.getAddress();
@@ -509,18 +524,7 @@
                     SurfaceControl.captureDisplay(captureArgs);
             screenshot = screenshotBuffer == null ? null : screenshotBuffer.asBitmap();
         }
-
-        if (screenshot == null) {
-            Log.e(TAG, "takeScreenshotInternal: Screenshot bitmap was null");
-            mNotificationsController.notifyScreenshotError(
-                    R.string.screenshot_failed_to_capture_text);
-            if (mCurrentRequestCallback != null) {
-                mCurrentRequestCallback.reportError();
-            }
-            return;
-        }
-
-        saveScreenshot(screenshot, finisher, screenRect, Insets.NONE, true);
+        return screenshot;
     }
 
     private void saveScreenshot(Bitmap screenshot, Consumer<Uri> finisher, Rect screenRect,
@@ -644,45 +648,56 @@
 
             final ScrollCaptureResponse response = mLastScrollCaptureResponse;
             mScreenshotView.showScrollChip(/* onClick */ () -> {
-                mScreenshotView.prepareScrollingTransition(response, mScreenBitmap);
-                // Clear the reference to prevent close() in dismissScreenshot
-                mLastScrollCaptureResponse = null;
-                final ListenableFuture<ScrollCaptureController.LongScreenshot> future =
-                        mScrollCaptureController.run(response);
-                future.addListener(() -> {
-                    ScrollCaptureController.LongScreenshot longScreenshot;
-                    try {
-                        longScreenshot = future.get();
-                    } catch (CancellationException | InterruptedException | ExecutionException e) {
-                        Log.e(TAG, "Exception", e);
-                        return;
-                    }
+                DisplayMetrics displayMetrics = new DisplayMetrics();
+                getDefaultDisplay().getRealMetrics(displayMetrics);
+                Bitmap newScreenshot = captureScreenshot(
+                        new Rect(0, 0, displayMetrics.widthPixels, displayMetrics.heightPixels));
 
-                    mLongScreenshotHolder.setLongScreenshot(longScreenshot);
-                    mLongScreenshotHolder.setTransitionDestinationCallback(
-                            (transitionDestination, onTransitionEnd) ->
-                                    mScreenshotView.startLongScreenshotTransition(
-                                            transitionDestination, onTransitionEnd,
-                                            longScreenshot));
+                mScreenshotView.prepareScrollingTransition(response, mScreenBitmap, newScreenshot);
+                // delay starting scroll capture to make sure the scrim is up before the app moves
+                mScreenshotView.post(() -> {
+                    // Clear the reference to prevent close() in dismissScreenshot
+                    mLastScrollCaptureResponse = null;
+                    final ListenableFuture<ScrollCaptureController.LongScreenshot> future =
+                            mScrollCaptureController.run(response);
+                    future.addListener(() -> {
+                        ScrollCaptureController.LongScreenshot longScreenshot;
+                        try {
+                            longScreenshot = future.get();
+                        } catch (CancellationException
+                                | InterruptedException
+                                | ExecutionException e) {
+                            Log.e(TAG, "Exception", e);
+                            return;
+                        }
 
-                    final Intent intent = new Intent(mContext, LongScreenshotActivity.class);
-                    intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
+                        mLongScreenshotHolder.setLongScreenshot(longScreenshot);
+                        mLongScreenshotHolder.setTransitionDestinationCallback(
+                                (transitionDestination, onTransitionEnd) ->
+                                        mScreenshotView.startLongScreenshotTransition(
+                                                transitionDestination, onTransitionEnd,
+                                                longScreenshot));
 
-                    Pair<ActivityOptions, ExitTransitionCoordinator> transition =
-                            ActivityOptions.startSharedElementAnimation(mWindow,
-                                    new ScreenshotExitTransitionCallbacksSupplier(false).get(),
-                                    null);
-                    transition.second.startExit();
-                    mContext.startActivity(intent, transition.first.toBundle());
-                    RemoteAnimationAdapter runner = new RemoteAnimationAdapter(
-                            SCREENSHOT_REMOTE_RUNNER, 0, 0);
-                    try {
-                        WindowManagerGlobal.getWindowManagerService()
-                                .overridePendingAppTransitionRemote(runner, DEFAULT_DISPLAY);
-                    } catch (Exception e) {
-                        Log.e(TAG, "Error overriding screenshot app transition", e);
-                    }
-                }, mMainExecutor);
+                        final Intent intent = new Intent(mContext, LongScreenshotActivity.class);
+                        intent.setFlags(
+                                Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
+
+                        Pair<ActivityOptions, ExitTransitionCoordinator> transition =
+                                ActivityOptions.startSharedElementAnimation(mWindow,
+                                        new ScreenshotExitTransitionCallbacksSupplier(false).get(),
+                                        null);
+                        transition.second.startExit();
+                        mContext.startActivity(intent, transition.first.toBundle());
+                        RemoteAnimationAdapter runner = new RemoteAnimationAdapter(
+                                SCREENSHOT_REMOTE_RUNNER, 0, 0);
+                        try {
+                            WindowManagerGlobal.getWindowManagerService()
+                                    .overridePendingAppTransitionRemote(runner, DEFAULT_DISPLAY);
+                        } catch (Exception e) {
+                            Log.e(TAG, "Error overriding screenshot app transition", e);
+                        }
+                    }, mMainExecutor);
+                });
             });
         } catch (CancellationException e) {
             // Ignore
diff --git a/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotView.java b/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotView.java
index 3c830cc..9fe8c84 100644
--- a/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotView.java
+++ b/packages/SystemUI/src/com/android/systemui/screenshot/ScreenshotView.java
@@ -36,8 +36,10 @@
 import android.app.Notification;
 import android.app.PendingIntent;
 import android.content.Context;
+import android.content.res.ColorStateList;
 import android.content.res.Resources;
 import android.graphics.Bitmap;
+import android.graphics.BlendMode;
 import android.graphics.Color;
 import android.graphics.Insets;
 import android.graphics.Matrix;
@@ -257,10 +259,10 @@
     @Override // ViewTreeObserver.OnComputeInternalInsetsListener
     public void onComputeInternalInsets(ViewTreeObserver.InternalInsetsInfo inoutInfo) {
         inoutInfo.setTouchableInsets(ViewTreeObserver.InternalInsetsInfo.TOUCHABLE_INSETS_REGION);
-        inoutInfo.touchableRegion.set(getTouchRegion());
+        inoutInfo.touchableRegion.set(getTouchRegion(true));
     }
 
-    private Region getTouchRegion() {
+    private Region getTouchRegion(boolean includeScrim) {
         Region touchRegion = new Region();
 
         final Rect tmpRect = new Rect();
@@ -273,6 +275,11 @@
         mDismissButton.getBoundsOnScreen(tmpRect);
         touchRegion.op(tmpRect, Region.Op.UNION);
 
+        if (includeScrim && mScrollingScrim.getVisibility() == View.VISIBLE) {
+            mScrollingScrim.getBoundsOnScreen(tmpRect);
+            touchRegion.op(tmpRect, Region.Op.UNION);
+        }
+
         if (QuickStepContract.isGesturalMode(mNavMode)) {
             final WindowManager wm = mContext.getSystemService(WindowManager.class);
             final WindowMetrics windowMetrics = wm.getCurrentWindowMetrics();
@@ -296,7 +303,7 @@
                     if (ev instanceof MotionEvent) {
                         MotionEvent event = (MotionEvent) ev;
                         if (event.getActionMasked() == MotionEvent.ACTION_DOWN
-                                && !getTouchRegion().contains(
+                                && !getTouchRegion(false).contains(
                                 (int) event.getRawX(), (int) event.getRawY())) {
                             mCallbacks.onTouchOutside();
                         }
@@ -313,6 +320,10 @@
 
     @Override // ViewGroup
     public boolean onInterceptTouchEvent(MotionEvent ev) {
+        // scrolling scrim should not be swipeable; return early if we're on the scrim
+        if (!getTouchRegion(false).contains((int) ev.getRawX(), (int) ev.getRawY())) {
+            return false;
+        }
         // always pass through the down event so the swipe handler knows the initial state
         if (ev.getActionMasked() == MotionEvent.ACTION_DOWN) {
             mSwipeDismissHandler.onTouch(this, ev);
@@ -374,10 +385,6 @@
         return mScreenshotPreview;
     }
 
-    View getScrollablePreview() {
-        return mScrollablePreview;
-    }
-
     /**
      * Set up the logger and callback on dismissal.
      *
@@ -807,8 +814,9 @@
         anim.start();
     }
 
-    void prepareScrollingTransition(ScrollCaptureResponse response, Bitmap screenBitmap) {
-        mScrollingScrim.setImageBitmap(screenBitmap);
+    void prepareScrollingTransition(ScrollCaptureResponse response, Bitmap screenBitmap,
+            Bitmap newBitmap) {
+        mScrollingScrim.setImageBitmap(newBitmap);
         mScrollingScrim.setVisibility(View.VISIBLE);
         Rect scrollableArea = scrollableAreaOnScreen(response);
         float scale = mCornerSizeX
@@ -828,7 +836,19 @@
 
         mScrollablePreview.setImageBitmap(screenBitmap);
         mScrollablePreview.setVisibility(View.VISIBLE);
-        createScreenshotFadeDismissAnimation(true).start();
+        mDismissButton.setVisibility(View.GONE);
+        mActionsContainer.setVisibility(View.GONE);
+        mBackgroundProtection.setVisibility(View.GONE);
+        // set these invisible, but not gone, so that the views are laid out correctly
+        mActionsContainerBackground.setVisibility(View.INVISIBLE);
+        mScreenshotPreviewBorder.setVisibility(View.INVISIBLE);
+        mScreenshotPreview.setVisibility(View.INVISIBLE);
+        mScrollingScrim.setImageTintBlendMode(BlendMode.SRC_ATOP);
+        ValueAnimator anim = ValueAnimator.ofFloat(0, .3f);
+        anim.addUpdateListener(animation -> mScrollingScrim.setImageTintList(
+                ColorStateList.valueOf(Color.argb((float) animation.getAnimatedValue(), 0, 0, 0))));
+        anim.setDuration(200);
+        anim.start();
     }
 
     boolean isDismissing() {
@@ -844,10 +864,6 @@
     }
 
     private void animateDismissal(Animator dismissAnimation) {
-        if (DEBUG_WINDOW) {
-            Log.d(TAG, "removing OnComputeInternalInsetsListener");
-        }
-        getViewTreeObserver().removeOnComputeInternalInsetsListener(this);
         mDismissAnimation = dismissAnimation;
         mDismissAnimation.addListener(new AnimatorListenerAdapter() {
             private boolean mCancelled = false;
@@ -909,6 +925,7 @@
                 mContext.getResources().getString(R.string.screenshot_preview_description));
         mScreenshotPreview.setOnClickListener(null);
         mShareChip.setOnClickListener(null);
+        mScrollingScrim.setVisibility(View.GONE);
         mEditChip.setOnClickListener(null);
         mShareChip.setIsPending(false);
         mEditChip.setIsPending(false);
@@ -931,7 +948,7 @@
             transition.action.actionIntent.send();
 
             // fade out non-preview UI
-            createScreenshotFadeDismissAnimation(false).start();
+            createScreenshotFadeDismissAnimation().start();
         } catch (PendingIntent.CanceledException e) {
             mPendingSharedTransition = false;
             if (transition.onCancelRunnable != null) {
@@ -969,7 +986,7 @@
         return animSet;
     }
 
-    ValueAnimator createScreenshotFadeDismissAnimation(boolean fadePreview) {
+    ValueAnimator createScreenshotFadeDismissAnimation() {
         ValueAnimator alphaAnim = ValueAnimator.ofFloat(0, 1);
         alphaAnim.addUpdateListener(animation -> {
             float alpha = 1 - animation.getAnimatedFraction();
@@ -978,9 +995,6 @@
             mActionsContainer.setAlpha(alpha);
             mBackgroundProtection.setAlpha(alpha);
             mScreenshotPreviewBorder.setAlpha(alpha);
-            if (fadePreview) {
-                mScreenshotPreview.setAlpha(alpha);
-            }
         });
         alphaAnim.setDuration(600);
         return alphaAnim;