Android Handler詳解

/***

  * Handler的定義:

  * 主要接受子線程發送的數據, 並用此數據配合主線程更新UI。當應用程序啓動時,

  * Android首先會開啓一個主線程 (也就是UI線程) , 主線程爲管理界面中的UI控件,進行事件分發, 比如說,

  * 你要是點擊一個 Button ,Android會分發事件到Button上,來響應你的操作。

  * 如果此時需要一個耗時的操作,例如: 聯網讀取數據,或者讀取本地較大的一個文件的時候,你不能把這些操作放在主線程中,

  * 如果你放在主線程中的話,界面會出現假死現象, 如果5秒鐘還沒有完成的話,會收到Android系統的一個錯誤提示 "強制關閉"。

  * 這個時候我們需要把這些耗時的操作,放在一個子線程中,因爲子線程涉及到UI更新,Android主線程是線程不安全的,

  * 也就是說,更新UI只能在主線程中更新,子線程中操作是危險的。這個時候,Handler就出現了,來解決這個複雜的問題 ,

  * 由於Handler運行在主線程中(UI線程中),它與子線程可以通過Message對象來傳遞數據,

  * 這個時候,Handler就承擔着接受子線程傳過來的(子線程用sedMessage()方法傳弟)Message對象(裏面包含數據),把這些消息放入主線程隊列中,配合主線程進行更新UI。

  * Handler一些特點:

  * Handler可以分發Message對象和Runnable對象到主線程中, 每個Handler實例,都會綁定到創建他的線程中(一般是位於主線程),

  * 它有兩個作用: (1): 安排消息或Runnable 在某個主線程中某個地方執行, (2)安排一個動作在不同的線程中執行

  * Handler中分發消息的一些方法
* post(Runnable)

  * postAtTime(Runnable,long)

  * postDelayed(Runnable,long)

  * sendEmptyMessage(int)

  * sendMessage(Message)

  * sendMessageAtTime(Message,long)

  * sendMessageDelayed(Message,long)

  * 以上post類方法允許你排列一個Runnable對象到主線程隊列中,當需要在不同於主UI線程中執行則需要配合HandlerThread進行使用:

  * HandlerThread handlerThread = new HandlerThread("myHandlerThread");

  * handlerThread.start();

  * handler = new Handler(handlerThread.getLooper());* sendMessage類方法, 允許你安排一個帶數據的Message對象到隊列中,等待更新.

  * @author xiaoshuang

  *

  */public class HandlerActivity extends Activity {

  private TextView textView;

  private MyHandler myHandler;

  private Button button;

  private ProgressBar progressBar;

  private MyThread m=new MyThread();

  /** Called when the activity is first created. */

  @Override

  public void onCreate(Bundle savedInstanceState) {

  super.onCreate(savedInstanceState);

  setContentView(R.layout.main);

  textView=(TextView)findViewById(R.id.text);

  button=(Button)findViewById(R.id.startButton);

  progressBar=(ProgressBar)findViewById(R.id.bar);

  progressBar.setMax(100);

  button.setOnClickListener(new View.OnClickListener() {

  @Override

  public void onClick(View arg0) {

  myHandler=new MyHandler();

  new Thread(m).start();

  System.out.println("onCreate--The Thread is: "+Thread.currentThread().getId());

  }

  });

  }//在對UI進行更新時,執行時所在的線程爲主UI線程

  class MyHandler extends Handler{//繼承Handler類時,必須重寫handleMessage方法

  public MyHandler(){

  }

  public MyHandler(Looper l){

  super(l);

  }

  @Override

  public void handleMessage(Message msg) {//執行接收到的通知,此時執行的順序是按照隊列進行,即先進先出

  System.out.println("Handler--The ThreadId is: "+Thread.currentThread().getId());

  super.handleMessage(msg);

  Bundle b=msg.getData();

  String textStr0=textView.getText().toString();

  String textStr1=b.getString("textStr");

  HandlerActivity.this.textView.setText(textStr0+" "+textStr1);//更改TextView中的值

  int barValue=b.getInt("barValue");HandlerActivity.this.progressBar.setProgress(barValue);//更改進度條當中的值

  }

  }//該線程將會在單獨的線程中運行

  class MyThread implements Runnable{

  int i=1;

  @Override

  public void run() {

  while(i<11){

  System.out.println("Thread--The ThreadId is: "+Thread.currentThread().getId());

  try {

  Thread.sleep(1000);

  } catch (InterruptedException e) {

  e.printStackTrace();

  }

  Message msg=new Message();

  Bundle b=new Bundle();

  b.putString("textStr", "線程運行"+i+"次");

  b.putInt("barValue", i*10);

  i++;

  msg.setData(b);

  HandlerActivity.this.myHandler.sendMessage(msg);//通過sendMessage向Handler發送更新UI的消息

  }

  }

  }

  }

  /***
發佈了8 篇原創文章 · 獲贊 6 · 訪問量 11萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章