一.service的用途 1.1 一種是執行長時間運行的耗時操做 1.如網路下載、音樂播放2.文件系統監控等 1.2 另一種是負責組件間的交互 1.將某些功能以Service組件形式封裝,然後提供給其他組件調用 二.Service的生命周期 Service不能自己啟動,必須由其他應用組件來調用根據調 ...
一.service的用途
1.1 一種是執行長時間運行的耗時操做
1.如網路下載、音樂播放
2.文件系統監控等
1.2 另一種是負責組件間的交互
1.將某些功能以Service組件形式封裝,然後提供給其他組件調用
二.Service的生命周期
Service不能自己啟動,必須由其他應用組件來調用
根據調用方式不同,分為兩種運行模式:
運行模式不同,其生命周期也不同
啟動模式 綁定模式
2.1啟動模式下的service,代碼如下
創建啟動模式運行的Service組件:
創建Service類,繼承android.app.Service類
在Service類中實現onStartCommand等生命周期方法
在AndroidManifest.xml文件中配置Service組件
public class MyFirstService extends Service { @Override public void onCreate() { super.onCreate(); Log.i("First Service","First Service Create"); } //啟動模式下,服務在onStartCommand方法中實現 MediaPlayer mp; @Override public int onStartCommand(Intent intent, int flags, int startId) { Log.i("First Service","First Service Running,"+intent.getStringExtra("message")); if(mp==null) { mp = new MediaPlayer(); } mp.reset(); String path= Environment.getExternalStorageDirectory().getAbsolutePath()+"/nobody.mp3"; try { mp.setDataSource(path); mp.prepare(); mp.start(); } catch (IOException e) { e.printStackTrace(); } return START_NOT_STICKY; } @Override public void onDestroy() { super.onDestroy(); Log.i("First Service","First Service Destroy"); if(mp!=null){ mp.stop(); mp.release(); mp=null; } //Intent intent=new Intent(this,MyFirstService.class); //startService(intent); } @Nullable @Override public IBinder onBind(Intent intent) { return null; } }
<!--配置服務--> <service android:label="Android系統服務" android:enabled="true" android:exported="true" android:name="com.example.service.MyFirstService"/>
主要業務邏輯在onStartCommand方法中實現,該方法的返回值決定了不同的Service運行模式
START_NOT_STICKY:在Service意外被終止後將停止。適用場景:網上下載數據
START_REDELIVER_INTENT:在Service意外被終止後將停止將自動重新運行並保證Intent被處理。適用場景:關鍵業務處理
START_STICKY:確保Service一直保持啟動狀態,但不保證Intent執行。適用場景:後臺播放音樂
2.1.1 IntentService代碼如下
Service組件經常涉及多線程以及同步問題
使用IntentService幫助開發人員解決多線程同步問題
會創建一個工作隊列,每次將一個Intent傳遞到onHandleIntent()方法,無需擔心多線程同步問題。
創建啟動模式運行的IntentService組件:
創建IntentService類,繼承import android.app.IntentService;類
在Service類中重寫MyIntentService方法
在AndroidManifest.xml文件中配置MyIntentService組件
public class MyIntentService extends IntentService { public MyIntentService() { super("MyIntentService"); } public MyIntentService(String name) { super(name); } @Override protected void onHandleIntent(Intent intent) { for(int i=1;i<=100;i++){ Log.i("Intent Service","i="+i); SystemClock.sleep(100); } }
<service
android:name="com.example.service.MyIntentService"/>
2.1綁定模式下的service,代碼如下
創建Service類,繼承android.app.Service類
在Service類中實現一個內部類,它繼承Binder類。併在Service類的onBind()生命方法中返回該內部類對象
在AndroidManifest.xml文件中配置Service組件
public class MyBindService extends Service { /** * 這是一個重點方法,返回調用對象一個Binder對象用來調用已經定義好的服務 * @param intent * @return */ @Nullable @Override public IBinder onBind(Intent intent) { Log.i("MyBindService","MyBindService Bind"); return new MyBinder(); } //定義一個IBinder的實現類,在該類中實現一些具體的服務方法 public class MyBinder extends Binder{ public MediaPlayer mp; public int current=0; public double sum(double n1,double n2){ return n1+n2; } public void playMusic(String path){ if(mp!=null) return; mp=new MediaPlayer(); try { mp.reset(); mp.setDataSource(path); mp.prepare(); mp.start(); new Thread(new Runnable() { @Override public void run() { while (mp!=null&¤t<=mp.getDuration()){ current=mp.getCurrentPosition(); SystemClock.sleep(200); } } }).start(); } catch (IOException e) { e.printStackTrace(); } } public void stopMusic(){ if(mp!=null){ mp.stop(); mp.release(); mp=null; } } } //取消Service組件的綁定 @Override public boolean onUnbind(Intent intent) { Log.i("MyBindService","MyBindService unBind"); return super.onUnbind(intent); } @Override public void onCreate() { super.onCreate(); Log.i("MyBindService","MyBindService Create"); } @Override public void onDestroy() { super.onDestroy(); Log.i("MyBindService","MyBindService Destroy"); }
<service
android:name="com.example.service.MyBindService"/>