Android中定時器Timer和TimerTask的啓動,停止,暫停,繼續等操作實例

下面是一個在Android中使用定時器Timer和TimerTask的啓動,停止,暫停,繼續等操作的demo。
需要注意的問題主要有兩點:
1、Timer和TimerTask在調用cancel()取消後不能再執行 schedule語句,否則提示出錯,提示如下:
  1. D/AndroidRuntime( 6672): Shutting down VM    
  2. W/dalvikvm( 6672): threadid=1: thread exiting with uncaught exception (group=0x40018560)    
  3. E/AndroidRuntime( 6672): FATAL EXCEPTION: main    
  4. E/AndroidRuntime( 6672): java.lang.IllegalStateException: Timer was canceled    
  5. E/AndroidRuntime( 6672):    at java.util.Timer.scheduleImpl(Timer.java:563)    
  6. E/AndroidRuntime( 6672):    at java.util.Timer.schedule(Timer.java:483)    
  7. E/AndroidRuntime( 6672):    at com.snowdream.timerdemo.TimerDemoActivity$2.onClick(TimerDemoActivity.java:73)    
  8. E/AndroidRuntime( 6672):    at android.view.View.performClick(View.java:2501)    
  9. E/AndroidRuntime( 6672):    at android.view.View$PerformClick.run(View.java:9107)    
  10. E/AndroidRuntime( 6672):    at android.os.Handler.handleCallback(Handler.java:587)    
  11. E/AndroidRuntime( 6672):    at android.os.Handler.dispatchMessage(Handler.java:92)    
  12. E/AndroidRuntime( 6672):    at android.os.Looper.loop(Looper.java:130)    
  13. E/AndroidRuntime( 6672):    at android.app.ActivityThread.main(ActivityThread.java:3835)    
  14. E/AndroidRuntime( 6672):    at java.lang.reflect.Method.invokeNative(Native Method)    
  15. E/AndroidRuntime( 6672):    at java.lang.reflect.Method.invoke(Method.java:507)    
  16. E/AndroidRuntime( 6672):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:841)    
  17. E/AndroidRuntime( 6672):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:599)    
  18. E/AndroidRuntime( 6672):    at dalvik.system.NativeStart.main(Native Method)    
  19. W/ActivityManager(  154):   Force finishing activity com.snowdream.timerdemo/.TimerDemoActivity    
  20. W/ActivityManager(  154): Activity pause timeout for HistoryRecord{40550560 com.snowdream.timerdemo/.TimerDemoActivity}    
  21. W/ActivityManager(  154): Activity destroy timeout for HistoryRecord{40550560 com.snowdream.timerdemo/.TimerDemoActivity}    
  22. D/dalvikvm(  800): GC_EXPLICIT freed 13K, 58% free 3127K/7431K, external 0K/0K, paused 70ms    
  23. D/dalvikvm(  562): GC_EXPLICIT freed 59K, 51% free 2935K/5959K, external 245K/512K, paused 84ms    
  24. I/ActivityManager(  154): Start proc com.android.email for service com.android.email/.service.MailService: pid=6691 uid=10019 gids={3003, 1015}    
2、只能在UI主線程中更新控件/組件。在其他線程中,更新控件/組件,會提示出錯,提示如下: 
(注:這種情況下,可以通過Hander發送消息的方式來更新控件/組件,詳情參考例子。)
  1. E/AndroidRuntime( 6309): android.view.ViewRoot$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.    
  2. E/AndroidRuntime( 6309):    at android.view.ViewRoot.checkThread(ViewRoot.java:2941)    
  3. E/AndroidRuntime( 6309):    at android.view.ViewRoot.invalidateChild(ViewRoot.java:643)    
  4. E/AndroidRuntime( 6309):    at android.view.ViewRoot.invalidateChildInParent(ViewRoot.java:669)    
  5. E/AndroidRuntime( 6309):    at android.view.ViewGroup.invalidateChild(ViewGroup.java:2511)    
  6. E/AndroidRuntime( 6309):    at android.view.View.invalidate(View.java:5296)    
  7. E/AndroidRuntime( 6309):    at android.widget.TextView.checkForRelayout(TextView.java:5533)    
  8. E/AndroidRuntime( 6309):    at android.widget.TextView.setText(TextView.java:2730)    
  9. E/AndroidRuntime( 6309):    at android.widget.TextView.setText(TextView.java:2598)    
  10. E/AndroidRuntime( 6309):    at android.widget.TextView.setText(TextView.java:2573)    
  11. E/AndroidRuntime( 6309):    at com.snowdream.timerdemo.TimerDemoActivity$1.run(TimerDemoActivity.java:48)    
  12. E/AndroidRuntime( 6309):    at java.util.Timer$TimerImpl.run(Timer.java:284)    

Demo源碼如下:TimerDemoActivity.java
  1. package com.snowdream.timerdemo;  
  2.   
  3. import java.util.Timer;    
  4. import java.util.TimerTask;    
  5. import android.app.Activity;    
  6. import android.os.Bundle;    
  7. import android.os.Handler;    
  8. import android.os.Message;    
  9. import android.util.Log;    
  10. import android.view.View;    
  11. import android.widget.Button;    
  12. import android.widget.TextView;    
  13.   
  14.   
  15. public class TimerDemoActivity extends Activity {    
  16.     private static String  TAG = "TimerDemo";    
  17.     private TextView mTextView = null;    
  18.     private Button mButton_start = null;    
  19.     private Button mButton_pause = null;    
  20.     private Timer mTimer = null;    
  21.     private TimerTask mTimerTask = null;    
  22.     private Handler mHandler = null;    
  23.     private static int count = 0;    
  24.     private boolean isPause = false;    
  25.     private boolean isStop = true;    
  26.     private static int delay = 1000;  //1s    
  27.     private static int period = 1000;  //1s    
  28.     private static final int UPDATE_TEXTVIEW = 0;    
  29.         
  30.     @Override    
  31.     public void onCreate(Bundle savedInstanceState) {    
  32.         super.onCreate(savedInstanceState);    
  33.         setContentView(R.layout.main);    
  34.         mTextView = (TextView)findViewById(R.id.mytextview);     
  35.         mButton_start = (Button)findViewById(R.id.mybutton_start);    
  36.         mButton_pause = (Button)findViewById(R.id.mybutton_pause);    
  37.   
  38.   
  39.         mButton_start.setOnClickListener(new Button.OnClickListener() {    
  40.             public void onClick(View v) {    
  41.                 if (isStop) {    
  42.                     Log.i(TAG, "Start");    
  43.                 } else {    
  44.                     Log.i(TAG, "Stop");    
  45.                 }    
  46.     
  47.                 isStop = !isStop;    
  48.     
  49.                 if (!isStop) {    
  50.                     startTimer();    
  51.                 }else {    
  52.                     stopTimer();    
  53.                 }    
  54.     
  55.                 if (isStop) {    
  56.                     mButton_start.setText(R.string.start);    
  57.                 } else {    
  58.                     mButton_start.setText(R.string.stop);    
  59.                 }    
  60.             }    
  61.         });    
  62.     
  63.         mButton_pause.setOnClickListener(new Button.OnClickListener() {    
  64.             public void onClick(View v) {    
  65.                 if (isPause) {    
  66.                     Log.i(TAG, "Resume");    
  67.                 } else {    
  68.                     Log.i(TAG, "Pause");    
  69.                 }    
  70.     
  71.                 isPause = !isPause;    
  72.     
  73.                 if (isPause) {    
  74.                     mButton_pause.setText(R.string.resume);    
  75.                 } else {    
  76.                     mButton_pause.setText(R.string.pause);    
  77.                 }    
  78.             }    
  79.         });    
  80.             
  81.         mHandler = new Handler(){    
  82.             @Override    
  83.             public void handleMessage(Message msg) {    
  84.                 switch (msg.what) {    
  85.                 case UPDATE_TEXTVIEW:    
  86.                     updateTextView();    
  87.                     break;    
  88.                 default:    
  89.                     break;    
  90.                 }    
  91.             }    
  92.         };    
  93.     }    
  94.     
  95.     private void updateTextView(){    
  96.         mTextView.setText(String.valueOf(count));    
  97.     }    
  98.     
  99.     private void startTimer(){    
  100.         if (mTimer == null) {    
  101.             mTimer = new Timer();    
  102.         }    
  103.     
  104.         if (mTimerTask == null) {    
  105.             mTimerTask = new TimerTask() {    
  106.                 @Override    
  107.                 public void run() {    
  108.                     Log.i(TAG, "count: "+String.valueOf(count));    
  109.                     sendMessage(UPDATE_TEXTVIEW);    
  110.                         
  111.                     do {    
  112.                         try {    
  113.                             Log.i(TAG, "sleep(1000)...");    
  114.                             Thread.sleep(1000);    
  115.                         } catch (InterruptedException e) {    
  116.                         }       
  117.                     } while (isPause);    
  118.                         
  119.                     count ++;      
  120.                 }    
  121.             };    
  122.         }    
  123.     
  124.         if(mTimer != null && mTimerTask != null )    
  125.             mTimer.schedule(mTimerTask, delay, period);    
  126.     
  127.     }    
  128.     
  129.     private void stopTimer(){    
  130.         if (mTimer != null) {    
  131.             mTimer.cancel();    
  132.             mTimer = null;    
  133.         }    
  134.         if (mTimerTask != null) {    
  135.             mTimerTask.cancel();    
  136.             mTimerTask = null;    
  137.         }       
  138.         count = 0;    
  139.     }    
  140.         
  141.     public void sendMessage(int id){    
  142.         if (mHandler != null) {    
  143.             Message message = Message.obtain(mHandler, id);       
  144.             mHandler.sendMessage(message);     
  145.         }    
  146.     }    
  147. }    


layout-main.xml 

  1. <?xml version="1.0" encoding="utf-8"?>    
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    
  3.   android:layout_width="fill_parent"    
  4.   android:layout_height="fill_parent"    
  5.   android:orientation="vertical" >    
  6.   <TextView    
  7.     android:id="@+id/mytextview"    
  8.     android:layout_width="fill_parent"    
  9.     android:layout_height="wrap_content"    
  10.     android:gravity="center"    
  11.     android:text="@string/number" />    
  12.     
  13.   <LinearLayout    
  14.     android:layout_width="fill_parent"    
  15.     android:layout_height="wrap_content"    
  16.     android:gravity="center"    
  17.     android:orientation="horizontal" >    
  18.    
  19.   <Button    
  20.     android:id="@+id/mybutton_start"    
  21.     android:layout_width="wrap_content"    
  22.     android:layout_height="wrap_content"    
  23.     android:text="@string/start" />    
  24.    
  25.   <Button    
  26.     android:id="@+id/mybutton_pause"    
  27.     android:layout_width="wrap_content"    
  28.     android:layout_height="wrap_content"    
  29.     android:text="@string/pause" />    
  30.   </LinearLayout>    
  31. </LinearLayout>    

strings.xml

  1. <?xml version="1.0" encoding="utf-8"?>    
  2. <resources>    
  3.   <string name="app_name">TimerDemo</string>    
  4.   <string name="number">0</string>    
  5.   <string name="start">start</string>    
  6.   <string name="stop">stop</string>    
  7.   <string name="pause">pause</string>    
  8.   <string name="resume">resume</string>    
  9. </resources>    
源碼下載:http://download.csdn.net/detail/yang_hui1986527/3922447
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章