Show the 100% state of the progress at least one frame.

  Bug: 11505806

Change-Id: I5fe8456ff93cd50da53e022ac2cf2dd9ac633b2f
diff --git a/src/com/android/camera/ui/PieRenderer.java b/src/com/android/camera/ui/PieRenderer.java
index 58bee94..60d33c3 100644
--- a/src/com/android/camera/ui/PieRenderer.java
+++ b/src/com/android/camera/ui/PieRenderer.java
@@ -16,9 +16,6 @@
 
 package com.android.camera.ui;
 
-import java.util.ArrayList;
-import java.util.List;
-
 import android.animation.Animator;
 import android.animation.Animator.AnimatorListener;
 import android.animation.ValueAnimator;
@@ -40,8 +37,12 @@
 import android.view.animation.Transformation;
 
 import com.android.camera.drawable.TextDrawable;
+import com.android.camera.ui.ProgressRenderer.VisibilityListener;
 import com.android.camera2.R;
 
+import java.util.ArrayList;
+import java.util.List;
+
 /**
  * An overlay renderer that is used to display focus state and progress state.
  */
@@ -709,6 +710,11 @@
         return false;
     }
 
+    @Override
+    public boolean isVisible() {
+        return super.isVisible() || mProgressRenderer.isVisible();
+    }
+
     private boolean pulledToCenter(PointF polarCoords) {
         return polarCoords.y < mArcRadius - mRadiusInc;
     }
@@ -1014,11 +1020,27 @@
         mState = STATE_IDLE;
     }
 
+    public void clear(boolean waitUntilProgressIsHidden) {
+        if (mState == STATE_PIE)
+            return;
+        cancelFocus();
+
+        if (waitUntilProgressIsHidden) {
+            mOverlay.post(mDisappear);
+            mProgressRenderer.setVisibilityListener(null);
+        } else {
+            mProgressRenderer.setVisibilityListener(new VisibilityListener() {
+                @Override
+                public void onHidden() {
+                    mOverlay.post(mDisappear);
+                }
+            });
+        }
+    }
+
     @Override
     public void clear() {
-        if (mState == STATE_PIE) return;
-        cancelFocus();
-        mOverlay.post(mDisappear);
+        clear(false);
     }
 
     private void startAnimation(long duration, boolean timeout,
diff --git a/src/com/android/camera/ui/ProgressRenderer.java b/src/com/android/camera/ui/ProgressRenderer.java
index 1783c70..1945dcf 100644
--- a/src/com/android/camera/ui/ProgressRenderer.java
+++ b/src/com/android/camera/ui/ProgressRenderer.java
@@ -28,6 +28,11 @@
  * Renders a circular progress bar on the screen.
  */
 public class ProgressRenderer {
+
+    public static interface VisibilityListener {
+        public void onHidden();
+    }
+
     private final int mProgressRadius;
     private final Paint mProgressBasePaint;
     private final Paint mProgressPaint;
@@ -35,6 +40,14 @@
     private RectF mArcBounds = new RectF(0, 0, 1, 1);
     private int mProgressAngleDegrees = 270;
     private boolean mVisible = false;
+    private VisibilityListener mVisibilityListener;
+
+    /**
+     * After we reach 100%, keep on painting the progress for nother x frames
+     * before hiding it.
+     */
+    private static final int SHOW_PROGRESS_X_ADDITIONAL_FRAMES = 5;
+    private int showProgressXMoreFrames;
 
     public ProgressRenderer(Context context) {
         mProgressRadius = context.getResources().getDimensionPixelSize(R.dimen.pie_progress_radius);
@@ -44,14 +57,11 @@
         mProgressPaint = createProgressPaint(pieProgressWidth, 1.0f);
     }
 
-    private static Paint createProgressPaint(int width, float alpha) {
-        Paint paint = new Paint();
-        paint.setAntiAlias(true);
-        // 20% alpha.
-        paint.setColor(Color.argb((int) (alpha * 255), 255, 255, 255));
-        paint.setStrokeWidth(width);
-        paint.setStyle(Paint.Style.STROKE);
-        return paint;
+    /**
+     * Sets or replaces a visiblity listener.
+     */
+    public void setVisibilityListener(VisibilityListener listener) {
+        mVisibilityListener = listener;
     }
 
     /**
@@ -65,8 +75,10 @@
         percent = Math.min(100, Math.max(percent, 0));
         mProgressAngleDegrees = (int) ((360f / 100) * percent);
 
-        // Hide when processing reached 100 percent.
-        mVisible = percent < 100;
+        // We hide the progress once we drew the 100% state once.
+        if (percent < 100) {
+            mVisible = true;
+        }
     }
 
     /**
@@ -82,5 +94,37 @@
 
         canvas.drawCircle(centerX, centerY, mProgressRadius, mProgressBasePaint);
         canvas.drawArc(mArcBounds, -90, mProgressAngleDegrees, false, mProgressPaint);
+
+        // After we reached 100%, we paint the progress renderer for another x
+        // frames until we hide it.
+        if (mProgressAngleDegrees == 360) {
+            if (showProgressXMoreFrames <= 0) {
+                showProgressXMoreFrames = SHOW_PROGRESS_X_ADDITIONAL_FRAMES;
+            } else {
+                if (--showProgressXMoreFrames == 0) {
+                    mVisible = false;
+                    if (mVisibilityListener != null) {
+                        mVisibilityListener.onHidden();
+                    }
+                }
+            }
+        }
+    }
+
+    /**
+     * @return Whether the progress renderer is visible.
+     */
+    public boolean isVisible() {
+        return mVisible;
+    }
+
+    private static Paint createProgressPaint(int width, float alpha) {
+        Paint paint = new Paint();
+        paint.setAntiAlias(true);
+        // 20% alpha.
+        paint.setColor(Color.argb((int) (alpha * 255), 255, 255, 255));
+        paint.setStrokeWidth(width);
+        paint.setStyle(Paint.Style.STROKE);
+        return paint;
     }
 }