Handler是做什么的?
handler是用来更新UI和发送,处理消息的。
Handler,Looper,messageQueue关系?
handler:发送消息
looper:接收消息,并发消息回传给hanlder自己
messageQueue:存储消息
常见的4种更新UI方法
...
/更新Ui
new Thread(){
@Override
public void run() {
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
// 4种更新UI的方法全部都是子UI线程(主线程进行)
// handler1();
// handler2();
// handler3();
// handler4();
}
}.start();;
}
private void handler1() {
//实际上在内部也是调用handler.sendMessageDelayed(),也是发送message
handler.post(new Runnable() {
@Override
public void run() {
bt1.setText("change bt1");
}
});
}
private void handler2() {
//实际上发送信息给hanler, 然后在handleMessage方法里更新UI
handler.sendEmptyMessage(1);
}
private void handler3() {
//实际上内部是调用handler.post()
runOnUiThread(new Runnable() {
@Override
public void run() {
bt1.setText("change bt1");
}
});
}
private void handler4() {
//实际上内部是调用handler.post()
bt1.post(new Runnable() {
@Override
public void run() {
bt1.setText("change bt1");
}
});
}
...
主线程与子线程传递消息,信息交互
实际上是主线程的handler与子线程的handler互相发送消息
public class MainActivity extends Activity{
private Button bt1;
private Button bt2;
//这里的执行操作在主线程
private Handler handler = new Handler(){
public void handleMessage(android.os.Message msg) {
threadHandler.sendEmptyMessageDelayed(1, 1000);
Log.v("TAG", "handler-->"+Thread.currentThread());
};
};
private Handler threadHandler;
private HandlerThread thread;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
thread = new HandlerThread("handlerThread");
thread.start();
//这里的执行操作在子线程
threadHandler = new Handler(thread.getLooper()) {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
handler.sendEmptyMessageDelayed(333, 1000);
Log.v("TAG", "threadHandler-->"+Thread.currentThread());
}
};
bt1 = (Button) findViewById(R.id.button1);
bt1.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
handler.sendEmptyMessage(1);
}
});
bt2 = (Button) findViewById(R.id.button2);
bt2.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
handler.removeMessages(333);//remove的what 要对应
}
});
}
效果
注意要点:
1.子线程中的hanlder必须指定一个looper,looper从该子线程获得
2.实际上停止消息的传递,要在刚发生的一瞬间,remove掉该message(猜测:刚发生后,还没在Queue里取出message,然后remove调,就不会执行handleMessaage,从而停止通信)
实际上是可以在子线程更新UI,当强烈不推荐这样,推荐在hanlder内更新UI
子线程更新UI :
new Thread(){
@Override
public void run() {
bt1.setText("change bt1");
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}.start();;
}
实际上就是在调用Thread.sleep()之前setText(),这样可以更新UI且不报错. 若是在Thread.sleep()之后setText()就会报异常,再重复一次,不推荐在子线程更新UI
//这些问题与ViewRootIMP有关
转载于:http://www.imooc.com/learn/267
2016/4/8更新
1.looper.prepare()获得一个当前线程里的looper实例,在实例里创建一个messageQueue
2.looper.loop()不断从messageQueue里取得message并回调msg.target.dispatchMessage(msg)
3.在handler构造方法里得到当前线程的looper实例,并与looper实例里面的messagequeue相关联
4.Handler的sentMessage方法会把message的taget赋值给handler,然后加入到messageQueue里
5.在构造handler时会重写handlermessage方法,实际上就是msg.target.dispatchMessage(msg)最终调用的方法
转载于:http://blog.csdn.net/lmj623565791/article/details/38377229/