I am showing my alert dialog in a separate thread and its not working for me. initially when I click
register button for 3000ms I am showing a progress dialogue. and after that I want to show a alert box but its not working. How to solve this?
Thanks in advance...!
register.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
Log.v(TAG, "Trying to Login");
showDialog(0);
t = new Thread() {
public void run() {
showDialog(0);
try {
Thread.sleep(3000);
removeDialog(0);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
};
t.start();
try {
some data sending to server
Object responce=(Object)soapEnvelope.getResponse();
temp=responce.toString();
if(temp.equals("1")){
temp = "The result is 1";
}
System.out.println("The result is "+temp);
new Thread()
{
public void run()
{
try
{
sleep(3000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
AlertDialog.Builder successfullyLogin = new Builder(Register.this);
successfullyLogin.setCancelable(false);
successfullyLogin.setMessage("Successfully Login !").show();
//Toast.makeText(getBaseContext(), "Toast text", Toast.LENGTH_LONG).show();
}
};
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
@Override
protected Dialog onCreateDialog(int id) {
switch (id) {
case 0: {
dialog = new ProgressDialog(this);
dialog.setMessage("Please wait while connecting...");
dialog.setIndeterminate(true);
dialog.setCancelable(true);
}
return dialog;
}
return null;
}
Replace all your threading with AsyncTask classes. They are designed specifically for this type of thing, and work perfectly with the UI for showing dialogs, and dismissing them in the UI thread while still doing background work where you need it.
In this way, you don't need the 3000ms timeout, it just dismisses when it returns. Of course, you could time how long the login takes and keep the dialog up until your 3000ms is up if you want to, but I wouldn't. Also, if you want to pause in Android use SystemClock.sleep(3000);
instead of java's native thread sleep, as you don't need to try/catch the interrupt.
An example that replaces your code (notice the complete lack of threads, try/catches etc that usually litter threading code):
// ... initialising onClickListener of your button to call the async task
Button button = (Button) findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
new StartLoginAsyncTask(YOURAPP.this).execute((Void []) null);
}
});
}
private class StartLoginAsyncTask extends AsyncTask<Void, Void, Integer> {
private ProgressDialog dialog;
private final Context context;
public StartLoginAsyncTask(Context context) {
this.context = context;
}
@Override
protected void onPreExecute() {
// UI work allowed here
dialog = new ProgressDialog(context);
// setup your dialog here
dialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
dialog.setMessage(context.getString(R.string.please_wait_message));
dialog.setCancelable(false);
dialog.show();
}
@Override
protected Integer doInBackground(Void... ignored) {
Integer returnCode = doLogin();
return returnCode;
}
@Override
protected void onPostExecute(Integer returnCode) {
// UI work allowed here
dialog.dismiss();
if (returnCode == LOGIN_OK) {
// ... show other dialogs here that it was OK
} else {
// ... bad news dialog here
}
}
}
private Integer doLogin() {
// ... write your login code here.
// This is run in background, do not do any UI work here
return LOGIN_OK;
}
If you want the login to interrupt the dialog, then add a custom TimeoutException
to the doLogin()
, catch it in the doInBackground()
, and return the appropriate Integer response and handle it in onPostExecute()
.
I think a dialog can only be shown from the main UI thread. So the idea would be to have a handler in your main thread and post a message on it from the new thread, which will launch the dialog.
Take a look at AsyncTask
From JavaDocs: AsyncTask enables proper and easy use of the UI thread. This class allows to perform background operations and publish results on the UI thread without having to manipulate threads and/or handlers.
Inside thread you should use Handler for showing the AlertDialog:
Handler messageHandler = new Handler() {
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what) {
case 111:
// Build and show AlertDialog here
break;
}
}
}
Use below in place of showdialog(0);
messageHandler.sendEmptyMessage(111);