Merge "Part 2: Adding clear-all to history"
diff --git a/packages/SystemUI/res/drawable/recents_dismiss_all_history.xml b/packages/SystemUI/res/drawable/recents_dismiss_all_history.xml
new file mode 100644
index 0000000..6a417e6
--- /dev/null
+++ b/packages/SystemUI/res/drawable/recents_dismiss_all_history.xml
@@ -0,0 +1,54 @@
+<!--
+Copyright (C) 2016 The Android Open Source Project
+
+   Licensed under the Apache License, Version 2 (the "License");
+    you may not use this file except in compliance with the License.
+    You may obtain a copy of the License at
+
+         http://www.apache.org/licenses/LICENSE-2.0
+
+    Unless required by applicable law or agreed to in writing, software
+    distributed under the License is distributed on an "AS IS" BASIS,
+    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+    See the License for the specific language governing permissions and
+    limitations under the License.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+    android:height="16dp"
+    android:width="28dp"
+    android:viewportHeight="48"
+    android:viewportWidth="72" >
+    <group
+        android:name="dismiss_all"
+        android:translateX="48"
+        android:translateY="6" >
+        <group
+            android:name="3"
+            android:translateX="-24"
+            android:translateY="36" >
+            <path
+                android:name="rectangle_path_1_2"
+                android:pathData="M -24.0,-6.0 l 48.0,0 l 0,12.0 l -48.0,0 Z"
+                android:fillColor="#FFFFFFFF"
+                android:fillAlpha="1" />
+        </group>
+        <group
+            android:name="2"
+            android:translateX="-12"
+            android:translateY="18" >
+            <path
+                android:name="rectangle_path_1_1"
+                android:pathData="M -24.0,-6.0 l 48.0,0 l 0,12.0 l -48.0,0 Z"
+                android:fillColor="#FFFFFFFF"
+                android:fillAlpha="1" />
+        </group>
+        <group
+            android:name="1" >
+            <path
+                android:name="rectangle_path_1"
+                android:pathData="M -24.0,-6.0 l 48.0,0 l 0,12.0 l -48.0,0 Z"
+                android:fillColor="#FFFFFFFF"
+                android:fillAlpha="1" />
+        </group>
+    </group>
+</vector>
diff --git a/packages/SystemUI/res/layout/recents_history_clear_all_button.xml b/packages/SystemUI/res/layout/recents_history_clear_all_button.xml
new file mode 100644
index 0000000..05f0979
--- /dev/null
+++ b/packages/SystemUI/res/layout/recents_history_clear_all_button.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2016 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<TextView
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/button"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    android:gravity="start|center_vertical"
+    android:paddingStart="16dp"
+    android:paddingEnd="16dp"
+    android:paddingTop="14dp"
+    android:paddingBottom="14dp"
+    android:drawableStart="@drawable/recents_dismiss_all_history"
+    android:contentDescription="@string/recents_history_clear_all_button_label"
+    android:textSize="14sp"
+    android:textColor="#FFFFFF"
+    android:textAllCaps="true"
+    android:shadowColor="#99000000"
+    android:shadowDx="0"
+    android:shadowDy="2"
+    android:shadowRadius="5"
+    android:fontFamily="sans-serif-medium"
+    android:background="?android:selectableItemBackground"
+    android:visibility="invisible" />
diff --git a/packages/SystemUI/res/values/strings.xml b/packages/SystemUI/res/values/strings.xml
index 707225c..3efa52f 100644
--- a/packages/SystemUI/res/values/strings.xml
+++ b/packages/SystemUI/res/values/strings.xml
@@ -716,6 +716,8 @@
     <string name="recents_launch_error_message">Could not start <xliff:g id="app" example="Calendar">%s</xliff:g>.</string>
     <!-- Recents: Show history string. [CHAR LIMIT=NONE] -->
     <string name="recents_history_button_label">History</string>
+    <!-- Recents: History clear all string. [CHAR LIMIT=NONE] -->
+    <string name="recents_history_clear_all_button_label">Clear</string>
 
     <!-- Recents: MultiStack add stack split horizontal radio button. [CHAR LIMIT=NONE] -->
     <string name="recents_multistack_add_stack_dialog_split_horizontal">Split Horizontal</string>
diff --git a/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java b/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
index cd2c942..c3b794d 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/RecentsActivity.java
@@ -34,7 +34,6 @@
 import android.util.Log;
 import android.view.KeyEvent;
 import android.view.View;
-import android.view.ViewStub;
 import android.view.ViewTreeObserver;
 import android.view.WindowManager;
 
@@ -57,7 +56,6 @@
 import com.android.systemui.recents.events.activity.LaunchTaskSucceededEvent;
 import com.android.systemui.recents.events.activity.ShowHistoryEvent;
 import com.android.systemui.recents.events.activity.TaskStackUpdatedEvent;
-import com.android.systemui.recents.events.activity.ToggleHistoryEvent;
 import com.android.systemui.recents.events.activity.ToggleRecentsEvent;
 import com.android.systemui.recents.events.component.RecentsVisibilityChangedEvent;
 import com.android.systemui.recents.events.component.ScreenPinningRequestEvent;
@@ -71,7 +69,6 @@
 import com.android.systemui.recents.events.ui.focus.DismissFocusedTaskViewEvent;
 import com.android.systemui.recents.events.ui.focus.FocusNextTaskViewEvent;
 import com.android.systemui.recents.events.ui.focus.FocusPreviousTaskViewEvent;
-import com.android.systemui.recents.history.RecentsHistoryView;
 import com.android.systemui.recents.misc.DozeTrigger;
 import com.android.systemui.recents.misc.SystemServicesProxy;
 import com.android.systemui.recents.model.RecentsPackageMonitor;
@@ -83,8 +80,6 @@
 import com.android.systemui.recents.views.SystemBarScrimViews;
 import com.android.systemui.statusbar.BaseStatusBar;
 
-import java.util.ArrayList;
-
 /**
  * The main Recents activity that is started from AlternateRecentsComponent.
  */
diff --git a/packages/SystemUI/src/com/android/systemui/recents/events/activity/ClearHistoryEvent.java b/packages/SystemUI/src/com/android/systemui/recents/events/activity/ClearHistoryEvent.java
new file mode 100644
index 0000000..98c0a69
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/recents/events/activity/ClearHistoryEvent.java
@@ -0,0 +1,26 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.systemui.recents.events.activity;
+
+import com.android.systemui.recents.events.EventBus;
+
+/**
+ * This is sent when the history is to be cleared
+ */
+public class ClearHistoryEvent extends EventBus.AnimatedEvent {
+    // Simple event
+}
diff --git a/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryAdapter.java b/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryAdapter.java
index 2c28c29..278ac54 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryAdapter.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryAdapter.java
@@ -34,6 +34,7 @@
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.HideHistoryButtonEvent;
 import com.android.systemui.recents.events.activity.HideHistoryEvent;
+import com.android.systemui.recents.events.ui.DeleteTaskDataEvent;
 import com.android.systemui.recents.misc.SystemServicesProxy;
 import com.android.systemui.recents.model.RecentsTaskLoader;
 import com.android.systemui.recents.model.Task;
@@ -210,6 +211,23 @@
     }
 
     /**
+     * Removes all historical tasks.
+     */
+    public void removeAllTasks() {
+        for (int i = mRows.size() - 1; i >= 0; i--) {
+            Row row = mRows.get(i);
+            if (row.getViewType() == TASK_ROW_VIEW_TYPE) {
+                TaskRow taskRow = (TaskRow) row;
+                Task task = taskRow.task;
+                mStack.removeTask(task, TaskViewAnimation.IMMEDIATE);
+                EventBus.getDefault().send(new DeleteTaskDataEvent(task));
+                i = removeTaskRow(i);
+            }
+        }
+        dismissHistory();
+    }
+
+    /**
      * Returns the row at the given {@param position}.
      */
     public Row getRow(int position) {
diff --git a/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryView.java b/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryView.java
index 6dd4b53..96b5cac 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/history/RecentsHistoryView.java
@@ -37,13 +37,12 @@
 import com.android.systemui.recents.RecentsActivity;
 import com.android.systemui.recents.RecentsConfiguration;
 import com.android.systemui.recents.events.EventBus;
+import com.android.systemui.recents.events.activity.ClearHistoryEvent;
 import com.android.systemui.recents.events.activity.PackagesChangedEvent;
 import com.android.systemui.recents.events.ui.ResetBackgroundScrimEvent;
 import com.android.systemui.recents.events.ui.UpdateBackgroundScrimEvent;
-import com.android.systemui.recents.misc.ReferenceCountedTrigger;
 import com.android.systemui.recents.model.TaskStack;
 import com.android.systemui.recents.views.AnimateableViewBounds;
-import com.android.systemui.statusbar.phone.PhoneStatusBar;
 
 /**
  * A list of the recent tasks that are not in the stack.
@@ -96,7 +95,7 @@
     /**
      * Updates this history view with the recent tasks, and then shows it.
      */
-    public void show(TaskStack stack, int stackHeight) {
+    public void show(TaskStack stack, int stackHeight, View clearAllButton) {
         setVisibility(View.VISIBLE);
         setAlpha(0f);
         setTranslationY(-stackHeight * TRANSLATION_Y_PCT);
@@ -106,6 +105,13 @@
                 .setDuration(mHistoryTransitionDuration)
                 .setInterpolator(mFastOutSlowInInterpolator)
                 .setUpdateListener(this)
+                .start();
+        clearAllButton.setVisibility(View.VISIBLE);
+        clearAllButton.setAlpha(0f);
+        clearAllButton.animate()
+                .alpha(1f)
+                .setDuration(mHistoryTransitionDuration)
+                .setInterpolator(mFastOutSlowInInterpolator)
                 .withLayer()
                 .start();
         mAdapter.updateTasks(getContext(), stack);
@@ -118,7 +124,7 @@
     /**
      * Hides this history view.
      */
-    public void hide(boolean animate, int stackHeight) {
+    public void hide(boolean animate, int stackHeight, final View clearAllButton) {
         if (animate) {
             animate()
                     .alpha(0f)
@@ -132,11 +138,25 @@
                             setVisibility(View.INVISIBLE);
                         }
                     })
+                    .start();
+            clearAllButton.animate()
+                    .alpha(0f)
+                    .translationY(0f)
+                    .setDuration(mHistoryTransitionDuration)
+                    .setInterpolator(mFastOutSlowInInterpolator)
+                    .withEndAction(new Runnable() {
+                        @Override
+                        public void run() {
+                            clearAllButton.setVisibility(View.INVISIBLE);
+                        }
+                    })
                     .withLayer()
                     .start();
         } else {
             setAlpha(0f);
             setVisibility(View.INVISIBLE);
+            clearAllButton.setAlpha(0f);
+            clearAllButton.setVisibility(View.INVISIBLE);
         }
         mIsVisible = false;
         EventBus.getDefault().send(new ResetBackgroundScrimEvent());
@@ -222,9 +242,18 @@
         mViewBounds.setClipTop(top);
     }
 
+    @Override
+    public boolean hasOverlappingRendering() {
+        return false;
+    }
+
     /**** EventBus Events ****/
 
     public final void onBusEvent(PackagesChangedEvent event) {
         mAdapter.removeTasks(event.packageName, event.userId);
     }
+
+    public final void onBusEvent(ClearHistoryEvent event) {
+        mAdapter.removeAllTasks();
+    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsView.java b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsView.java
index 41739c4..b59ff30 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/RecentsView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/RecentsView.java
@@ -34,7 +34,6 @@
 import android.view.View;
 import android.view.ViewOutlineProvider;
 import android.view.ViewPropertyAnimator;
-import android.view.ViewStub;
 import android.view.WindowInsets;
 import android.view.animation.AnimationUtils;
 import android.view.animation.Interpolator;
@@ -51,6 +50,7 @@
 import com.android.systemui.recents.RecentsConfiguration;
 import com.android.systemui.recents.RecentsDebugFlags;
 import com.android.systemui.recents.events.EventBus;
+import com.android.systemui.recents.events.activity.ClearHistoryEvent;
 import com.android.systemui.recents.events.activity.DismissRecentsToHomeAnimationStarted;
 import com.android.systemui.recents.events.activity.EnterRecentsWindowAnimationCompletedEvent;
 import com.android.systemui.recents.events.activity.HideHistoryButtonEvent;
@@ -99,6 +99,7 @@
     private TaskStackView mTaskStackView;
     private RecentsAppWidgetHostView mSearchBar;
     private TextView mHistoryButton;
+    private TextView mHistoryClearAllButton;
     private View mEmptyView;
     private RecentsHistoryView mHistoryView;
 
@@ -154,6 +155,7 @@
                 EventBus.getDefault().send(new ToggleHistoryEvent());
             }
         });
+        addView(mHistoryButton);
         mHistoryButton.setClipToOutline(true);
         mHistoryButton.setOutlineProvider(new ViewOutlineProvider() {
             @Override
@@ -161,7 +163,6 @@
                 outline.setRoundRect(0, 0, view.getWidth(), view.getHeight(), cornerRadius);
             }
         });
-        addView(mHistoryButton);
         mEmptyView = inflater.inflate(R.layout.recents_empty, this, false);
         addView(mEmptyView);
 
@@ -406,6 +407,11 @@
         measureChild(mHistoryButton,
                 MeasureSpec.makeMeasureSpec(historyButtonRect.width(), MeasureSpec.AT_MOST),
                 MeasureSpec.makeMeasureSpec(historyButtonRect.height(), MeasureSpec.AT_MOST));
+        if (mHistoryClearAllButton != null && mHistoryClearAllButton.getVisibility() != GONE) {
+            measureChild(mHistoryClearAllButton,
+                    MeasureSpec.makeMeasureSpec(historyButtonRect.width(), MeasureSpec.AT_MOST),
+                    MeasureSpec.makeMeasureSpec(historyButtonRect.height(), MeasureSpec.AT_MOST));
+        }
 
         setMeasuredDimension(width, height);
     }
@@ -441,16 +447,33 @@
             mHistoryView.layout(left, top, right, bottom);
         }
 
-        // Layout the history button such that its drawable is left-aligned with the stack,
+        // Layout the history button such that its drawable is start-aligned with the stack,
         // vertically centered in the available space above the stack
         Rect historyButtonRect = mTaskStackView.mLayoutAlgorithm.mHistoryButtonRect;
-        int historyLeft = historyButtonRect.left - mHistoryButton.getPaddingStart();
+        int historyLeft = isLayoutRtl()
+                ? historyButtonRect.right + mHistoryButton.getPaddingStart()
+                        - mHistoryButton.getMeasuredWidth()
+                : historyButtonRect.left - mHistoryButton.getPaddingStart();
         int historyTop = historyButtonRect.top +
                 (historyButtonRect.height() - mHistoryButton.getMeasuredHeight()) / 2;
         mHistoryButton.layout(historyLeft, historyTop,
                 historyLeft + mHistoryButton.getMeasuredWidth(),
                 historyTop + mHistoryButton.getMeasuredHeight());
 
+        // Layout the history clear all button such that it is end-aligned with the stack,
+        // vertically centered in the available space above the stack
+        if (mHistoryClearAllButton != null && mHistoryClearAllButton.getVisibility() != GONE) {
+            int clearAllLeft = isLayoutRtl()
+                    ? historyButtonRect.left - mHistoryClearAllButton.getPaddingStart()
+                    : historyButtonRect.right + mHistoryClearAllButton.getPaddingStart()
+                            - mHistoryClearAllButton.getMeasuredWidth();
+            int clearAllTop = historyButtonRect.top +
+                    (historyButtonRect.height() - mHistoryClearAllButton.getMeasuredHeight()) / 2;
+            mHistoryClearAllButton.layout(clearAllLeft, clearAllTop,
+                    clearAllLeft + mHistoryClearAllButton.getMeasuredWidth(),
+                    clearAllTop + mHistoryClearAllButton.getMeasuredHeight());
+        }
+
         if (mAwaitingFirstLayout) {
             mAwaitingFirstLayout = false;
 
@@ -665,16 +688,37 @@
 
     public final void onBusEvent(ShowHistoryEvent event) {
         if (mHistoryView == null) {
-            mHistoryView = (RecentsHistoryView) LayoutInflater.from(getContext()).inflate(
-                    R.layout.recents_history, this, false);
+            LayoutInflater inflater = LayoutInflater.from(getContext());
+            mHistoryView = (RecentsHistoryView) inflater.inflate(R.layout.recents_history, this,
+                    false);
             addView(mHistoryView);
 
+            final float cornerRadius = getResources().getDimensionPixelSize(
+                    R.dimen.recents_task_view_rounded_corners_radius);
+            mHistoryClearAllButton = (TextView) inflater.inflate(
+                    R.layout.recents_history_clear_all_button, this, false);
+            mHistoryClearAllButton.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                    EventBus.getDefault().send(new ClearHistoryEvent());
+                }
+            });
+            mHistoryClearAllButton.setClipToOutline(true);
+            mHistoryClearAllButton.setOutlineProvider(new ViewOutlineProvider() {
+                @Override
+                public void getOutline(View view, Outline outline) {
+                    outline.setRoundRect(0, 0, view.getWidth(), view.getHeight(), cornerRadius);
+                }
+            });
+            addView(mHistoryClearAllButton);
+
             // Since this history view is inflated by a view stub after the insets have already
             // been applied, we have to set them ourselves initial from the insets that were last
             // provided.
             mHistoryView.setSystemInsets(mSystemInsets);
             mHistoryView.setHeaderHeight(mHistoryButton.getMeasuredHeight());
             mHistoryButton.bringToFront();
+            mHistoryClearAllButton.bringToFront();
         }
 
         // Animate the empty view in parallel with the history view (the task view animations are
@@ -685,7 +729,7 @@
                     R.integer.recents_history_transition_duration);
             mEmptyView.animate()
                     .alpha(0f)
-                    .translationY(stackRect.bottom)
+                    .translationY(stackRect.height() / 2)
                     .setDuration(historyTransitionDuration)
                     .setInterpolator(mFastOutSlowInInterpolator)
                     .withEndAction(new Runnable() {
@@ -697,7 +741,7 @@
                     .start();
         }
 
-        mHistoryView.show(mStack, stackRect.height());
+        mHistoryView.show(mStack, stackRect.height(), mHistoryClearAllButton);
     }
 
     public final void onBusEvent(HideHistoryEvent event) {
@@ -716,7 +760,7 @@
                     .start();
         }
 
-        mHistoryView.hide(event.animate, stackRect.height());
+        mHistoryView.hide(event.animate, stackRect.height(), mHistoryClearAllButton);
     }
 
     public final void onBusEvent(ShowHistoryButtonEvent event) {
@@ -737,6 +781,8 @@
             mHistoryButton.setAlpha(0f);
             if (translate) {
                 mHistoryButton.setTranslationY(-mHistoryButton.getMeasuredHeight() * 0.25f);
+            } else {
+                mHistoryButton.setTranslationY(0f);
             }
             postAnimationTrigger.addLastDecrementRunnable(new Runnable() {
                 @Override
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
index 1c545c8..efa3ded 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskStackView.java
@@ -64,7 +64,6 @@
 import com.android.systemui.recents.events.ui.DismissTaskViewEvent;
 import com.android.systemui.recents.events.ui.StackViewScrolledEvent;
 import com.android.systemui.recents.events.ui.TaskViewDismissedEvent;
-import com.android.systemui.recents.events.ui.UpdateBackgroundScrimEvent;
 import com.android.systemui.recents.events.ui.UpdateFreeformTaskViewVisibilityEvent;
 import com.android.systemui.recents.events.ui.UserInteractionEvent;
 import com.android.systemui.recents.events.ui.dragndrop.DragDropTargetChangedEvent;
@@ -81,7 +80,6 @@
 import com.android.systemui.recents.model.Task;
 import com.android.systemui.recents.model.TaskStack;
 
-import java.lang.ref.Reference;
 import java.util.ArrayList;
 import java.util.List;
 
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
index d5aea9d..36760f7 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewHeader.java
@@ -47,7 +47,6 @@
 import com.android.systemui.R;
 import com.android.systemui.recents.Constants;
 import com.android.systemui.recents.Recents;
-import com.android.systemui.recents.RecentsDebugFlags;
 import com.android.systemui.recents.events.EventBus;
 import com.android.systemui.recents.events.activity.LaunchTaskEvent;
 import com.android.systemui.recents.events.ui.ShowApplicationInfoEvent;
diff --git a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java
index de96d9d..c3a0ac9 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/views/TaskViewThumbnail.java
@@ -27,8 +27,6 @@
 import android.graphics.Rect;
 import android.graphics.Shader;
 import android.util.AttributeSet;
-import android.util.FloatProperty;
-import android.util.Property;
 import android.view.View;
 import android.view.animation.AnimationUtils;
 import android.view.animation.Interpolator;