Home | History | Annotate | Download | only in mail
      1 /**
      2  * Copyright (c) 2011, Google Inc.
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *     http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 package com.android.mail;
     17 
     18 import android.content.Context;
     19 import android.os.Handler;
     20 import android.util.AttributeSet;
     21 import android.view.View;
     22 import android.widget.ProgressBar;
     23 
     24 /**
     25  * MinTimeProgressView implements a ProgressBar that waits MIN_DELAY ms to be
     26  * dismissed before showing. Once visible, the progress bar will be visible for
     27  * at least MIN_SHOW_TIME to avoid "flashes" in the UI when an event could take
     28  * a largely variable time to complete (from none, to a user perceivable amount)
     29  *
     30  * @author mindyp
     31  */
     32 public class MinTimeProgressView extends ProgressBar {
     33     private static int sMinShowTime;
     34 
     35     private static int sMinDelay;
     36 
     37     private long mStartTime = -1;
     38 
     39     private final Handler mHandler = new Handler();
     40 
     41     private boolean mDismissed = false;
     42 
     43     public MinTimeProgressView(Context context) {
     44         this(context, null);
     45     }
     46 
     47     public MinTimeProgressView(Context context, AttributeSet attrs) {
     48         super(context, attrs, R.style.MinTimeProgressViewStyle);
     49         sMinShowTime = context.getResources()
     50             .getInteger(R.integer.html_conv_progress_display_time);
     51         sMinDelay = context.getResources()
     52             .getInteger(R.integer.html_conv_progress_wait_time);
     53     }
     54 
     55     private final Runnable mDelayedHide = new Runnable() {
     56         @Override
     57         public void run() {
     58             MinTimeProgressView.super.setVisibility(View.GONE);
     59         }
     60     };
     61 
     62     private final Runnable mDelayedShow = new Runnable() {
     63         @Override
     64         public void run() {
     65             if (!mDismissed) {
     66                 mStartTime = System.currentTimeMillis();
     67                 MinTimeProgressView.super.setVisibility(View.VISIBLE);
     68             }
     69         }
     70     };
     71 
     72     private void hide() {
     73         mDismissed = true;
     74         long diff = System.currentTimeMillis() - mStartTime;
     75         if (diff >= sMinShowTime || mStartTime == -1) {
     76             // The progress spinner has been shown long enough
     77             // OR was not shown yet. If it wasn't shown yet,
     78             // it will just never be shown.
     79             MinTimeProgressView.super.setVisibility(View.GONE);
     80         } else {
     81             // The progress spinner is shown, but not long enough,
     82             // so put a delayed message in to hide it when its been
     83             // shown long enough.
     84             mHandler.postDelayed(mDelayedHide, sMinShowTime - diff);
     85         }
     86     }
     87 
     88     private void show() {
     89         // Reset the start time.
     90         mStartTime = -1;
     91         mHandler.postDelayed(mDelayedShow, sMinDelay);
     92     }
     93 
     94     @Override
     95     public void setVisibility(int visibility) {
     96         // Whenever the visibility gets changed, clear dismissed
     97         // state.
     98         mDismissed = false;
     99         switch (visibility) {
    100             case View.VISIBLE:
    101                 show();
    102                 break;
    103             case View.GONE:
    104                 hide();
    105                 break;
    106             default:
    107                 super.setVisibility(visibility);
    108         }
    109     }
    110 }
    111