Как показать ProgressBar через определенное время
Я работаю с Android API уровня 23 (Android 6). Я использую com.loopj.android.http.AsyncHttpClient для реализации асинхронной связи с моим внутренним сервером, и она работает нормально.
Во время связи с сервером я показываю индикатор выполнения, например:
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
и скрыть это так:
findViewById(R.id.loadingPanel).setVisibility(View.GONE);
когда сделано как предложено здесь.
Это работает очень хорошо.
В настоящее время большую часть времени запросы к серверу занимают всего несколько миллисекунд, поэтому отображение и скрытие индикатора выполнения вызывает некоторое мерцание, которое не является необходимым, и раздражает, если время запроса очень мало.
Что было бы хорошим способом показать индикатор выполнения только через определенное время после начала запроса, скажем, через одну секунду?
4 ответа
Я предполагаю, что вы сделали что-то вроде следующего
AsyncHttpClient client = new AsyncHttpClient();
client.get("https://www.example.com", new AsyncHttpResponseHandler() {
@Override
public void onStart() {
// called before request is started
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
}
@Override
public void onSuccess(int statusCode, Header[] headers, byte[] response) {
// called when response HTTP status is "200 OK"
findViewById(R.id.loadingPanel).setVisibility(View.GONE);
}
@Override
public void onFailure(int statusCode, Header[] headers, byte[] errorResponse, Throwable e) {
// called when response HTTP status is "4XX" (eg. 401, 403, 404)
}
@Override
public void onRetry(int retryNo) {
// called when request is retried
}
});
Просто попробуйте что-то вроде следующего
boolean showProgress= true;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
AsyncHttpClient client = new AsyncHttpClient();
client.get("https://www.google.com", new AsyncHttpResponseHandler() {
@Override
public void onStart() {
// called before request is started
//findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
if(showProgress){
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
}
}
}, 5*1000); // your progress will start after 5 seconds
}
@Override
public void onSuccess(int statusCode, Header[] headers, byte[] response) {
// called when response HTTP status is "200 OK"
//findViewById(R.id.loadingPanel).setVisibility(View.GONE);
showProgress = false;
}
@Override
public void onFailure(int statusCode, Header[] headers, byte[] errorResponse, Throwable e) {
// called when response HTTP status is "4XX" (eg. 401, 403, 404)
showProgress = false;
}
@Override
public void onRetry(int retryNo) {
// called when request is retried
}
});
}
Вы можете использовать переменную логического флага, изначально установленную в true. Затем, когда вы получите ответ от сервера, вы можете изменить значение флага. Тогда вы можете использовать обработчик, как:
Handler myHandler = new Handler();
myHandler.postDelayed(new Runnable() {
@Override
public void run() {
if(flag)
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
}
}, 1000);
Handler endHandler = new Handler();
endHandler.postDelayed(new Runnable() {
@Override
public void run() {
findViewById(R.id.loadingPanel).setVisibility(View.GONE);
}
}, MAX_WAIT_TIME_YOU_WANT);
Вы можете установить задержку перед отображением индикатора выполнения следующим образом:
Handler myHandler = new Handler();
myHandler.postDelayed(new Runnable() {
@Override
public void run() {
// Do something after 1s = 1000ms
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
}
}, 1000);
Вы можете просто использовать CountDownTimer
во втором тике. Как это:
private boolean mNeedToCloseProgress = false;
// in second with 100 ms tick
CountDownTimer mCdtStartProgress = new CountDownTimer(1000, 1000) {
public void onTick(long millisUntilFinished) {}
public void onFinish() {
mNeedToCloseProgress = true;
findViewById(R.id.loadingPanel).setVisibility(View.VISIBLE);
}
};
Затем, когда вы начинаете вызов API, вам нужно запустить таймер с помощью:
mCdtStartProgress.start();
который изменит флаг mNeedToCloseProgress
что говорит о том, должен ли прогресс быть близким.
Затем отмените таймер, когда вы закончите вызывать API и получите результат с:
mCdtStartProgress.cancel();
if(mNeedToCloseProgress) findViewById(R.id.loadingPanel).setVisibility(View.GONE);