java - Handler changing UI causes CalledFromWrongThreadException -


i've created handler can accessed anywhere within activity , written method make easier call handler:

private handler textfrombgthread = new handler() {     @override     public void handlemessage (message msg) {         // string msg         string outputstring = msg.getdata().getstring("output");         // find textview         textview output = (textview)findviewbyid(r.id.consoleoutputview);         // display output         log.i("textoutput","about display message: " + outputstring);         output.settext(output.gettext() + outputstring);         log.i("textoutput","message displayed");     } };  private void textoutputwrapper (string outputtext) {     message msg = new message();     bundle bndle = new bundle();     bndle.putstring("output", "\n" + outputtext);     msg.setdata(bndle);     textfrombgthread.handlemessage(msg); } 

so can called background thread with:

textoutputwrapper("attemping connect..."); 

this work 1+ times, however, actual visual change cause calledfromwrongthreadexception thrown. being new java & android, i'm stuck on why happening.

i have noticed crash tends happen when there's longer time period between calls & if calls textoutputwrapper(string) happening after 1 another, works. example, this:

int = 0; while (i < 200) {     textoutputwrapper(string.valueof(i));     i++; } 

works fine.

having looked @ logcat, seems garbage collector frees resources , next time textoutputwrapper(string) called, crashes (when output.settext(string) called, precise), although i'm not sure why cause error.

there's few things i'd change here:

using handler

a handler useful if want trigger ui update, , non-ui thread (aka "background" thread).

in case, it's not serving purpose. directly calling

textfrombgthread.handlemessage(msg); 

it's not designed that. way supposed use handler implement want done ui in handlemessage(message) method. did that. but, shouldn't directly call handlemessage(). if that, handlemessage() called whatever thread invokes textoutputwrapper(). if that's background thread, that's wrong.

what want call handler's sendmessage(message) method (or 1 of other available variants). sendmessage() put message in thread-safe queue, processed on main thread. main thread invoke handler's handlemessage(), passing queued message, , allowing safely change ui. so, change textoutputwrapper() use this:

private void textoutputwrapper (string outputtext) {     message msg = new message();     bundle bndle = new bundle();     bndle.putstring("output", "\n" + outputtext);     msg.setdata(bndle);     textfrombgthread.sendmessage(msg); } 

java conventions

this code bit hard read, experienced java developer. in java, typical coding standards reserve upper case names things classes, while methods start lower case letters. so, please rename method to:

private void textoutputwrapper (string outputtext); 

or, better yet, since in fact method, , not wrapper, per se, rename

private void outputtext(string text); 

safe threading alternatives

finally, might recommend if want method allows safely modify ui thread, use technique. don't find handler easy use beginners.

private void outputtext(final string outputstring) {     runonuithread(new runnable() {         @override         public void run() {             // find textview             textview output = (textview)findviewbyid(r.id.consoleoutputview);             // display output             log.i("textoutput","about display message: " + outputstring);             output.settext(output.gettext() + outputstring);             log.i("textoutput","message displayed");         }     }); } 

runonuithread() method available in every activity.

i'll point general docs on understanding threading in android:

http://www.vogella.com/articles/androidbackgroundprocessing/article.html

http://android-developers.blogspot.com/2009/05/painless-threading.html


Comments

Popular posts from this blog

c# - DetailsView in ASP.Net - How to add another column on the side/add a control in each row? -

javascript - firefox memory leak -

Trying to import CSV file to a SQL Server database using asp.net and c# - can't find what I'm missing -