Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> Android開發實例 >> Android Framework系列之IPC(一)

Android Framework系列之IPC(一)

編輯:Android開發實例

說到Android的IPC(Inter-Process Conmmunication)首先想到的就是Handler和Looper,Handler用於多進程之間的通信和數據交換,將各進程之間通信的數據Message放置到Message Queue裡,而Looper用於創建各進程自身的message queue,然後在適當的時候分發給相應的進程。

 

我們知道在Android中,每一個UI線程是一個主線程(Main Thread),Android為每一個主線程維護一個Message Queue,當用戶需要長時間的背景線程操作的時候,需要create自己的new thread,這樣的new thread是沒有自己的message queue的,只能共享主線程的message queue並且將所做的運算結果和數據通過Handler發送到主線程的message queue裡,被主線程共享。

 

  1. <?xml version="1.0" encoding="utf-8"?> 
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
  3.     android:orientation="vertical" 
  4.     android:layout_width="fill_parent" 
  5.     android:layout_height="fill_parent" 
  6.     > 
  7.  
  8.     <ProgressBar   
  9.         android:id="@+id/ProgressBar01"   
  10.         android:layout_width="150dip" 
  11.         android:layout_height="wrap_content" 
  12.         style="?android:attr/progressBarStyleHorizontal"> 
  13.     </ProgressBar> 
  14.       
  15. </LinearLayout> 

 這個xml文件創建了一個progressbar,並且將style設置成水平,

style="?android:attr/progressBarStyleHorizontal

 

  1. <?xml version="1.0" encoding="utf-8"?> 
  2. <manifest xmlns:android="http://schemas.android.com/apk/res/android" 
  3.       package="waterlife.ipc.demo" 
  4.       android:versionCode="1" 
  5.       android:versionName="1.0"> 
  6.     <application android:icon="@drawable/icon" android:label="@string/app_name"> 
  7.         <activity android:name=".IPCConmunication" 
  8.                   android:label="@string/app_name"> 
  9.             <intent-filter> 
  10.                 <action android:name="android.intent.action.MAIN" /> 
  11.                 <category android:name="android.intent.category.LAUNCHER" /> 
  12.             </intent-filter> 
  13.         </activity> 
  14.  
  15.     </application> 
  16.     <uses-permission android:name="android.permission.INTERNET" /> 
  17.  
  18. </manifest>  

為了訪問網絡,需要在manifest file裡設置access internet的permission,

    <uses-permission android:name="android.permission.INTERNET" />

 

  1. package waterlife.ipc.demo;  
  2.  
  3. import java.io.InputStream;  
  4. import java.net.MalformedURLException;  
  5. import java.net.URL;  
  6. import java.net.URLConnection;  
  7. import android.app.Activity;  
  8. import android.os.Bundle;  
  9. import android.os.Handler;  
  10. import android.os.HandlerThread;  
  11. import android.os.Looper;  
  12. import android.os.Message;  
  13. import android.widget.ProgressBar;  
  14.  
  15.  
  16. public class IPCConmunication extends Activity {  
  17.     static ProgressBar pb;  
  18.     final int UPDATE_PROGRESS_BAR = 1000;  
  19.     /** Called when the activity is first created. */ 
  20.     @Override 
  21.     public void onCreate(Bundle savedInstanceState) {  
  22.         super.onCreate(savedInstanceState);  
  23.         setContentView(R.layout.main);  
  24.         pb = (ProgressBar)findViewById(R.id.ProgressBar01);  
  25.         Download dl = new Download();  
  26.         new Thread(dl).start();  
  27.           
  28.     }  
  29.  
  30.  
  31.     Handler mHandle = new Handler()  
  32.     {  
  33.        public void handleMessage(Message msg)  
  34.         {  
  35.             switch(msg.what)  
  36.             {  
  37.                 case UPDATE_PROGRESS_BAR:  
  38.                     pb.setProgress(msg.arg1);  
  39.                     break;  
  40.                 default:  
  41.                     break;  
  42.             }  
  43.         }  
  44.     };  
  45.  
  46.     class Download implements Runnable  
  47.     {  
  48.  
  49.         @Override 
  50.         public void run() {  
  51.             int totalSize = 0;  
  52.             InputStream recevier = null;  
  53.  
  54.              try {  
  55.                 URL myUrl = new URL("http://bbs.nju.edu.cn");  
  56.  
  57.                 URLConnection urlConn = myUrl.openConnection();  
  58.                 totalSize = urlConn.getContentLength();  
  59.                 recevier = urlConn.getInputStream();  
  60.                 byte[] b =new byte[256];  
  61.                 int length = 0;  
  62.                 length += recevier.read(b);  
  63.                 while(length < totalSize)  
  64.                 {  
  65.                     Message msg = mHandle.obtainMessage(UPDATE_PROGRESS_BAR);  
  66.                     msg.arg1 = (int)(length*100/totalSize);  
  67.                     if(mHandle.hasMessages(UPDATE_PROGRESS_BAR))  
  68.                     {  
  69.                         mHandle.removeMessages(UPDATE_PROGRESS_BAR);  
  70.                     }  
  71.                     mHandle.sendMessage(msg);  
  72.                     length += recevier.read(b);  
  73.                     Thread.sleep(1000);  //睡眠1S,這個方法是不值得推薦的,因為它會使線程獨占CPU,在以後的例子會使用更加有效的方法  
  74.                 }  
  75.                 recevier.close();  
  76.             } catch (MalformedURLException e) {  
  77.                 // TODO Auto-generated catch block  
  78.                 e.printStackTrace();  
  79.             }catch (Exception ex)  
  80.             {  
  81.                 ex.printStackTrace();  
  82.             }      
  83.         }  
  84.     }  

我們create出來的一個new thread,用這個線程去網絡上下載數據包,並且把下載的進度更新到UI主線程的progressbar上。兩個線程之間的通信是用Handler來傳遞的。在這裡新的線程Download和UI main thread共用message queue。

 

當然,我們可以為自己新建的線程設置自身的message queue,方法如下:

 

  1. package waterlife.ipc.demo;  
  2.  
  3. import java.io.InputStream;  
  4. import java.net.MalformedURLException;  
  5. import java.net.URL;  
  6. import java.net.URLConnection;  
  7. import android.app.Activity;  
  8. import android.os.Bundle;  
  9. import android.os.Handler;  
  10. import android.os.HandlerThread;  
  11. import android.os.Looper;  
  12. import android.os.Message;  
  13. import android.widget.ProgressBar;  
  14.  
  15.  
  16. public class IPCConmunication extends Activity {  
  17.     static ProgressBar pb;  
  18.     final int UPDATE_PROGRESS_BAR = 1000;  
  19.     /** Called when the activity is first created. */ 
  20.     @Override 
  21.     public void onCreate(Bundle savedInstanceState) {  
  22.         super.onCreate(savedInstanceState);  
  23.         setContentView(R.layout.main);  
  24.         pb = (ProgressBar)findViewById(R.id.ProgressBar01);  
  25.         Download dl = new Download();  
  26.         new Thread(dl).start();  
  27.           
  28.     }  
  29.  
  30.  
  31.     class Download implements Runnable  
  32.     {  
  33.  
  34.         @Override 
  35.         public void run() {  
  36.             int totalSize = 0;  
  37.             InputStream recevier = null;  
  38.  
  39.             HandlerThread threadLoop = new HandlerThread("Download");  
  40.             threadLoop.start();  
  41.             Looper mLooper = threadLoop.getLooper();  
  42.             Handler mHandle = new Handler(mLooper)  
  43.             {  
  44.                 public void handleMessage(Message msg)  
  45.                 {  
  46.                     switch(msg.what)  
  47.                     {  
  48.                         case UPDATE_PROGRESS_BAR:  
  49.                             pb.setProgress(msg.arg1);  
  50.                             break;  
  51.                         default:  
  52.                             break;  
  53.                     }  
  54.                 }  
  55.             };  
  56.    
  57.             try {  
  58.                 URL myUrl = new URL("http://bbs.nju.edu.cn");  
  59.  
  60.                 URLConnection urlConn = myUrl.openConnection();  
  61.                 totalSize = urlConn.getContentLength();  
  62.                 recevier = urlConn.getInputStream();  
  63.                 byte[] b =new byte[256];  
  64.                 int length = 0;  
  65.                 length += recevier.read(b);  
  66.                 while(length < totalSize)  
  67.                 {  
  68.                     Message msg = mHandle.obtainMessage(UPDATE_PROGRESS_BAR);  
  69.                     msg.arg1 = (int)(length*100/totalSize);  
  70.                     if(mHandle.hasMessages(UPDATE_PROGRESS_BAR))  
  71.                     {  
  72.                         mHandle.removeMessages(UPDATE_PROGRESS_BAR);  
  73.                     }  
  74.                     mHandle.sendMessage(msg);  
  75.                     length += recevier.read(b);  
  76.                     Thread.sleep(1000);  
  77.                 }  
  78.                 recevier.close();  
  79.             } catch (MalformedURLException e) {  
  80.                 // TODO Auto-generated catch block  
  81.                 e.printStackTrace();  
  82.             }catch (Exception ex)  
  83.             {  
  84.                 ex.printStackTrace();  
  85.             }      
  86.         }  
  87.     }  

HandlerThread是一個專門用於新建Looper的線程類,它實現了Looper.prepare()和Looper.loop()的方法。HandlerThread ceate一個新的Looper並且綁定到新線程的Handler上,實現了對新線程創建自己的Message queue的目的。

  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved