ProgressDialog не будет отклонен, если я переключусь на другое приложение, даже если IntentService завершил
В моем приложении я использую IntentService для запуска длинного процесса (отправка данных на сервер)
Это код действия, которое запускает IntentService.
public class SendDataActivity extends Activity implements OnClickListener {
public static final String ACTION_SEND_DATA = "com.ss.quickorder.SEND_DATA";
private Button mSendDataButton;
private ProgressDialog mProgress;
// define instance variable for the broadcast receiver
private SendDataReceiver sendDataReceiver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_enviar_datos);
mSendDataButton = (Button) findViewById(R.id.sendDataButton);
mSendDataButton.setOnClickListener(this);
}
@Override
public void onClick(View v) {
// here get SharedPreferences and send them with the Intent
Intent inputIntent = new Intent(SendDataActivity.this,
SendaDataService.class);
// Display progress to the user
mProgress = ProgressDialog.show(this, "Sending Data",
"This might take a few minutes, please wait...", true);
startService(inputIntent);
}
@Override
protected void onPause() {
super.onPause();
LocalBroadcastManager localBroadcastManager = LocalBroadcastManager
.getInstance(this);
localBroadcastManager.unregisterReceiver(sendDataReceiver);
}
@Override
protected void onResume() {
super.onResume();
IntentFilter broadcastFilter = new IntentFilter(
SendDataActivity.ACTION_SEND_DATA);
sendDataReceiver = new SendDataReceiver();
LocalBroadcastManager localBroadcastManager = LocalBroadcastManager
.getInstance(this);
localBroadcastManager.registerReceiver(sendDataReceiver,
broadcastFilter);
}
// define an inner class for the broadcast receiver
class SendDataReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Log.d("QuickOrder", "Broadcast received!!!");
//get data from intent
boolean success = intent.getBooleanExtra("success", false);
// Clear progress indicator
SendDataActivity.this.mProgress.dismiss();
String message;
if (success) {
message = String.valueOf(intent.getIntExtra("resultado",0));
} else {
message = intent.getStringExtra("message");
Log.d("QuickOrder", "An error has occurred:-->" + message);
}
// update the display
Toast.makeText(SendDataActivity.this,
message, Toast.LENGTH_LONG).show();
}
}
}
Процесс выполняется в фоновом режиме, как и ожидалось, и когда он заканчивается, я использую LocalBroadcastManager, чтобы отправить некоторые данные обратно в действие, которое вызвало IntenService
Это код для IntentService
public class SendDataService extends IntentService {
private static final String NAME = "SendDataService";
public SendDataService() {
super(NAME);
// We don’t want intents redelivered
// in case we’re shut down unexpectedly
setIntentRedelivery(false);
}
@Override
protected void onHandleIntent(Intent intent) {
// get NetworkInfo object
ConnectivityManager connectivityManager = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
// if network is connected, download data
if (networkInfo != null && networkInfo.isConnected()) {
String message = "";
int result=0;
boolean success = false;
try {
//send data to the server
success=true;
} catch (Exception e) {
success=false;
message=e.getMessage();
}
Intent broadCasIntent=new Intent();
broadCasIntent.setAction(SendDataActivity.ACTION_SEND_DATA);
broadCasIntent.putExtra("success", success);
broadCasIntent.putExtra("result", result);
broadCasIntent.putExtra("message", message);
LocalBroadcastManager localBroadcastManager=LocalBroadcastManager
.getInstance(this);
localBroadcastManager.sendBroadcast(broadCasIntent);
}
}
}
Как вы можете видеть выше в действии SendDataActivity, я создал внутренний класс, который расширяет класс BroadcastReceiver, и в этом классе я отклоняю ProgressDialog.
Код для BroadcastReceiver в SendDataActivity
class SendDataReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Log.d("QuickOrder", "Broadcast received!!!");
//get data from intent
boolean success = intent.getBooleanExtra("success", false);
// Clear progress indicator
SendDataActivity.this.mProgress.dismiss(); //This doesn't work If I switch to another application
String message;
if (success) {
message = String.valueOf(intent.getIntExtra("resultado",0));
} else {
message = intent.getStringExtra("message");
Log.d("QuickOrder", "An error has occurred:-->" + message);
}
// update the display
Toast.makeText(SendDataActivity.this,
message, Toast.LENGTH_LONG).show();
}
}
С кодом, показанным выше, все работает, как и ожидалось, пока я остаюсь в приложении, но проблема возникает, если я переключаюсь на другое приложение или если я получаю телефонный звонок, а затем возвращаюсь к своему приложению. Там я по-прежнему нахожу ProgressDialog IntentService все еще будет работать, и я на 100% уверен, что он завершен, потому что я вижу результат в консоли LogCat и в базе данных.
Есть ли проблемы с ProgressDialogs в подобных сценариях? Я что-то пропустил?
Заранее спасибо.
1 ответ
Закройте диалоговое окно прогресса в onResume.
@Override
protected void onResume() {
super.onResume();
if (pDialog != null && pDialog.isShowing()) {
pDialog.dismiss();
}
}
Проблема здесь в том, что когда-то ваш IntentService
обработал ваш Intent
, его использование завершено, и он отправит трансляцию, а Android убьет это IntentService
, Это то, что он делает, обрабатывать Intent
,
Теперь, если ваш Activity
был приостановлен, нет никакого способа, которым он мог обработать Broadcast
отправлено вашим IntentService
и он не может запросить ваш IntentService
потому что они не могут быть привязаны к вашему Activity
,
То, что я предлагаю, это: использовать Bound Service. Ваш Activity
может начать Service
в onClick()
а затем использовать bindService()
иметь переменную, которая ссылается на ваш сервис. Вы также можете привязать к Service
в вашем onResume()
проверить, есть ли у него какие-либо запущенные операции или нет, и показать / отклонить ProgressDialog
соответственно.
Как только ваш Activity
зависит от вашего IntentService
, вы должны подойти к Bound Service
,