blob: 05b86a5d2ce07678b4eeb3a2fdbf35f2776c51a5 [file] [log] [blame]
Santos Cordon7d4ddf62013-07-10 11:58:08 -07001package com.android.phone;
2
3import com.android.internal.telephony.CommandException;
4
5import android.app.AlertDialog;
6import android.app.Dialog;
7import android.app.ProgressDialog;
8import android.content.DialogInterface;
9import android.preference.Preference;
10import android.preference.PreferenceActivity;
11import android.util.Log;
12import android.view.WindowManager;
13
14import java.util.ArrayList;
15
16interface TimeConsumingPreferenceListener {
17 public void onStarted(Preference preference, boolean reading);
18 public void onFinished(Preference preference, boolean reading);
19 public void onError(Preference preference, int error);
20 public void onException(Preference preference, CommandException exception);
21}
22
23public class TimeConsumingPreferenceActivity extends PreferenceActivity
24 implements TimeConsumingPreferenceListener,
25 DialogInterface.OnCancelListener {
26 private static final String LOG_TAG = "TimeConsumingPreferenceActivity";
27 private final boolean DBG = (PhoneGlobals.DBG_LEVEL >= 2);
28
29 private class DismissOnClickListener implements DialogInterface.OnClickListener {
30 @Override
31 public void onClick(DialogInterface dialog, int which) {
32 dialog.dismiss();
33 }
34 }
35 private class DismissAndFinishOnClickListener implements DialogInterface.OnClickListener {
36 @Override
37 public void onClick(DialogInterface dialog, int which) {
38 dialog.dismiss();
39 finish();
40 }
41 }
42 private final DialogInterface.OnClickListener mDismiss = new DismissOnClickListener();
43 private final DialogInterface.OnClickListener mDismissAndFinish
44 = new DismissAndFinishOnClickListener();
45
46 private static final int BUSY_READING_DIALOG = 100;
47 private static final int BUSY_SAVING_DIALOG = 200;
48
49 static final int EXCEPTION_ERROR = 300;
50 static final int RESPONSE_ERROR = 400;
51 static final int RADIO_OFF_ERROR = 500;
52 static final int FDN_CHECK_FAILURE = 600;
Rakesh Pallerla25f80562013-10-09 00:56:05 +053053 static final int STK_CC_SS_TO_DIAL_ERROR = 700;
54 static final int STK_CC_SS_TO_USSD_ERROR = 800;
55 static final int STK_CC_SS_TO_SS_ERROR = 900;
Santos Cordon7d4ddf62013-07-10 11:58:08 -070056
57 private final ArrayList<String> mBusyList = new ArrayList<String>();
58
59 protected boolean mIsForeground = false;
60
61 @Override
62 protected Dialog onCreateDialog(int id) {
63 if (id == BUSY_READING_DIALOG || id == BUSY_SAVING_DIALOG) {
64 ProgressDialog dialog = new ProgressDialog(this);
65 dialog.setTitle(getText(R.string.updating_title));
66 dialog.setIndeterminate(true);
67
68 switch(id) {
69 case BUSY_READING_DIALOG:
70 dialog.setCancelable(true);
71 dialog.setOnCancelListener(this);
72 dialog.setMessage(getText(R.string.reading_settings));
73 return dialog;
74 case BUSY_SAVING_DIALOG:
75 dialog.setCancelable(false);
76 dialog.setMessage(getText(R.string.updating_settings));
77 return dialog;
78 }
79 return null;
80 }
81
82 if (id == RESPONSE_ERROR || id == RADIO_OFF_ERROR || id == EXCEPTION_ERROR
Rakesh Pallerla25f80562013-10-09 00:56:05 +053083 || id == FDN_CHECK_FAILURE || id == STK_CC_SS_TO_DIAL_ERROR
84 || id == STK_CC_SS_TO_USSD_ERROR || id == STK_CC_SS_TO_SS_ERROR) {
Santos Cordon7d4ddf62013-07-10 11:58:08 -070085 AlertDialog.Builder builder = new AlertDialog.Builder(this);
86
87 int msgId;
88 int titleId = R.string.error_updating_title;
89
90 switch (id) {
91 case RESPONSE_ERROR:
92 msgId = R.string.response_error;
93 builder.setPositiveButton(R.string.close_dialog, mDismiss);
94 break;
95 case RADIO_OFF_ERROR:
96 msgId = R.string.radio_off_error;
97 // The error is not recoverable on dialog exit.
98 builder.setPositiveButton(R.string.close_dialog, mDismissAndFinish);
99 break;
100 case FDN_CHECK_FAILURE:
101 msgId = R.string.fdn_check_failure;
102 builder.setPositiveButton(R.string.close_dialog, mDismiss);
103 break;
Rakesh Pallerla25f80562013-10-09 00:56:05 +0530104 case STK_CC_SS_TO_DIAL_ERROR:
105 msgId = R.string.stk_cc_ss_to_dial_error;
106 builder.setPositiveButton(R.string.close_dialog, mDismiss);
107 break;
108 case STK_CC_SS_TO_USSD_ERROR:
109 msgId = R.string.stk_cc_ss_to_ussd_error;
110 builder.setPositiveButton(R.string.close_dialog, mDismiss);
111 break;
112 case STK_CC_SS_TO_SS_ERROR:
113 msgId = R.string.stk_cc_ss_to_ss_error;
114 builder.setPositiveButton(R.string.close_dialog, mDismiss);
115 break;
Santos Cordon7d4ddf62013-07-10 11:58:08 -0700116 case EXCEPTION_ERROR:
117 default:
118 msgId = R.string.exception_error;
119 // The error is not recoverable on dialog exit.
Omkar Kolangadeee1f87d2014-09-27 12:20:06 +0530120 builder.setPositiveButton(R.string.close_dialog, mDismiss);
Santos Cordon7d4ddf62013-07-10 11:58:08 -0700121 break;
122 }
123
124 builder.setTitle(getText(titleId));
125 builder.setMessage(getText(msgId));
126 builder.setCancelable(false);
127 AlertDialog dialog = builder.create();
128
129 // make the dialog more obvious by blurring the background.
130 dialog.getWindow().addFlags(WindowManager.LayoutParams.FLAG_BLUR_BEHIND);
131
132 return dialog;
133 }
134 return null;
135 }
136
137 @Override
138 public void onResume() {
139 super.onResume();
140 mIsForeground = true;
141 }
142
143 @Override
144 public void onPause() {
145 super.onPause();
146 mIsForeground = false;
147 }
148
149 @Override
150 public void onStarted(Preference preference, boolean reading) {
151 if (DBG) dumpState();
152 if (DBG) Log.d(LOG_TAG, "onStarted, preference=" + preference.getKey()
153 + ", reading=" + reading);
154 mBusyList.add(preference.getKey());
155
156 if (mIsForeground) {
157 if (reading) {
158 showDialog(BUSY_READING_DIALOG);
159 } else {
160 showDialog(BUSY_SAVING_DIALOG);
161 }
162 }
163
164 }
165
166 @Override
167 public void onFinished(Preference preference, boolean reading) {
168 if (DBG) dumpState();
169 if (DBG) Log.d(LOG_TAG, "onFinished, preference=" + preference.getKey()
170 + ", reading=" + reading);
171 mBusyList.remove(preference.getKey());
172
173 if (mBusyList.isEmpty()) {
174 if (reading) {
175 dismissDialogSafely(BUSY_READING_DIALOG);
176 } else {
177 dismissDialogSafely(BUSY_SAVING_DIALOG);
178 }
179 }
180 preference.setEnabled(true);
181 }
182
183 @Override
184 public void onError(Preference preference, int error) {
185 if (DBG) dumpState();
186 if (DBG) Log.d(LOG_TAG, "onError, preference=" + preference.getKey() + ", error=" + error);
187
188 if (mIsForeground) {
189 showDialog(error);
190 }
191 preference.setEnabled(false);
192 }
193
194 @Override
195 public void onException(Preference preference, CommandException exception) {
196 if (exception.getCommandError() == CommandException.Error.FDN_CHECK_FAILURE) {
197 onError(preference, FDN_CHECK_FAILURE);
Pavel Zhamaitsiakbcbed442015-04-08 16:59:23 -0700198 } else if (exception.getCommandError() == CommandException.Error.RADIO_NOT_AVAILABLE) {
199 onError(preference, RADIO_OFF_ERROR);
Santos Cordon7d4ddf62013-07-10 11:58:08 -0700200 } else {
201 preference.setEnabled(false);
202 onError(preference, EXCEPTION_ERROR);
203 }
204 }
205
206 @Override
207 public void onCancel(DialogInterface dialog) {
208 if (DBG) dumpState();
209 finish();
210 }
211
212 private void dismissDialogSafely(int id) {
213 try {
214 dismissDialog(id);
215 } catch (IllegalArgumentException e) {
216 // This is expected in the case where we were in the background
217 // at the time we would normally have shown the dialog, so we didn't
218 // show it.
219 }
220 }
221
222 /* package */ void dumpState() {
223 Log.d(LOG_TAG, "dumpState begin");
224 for (String key : mBusyList) {
225 Log.d(LOG_TAG, "mBusyList: key=" + key);
226 }
227 Log.d(LOG_TAG, "dumpState end");
228 }
229}