java - Android: can not show dialog from AsyncTask class -
i've builded updates class android app. works fine except download inner asynctask-class.
i wanted display progress dialog in loadingactivity while file downloading.
firstly, invoke updates class in oncreate method. parameter send activity context. in updates class constructor invoke check inner class (asynctask), parse json response url (works properly) , invoke download (next updates inner class) , here it's problem.
when i'm trying create progressdialog object, compiler throws:
04-01 02:53:56.864 24393-24425/pl.com.mpkostrowiec.schedule e/androidruntime﹕ fatal exception: asynctask #1 java.lang.runtimeexception: error occured while executing doinbackground() @ android.os.asynctask$3.done(asynctask.java:299) @ java.util.concurrent.futuretask.finishcompletion(futuretask.java:352) @ java.util.concurrent.futuretask.setexception(futuretask.java:219) @ java.util.concurrent.futuretask.run(futuretask.java:239) @ android.os.asynctask$serialexecutor$1.run(asynctask.java:230) @ java.util.concurrent.threadpoolexecutor.runworker(threadpoolexecutor.java:1080) @ java.util.concurrent.threadpoolexecutor$worker.run(threadpoolexecutor.java:573) @ java.lang.thread.run(thread.java:838) caused by: java.lang.runtimeexception: can't create handler inside thread has not called looper.prepare() @ android.os.handler.<init>(handler.java:197) @ android.os.handler.<init>(handler.java:111) @ android.app.dialog.<init>(dialog.java:107) @ android.app.alertdialog.<init>(alertdialog.java:114) @ android.app.alertdialog.<init>(alertdialog.java:98) @ android.app.progressdialog.<init>(progressdialog.java:77) @ pl.com.mpkostrowiec.schedule.downloadasync.<init>(downloadasync.java:30) @ pl.com.mpkostrowiec.schedule.updates$check.doinbackground(updates.java:128) @ pl.com.mpkostrowiec.schedule.updates$check.doinbackground(updates.java:74) @ android.os.asynctask$2.call(asynctask.java:287) @ java.util.concurrent.futuretask.run(futuretask.java:234) @ android.os.asynctask$serialexecutor$1.run(asynctask.java:230) @ java.util.concurrent.threadpoolexecutor.runworker(threadpoolexecutor.java:1080) @ java.util.concurrent.threadpoolexecutor$worker.run(threadpoolexecutor.java:573) @ java.lang.thread.run(thread.java:838)
i thought progressdialog constructor can't access context variable updates class, tried send parameter, doesn't resolve problem.
loadingactivity class:
package pl.com.mpkostrowiec.schedule; import ... public class loadingactivity extends activity { private final preferences preferences = new preferences(this); @override protected void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); setcontentview(r.layout.activity_loading); preferences.savepreference("preferences", "firstrun", "1"); // check if first run if (preferences.readpreference("preferences", "firstrun").equals("0")) { system.out.println("****************** not first run"); } else { // create directory file dir = this.getdir("versions", mode_private); new updates(this); } } }
update class:
package pl.com.mpkostrowiec.schedule; import ... interface afterexecutelistener { public void afterdownload(string[] versiondata, int type); } public class updates implements afterexecutelistener{ private static versionstable versionstable; private context context; public static boolean status_current = false; public static boolean status_new = false; private final int type_current = 0; private final int type_new = 1; private static final string url = "http://www.mpkostrowiec.com.pl/preview/"; private static final string get_versions = "includes/android/versions.php"; private static final string resources = "resources/android/versions/"; private static final string extension = ".db"; public updates(context context) { this.context = context; versionstable = new versionstable(this.context); new check(type_current).execute(); } public final void afterdownload(string[] versiondata, int type) { // add version data db versionstable.open(); versionstable.add(versiondata); versionstable.close(); // set status if (type == type_current) { system.out.println("****************** downloaded: " + type); status_current = true; } else if (type == type_new) { system.out.println("****************** downloaded: " + type); status_new = true; } schedule(); } private void schedule() { if (status_current) { if (status_new) { system.out.println("****************** success"); } else { new check(type_new).execute(); } } } private class check extends asynctask<string, integer, string> { public afterexecutelistener mlistener; private int type; public check(int type) { this.type = type; } @override protected string doinbackground(string... url) { string[] typestr = {"current", "new"}; // versions form url jsonobject json = null; string versions = null; httpresponse response; httpclient myclient = new defaulthttpclient(); httppost myconnection = new httppost(url + get_versions); try { response = myclient.execute(myconnection); versions = entityutils.tostring(response.getentity(), "utf-8"); } catch (clientprotocolexception e) { e.printstacktrace(); } catch (ioexception e) { e.printstacktrace(); } try{ jsonobject jobject = new jsonobject(versions); json = jobject.getjsonobject(typestr[type]); if (json.length() > 1) { string[] versiondata = {json.getstring("id"), json.getstring("name"), json.getstring("expdate")}; versionstable.open(); boolean idexist = versionstable.check(versiondata[0]); versionstable.close(); // check version if (!idexist) { // start downloading download download = new download(versiondata, type); download.setlistener(updates.this); download.execute(url + resources + versiondata[0] + extension); } } else { // if array contains false field not update if (type == type_current) { updates.status_current = true; } else if (type == type_new) { updates.status_new = true; } schedule(); } } catch ( jsonexception e) { e.printstacktrace(); } return null; } } private class download extends asynctask<string, integer, string> { public progressdialog mprogressdialog; public afterexecutelistener mlistener; private string[] versiondata; private int type; public download(string[] versiondata, int type) { this.versiondata = versiondata; this.type = type; // create progress dialog mprogressdialog = new progressdialog(context); // set progress dialog title mprogressdialog.settitle("updating..."); // set progress dialog message mprogressdialog.setmessage("update in progress. please wait."); mprogressdialog.setindeterminate(false); mprogressdialog.setmax(100); mprogressdialog.setprogressstyle(progressdialog.style_horizontal); } @override protected void onpreexecute() { super.onpreexecute(); // show progress dialog mprogressdialog.show(); } @override protected string doinbackground(string... url) { try { java.net.url url = new url(url[0]); urlconnection connection = url.openconnection(); connection.connect(); // detect file lenghth int filelength = connection.getcontentlength(); // locate storage location string filepath = context.getapplicationinfo().datadir + "/versions"; // download file inputstream input = new bufferedinputstream(url.openstream()); // save downloaded file outputstream output = new fileoutputstream(filepath + "/" + versiondata[0] + ".db"); byte data[] = new byte[1024]; long total = 0; int count; while ((count = input.read(data)) != -1) { total += count; // publish progress publishprogress((int) (total * 100 / filelength)); output.write(data, 0, count); } // close connection output.flush(); output.close(); input.close(); } catch (exception e) { // error log log.e("error", e.getmessage()); e.printstacktrace(); } return null; } @override protected void onprogressupdate(integer... progress) { super.onprogressupdate(progress); // update progress dialog mprogressdialog.setprogress(progress[0]); } @override protected void onpostexecute(string result) { // dismiss progress dialog mprogressdialog.dismiss(); mlistener.afterdownload(versiondata, type); } private void setlistener(afterexecutelistener listener) { mlistener = listener; } } }
Comments
Post a Comment