Handler
handler是用来处理异步消息的类。
由于子线程不能更新UI界面,主线程不能做耗时操作,handler是让子线程通过与主线程通信来更新UI。
Looper和MessageQueue的关系
当我们在线程中处理完数据后,可以通过Handler对象将消息发出,UI线程中的Looper不断从消息队列中取出消息,刷新UI。
当创建Looper时,将会自动创建MessageQueue,一个线程只会存在一个Looper和一个MessageQueue,当Looper和MessageQueue中有消息时,Looper将会从MessageQueue中取出消息。
Message对象
消息对象,子线程将需要传递到UI线程的信息放到Message对象中,Message对象可以通过Handler对象的方法获得。
- new Message:创建一个新的Message
- obtainMessage:使用原来有的Message
属性:
what属性,int类型,接收方用来识别是什么消息;
arg1、arg2属性,int类型,如果传递的消息仅仅是整型数字,可以直接将数字赋给arg1、arg2;
obj属性,可以传递的消息为String或者其他任意类型
sendTotarget方法:可以将消息发给指定的对象。
Handler的使用方法
handler对象
- sendEmptyMessage():发送消息,消息类型是int类型;
- sendMessage():发送消息,消息类型是Message类型;
- obtainMessage():从消息池中获得一个Message对象,sendMessage时发出Message
public class MainActivity extends AppCompatActivity {
private Button btn;
private TextView tips;
private Handler handler=new Handler(){
@Override
public void handleMessage(Message msg) {
int arg1=msg.arg1;
String info= (String) msg.obj;
if (msg.what==1)
tips.setText("下载完成"+arg1+info);
super.handleMessage(msg);
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
bindID();
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
tips.setText("开始下载");
new Thread(new Runnable() {
@Override
public void run() {
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
Message message=handler.obtainMessage();
message.what=1;
message.arg1=2;
message.obj="hello";
handler.sendMessage(message);
}
}).start();
}
});
}
private void bindID() {
btn=findViewById(R.id.cc_btn);
tips=findViewById(R.id.cc_tips);
}
}
效果图:
利用线程实现倒计时
1、layout文件布局:
<TextView
android:id="@+id/cc_tips"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="准备下载"
android:gravity="center"
android:textSize="30sp"
/>
<Button
android:id="@+id/cc_btn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="开始下载"
android:textSize="30sp"
/>
效果图:
2、在activity文件中,先定义好三个控件(按钮timebtn、倒计时时间textview、文本timetext),绑定ID之后,对timebtn设置监听时间,用来开始倒计时。
在timebtn监听事件里,创建线程,在子线程里实现for循环,用来倒计时。用“handler.sendEmptyMessage(i);”方法更新线程。
activity文件中java代码:
public class Main2Activity extends AppCompatActivity {
private Button timebtn;
private EditText timetext;
private TextView textView;
private int time;
private Handler handler=new Handler(){
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
textView.setText(msg.what+"");
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main2);
bindID();
timebtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//将字符串转换成整形
time= Integer.parseInt(timetext.getText().toString());
new Thread(new Runnable() {
@Override
public void run() {
for(int i=time;i>=0;i--){
//更新UI
handler.sendEmptyMessage(i);
// Message message=new Message();
// message.what=1;
// message.arg1=1;
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}).start();
}
});
}
private void bindID() {
timebtn=findViewById(R.id.cc2_timebtn);
textView=findViewById(R.id.cc2_time3);
timetext=findViewById(R.id.cc2_time);
}
}
效果图:
404

被折叠的 条评论
为什么被折叠?



