1服务可以通过startservice的方法 开启。通过stopservice的方法 停止。
服务有一个特点: 只会一次onCreate()方法一旦被创建出来,以后oncreate() 就不会再被执行了,
以后再去开启服务 只会执行onstart()方法,当服务被停止的时候 onDestroy();
2 服务通过bindservice的方法开启
首先 如果服务不存在 就会执行 oncreate() ->onbind()方法
一旦服务绑定成功 以后再去执行 bindsercie() 就不会在重新创建 或者绑定服务了();
如果我们现实的调用unbindservice()的方法 ,首先 on unbind()方法 -> ondestroy() ;
服务只能被解除绑定一次 多次解除绑定服务 程序会出异常.
开启服务 (startservice)
服务一旦开启与调用者没有任何的关系 , 调用着的activity 即便是退出了 也不会影响
后台的service的运行.
在activity里面 不能去调用服务里面的方法 (因为Service是框架new出来的,activity无法获取到该Service的引用).
通过绑定方式开启服务(bindservice)
服务跟调用者不求同生 ,但求同死.
如果调用者(activity)退出了 那他绑定的服务呢 也会跟着退出.
我们可以在activity里面调用服务里面的方法.
利用 serviceSonnection 接口 返回一个ibinder对象 , 拿着ibinder对象获取到服务里面方法的引用(自定义了一个接口信息) 调用服务里面的方法。
一个应用程序 一个进程里面 定义一个IService 的接口来描述方法
如果我们要调用另外一个进程 服务里面的方法 aidl(android interface defination language)
总结流程:
1.要想访问 一个服务里面的方法 我们需要用到 bindservice();
一 创建一个服务 这个服务里面有一个要被调用的方法.
二 定义一个接口IService , 接口里面的抽象方法 就是去调用service里面的方法。
三 定义一个mybinder对象 extends IBinder对象 实现 我们声明的接口IService, 在onbind
方法里面把mybinder返回回去。
四 在activity里面 通过bindservice的方法开启服务。
五 创建出来一个我们MyConn 实现 ServiceConnection接口 onserviceConnected的方法。
这个方法会有一个参数 这个参数就是 MyBinder的对象。
六 把mybinder强制类型转化成 IServcie。
七 调用IService里面的方法。
范例:开启、停止、绑定、解除绑定、调用服务里面的方法。
1 public interface IService { 2 public void callMethodInService(); 3 }
1 import android.app.Activity; 2 import android.content.ComponentName; 3 import android.content.Context; 4 import android.content.Intent; 5 import android.content.ServiceConnection; 6 import android.os.Bundle; 7 import android.os.IBinder; 8 import android.view.View; 9 import android.view.View.OnClickListener; 10 import android.widget.Button; 11 12 /** 13 * 通过startservice开启服务的生命周期。 14 * 利用bindservice调用服务里面的方法。 15 * @author dr 16 */ 17 public class DemoActivity extends Activity implements OnClickListener { 18 19 Button bt_start, bt_stop; 20 // 绑定服务 解除绑定服务 21 Button bt_bind_service, bt_unbind_service; 22 Button bt_call_service; 23 Intent intent; 24 MyConn conn; 25 IService iService; 26 27 @Override 28 public void onCreate(Bundle savedInstanceState) { 29 super.onCreate(savedInstanceState); 30 setContentView(R.layout.main); 31 32 bt_start = (Button) this.findViewById(R.id.button1); 33 bt_stop = (Button) this.findViewById(R.id.button2); 34 bt_bind_service = (Button) this.findViewById(R.id.button3); 35 bt_unbind_service = (Button) this.findViewById(R.id.button4); 36 bt_call_service = (Button) this.findViewById(R.id.button5); 37 bt_start.setOnClickListener(this); 38 bt_stop.setOnClickListener(this); 39 bt_bind_service.setOnClickListener(this); 40 bt_unbind_service.setOnClickListener(this); 41 bt_call_service.setOnClickListener(this); 42 intent = new Intent(this, MyService.class); 43 conn = new MyConn(); 44 } 45 46 @Override 47 public void onClick(View v) { 48 switch (v.getId()) { 49 case R.id.button1: // 开启服务 50 startService(intent); 51 break; 52 case R.id.button2: // 停止服务 53 stopService(intent); 54 break; 55 case R.id.button3: // 绑定服务 56 bindService(intent, conn, Context.BIND_AUTO_CREATE); 57 break; 58 case R.id.button4: // 解除绑定服务 59 unbindService(conn); 60 break; 61 // 绑定开启 62 case R.id.button5: // 调用服务里面的方法 63 iService.callMethodInService(); 64 break; 65 } 66 } 67 68 private class MyConn implements ServiceConnection { 69 // 绑定一个服务成功的时候 调用 onServiceConnected 70 @Override 71 public void onServiceConnected(ComponentName name, IBinder service) { 72 // 绑定成功后,会返回这个IBinder对象(MyService中的onBind返回的)。 73 iService = (IService) service; 74 } 75 76 @Override 77 public void onServiceDisconnected(ComponentName name) { 78 79 } 80 } 81 82 @Override 83 protected void onDestroy() { 84 unbindService(conn); 85 super.onDestroy(); 86 } 87 88 }
1 import android.app.Service; 2 import android.content.Intent; 3 import android.os.Binder; 4 import android.os.IBinder; 5 6 public class MyService extends Service { 7 8 @Override 9 public IBinder onBind(Intent intent) { 10 System.out.println("on bind"); 11 return new MyBinder(); 12 } 13 14 public class MyBinder extends Binder implements IService { 15 @Override 16 public void callMethodInService() { 17 sayHelloInService(); 18 } 19 } 20 21 /** 22 * 服务里面的一个方法 23 */ 24 public void sayHelloInService() { 25 System.out.println("hello in service"); 26 } 27 28 @Override 29 public boolean onUnbind(Intent intent) { 30 System.out.println("on unbind"); 31 return super.onUnbind(intent); 32 } 33 34 @Override 35 public void onCreate() { 36 System.out.println("oncreate"); 37 super.onCreate(); 38 } 39 40 @Override 41 public void onStart(Intent intent, int startId) { 42 System.out.println("onstart"); 43 44 super.onStart(intent, startId); 45 } 46 47 @Override 48 public void onDestroy() { 49 System.out.println("ondestroy"); 50 super.onDestroy(); 51 } 52 }
2.要想访问一个远程服务里的方法 需要用到aidl;
一 创建一个服务 这个服务里面有一个要被调用的方法.
二 定义一个接口IService , 接口里面的抽象方法 就是去调用service里面的方法。
把.java的后缀名改成aidl 把接口里面定义的访问权限的修饰符都给删除。
三 定义一个mybinder对象 extends IService.Stub, 在onbind方法里面把mybinder返回回去。
四 在activity里面 通过bindservice的方法开启服务。
五 创建出来一个我们MyConn 实现 ServiceConnection接口 onserviceConnected的方法,这个方法会有一个参数 这个参数就是MyBinder的对象。
六 IService = IService.Stub.asInterface(myBinder)。
七 调用IService的方法。
范例:采用aidl访问远程服务里面的方法
1 import android.app.Service; 2 import android.content.Intent; 3 import android.os.IBinder; 4 import android.os.RemoteException; 5 6 /** 7 * 采用aidl访问远程服务里面的方法 --- 远程服务 8 * 调用着是:callremote Project。 9 * @author dr 10 * 11 */ 12 public class RemoteService extends Service { 13 14 @Override 15 public IBinder onBind(Intent intent) { 16 return new MyBinder(); 17 } 18 19 private class MyBinder extends IService.Stub { 20 @Override 21 public void callMethodInService() throws RemoteException { 22 sayHelloInService(); 23 } 24 } 25 26 /** 27 * 服务里面的一个方法 28 */ 29 public void sayHelloInService() { 30 System.out.println("hello in service"); 31 } 32 33 @Override 34 public void onCreate() { 35 System.out.println("remote service oncreate"); 36 super.onCreate(); 37 } 38 39 }
1 // IService.aidl 文件 2 interface IService { 3 void callMethodInService(); 4 }
1 <?xml version="1.0" encoding="utf-8"?> 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android" 3 package="cn.itcast.remoteservice" 4 android:versionCode="1" 5 android:versionName="1.0" > 6 7 <uses-sdk android:minSdkVersion="8" /> 8 9 <application 10 android:icon="@drawable/ic_launcher" 11 android:label="@string/app_name" > 12 <service android:name=".RemoteService" > 13 <intent-filter > 14 <action android:name="cn.itcast.remoteservice"/> 15 </intent-filter> 16 </service> 17 </application> 18 19 </manifest>
1 import cn.itcast.remoteservice.IService; 2 import android.app.Activity; 3 import android.content.ComponentName; 4 import android.content.Intent; 5 import android.content.ServiceConnection; 6 import android.os.Bundle; 7 import android.os.IBinder; 8 import android.os.RemoteException; 9 import android.view.View; 10 11 /** 12 * 采用aidl访问远程服务里面的方法 --- 调用远程服务 13 * 调用着是:remoteservice Project。 14 * @author dr 15 * 16 */ 17 public class DemoActivity extends Activity { 18 IService iService; 19 @Override 20 public void onCreate(Bundle savedInstanceState) { 21 super.onCreate(savedInstanceState); 22 setContentView(R.layout.main); 23 24 Intent intent = new Intent(); 25 intent.setAction("cn.itcast.remoteservice"); 26 bindService(intent, new MyConn(), BIND_AUTO_CREATE); 27 } 28 29 30 public void click(View view){ 31 try { 32 // 调用了远程服务的方法 33 iService.callMethodInService(); 34 } catch (RemoteException e) { 35 // TODO Auto-generated catch block 36 e.printStackTrace(); 37 } 38 } 39 40 private class MyConn implements ServiceConnection{ 41 42 @Override 43 public void onServiceConnected(ComponentName name, IBinder service) { 44 iService = IService.Stub.asInterface(service); 45 } 46 47 @Override 48 public void onServiceDisconnected(ComponentName name) { 49 // TODO Auto-generated method stub 50 } 51 52 } 53 }
1 // 把 远程服务 Demo中的 aidl文件复制过来。包路径要一致。 2 interface IService { 3 void callMethodInService(); 4 }
1 <?xml version="1.0" encoding="utf-8"?> 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android" 3 package="cn.itcast.remoteservice" 4 android:versionCode="1" 5 android:versionName="1.0" > 6 7 <uses-sdk android:minSdkVersion="8" /> 8 9 <application 10 android:icon="@drawable/ic_launcher" 11 android:label="@string/app_name" > 12 <service android:name=".RemoteService" > 13 <intent-filter > 14 <action android:name="cn.itcast.remoteservice"/> 15 </intent-filter> 16 </service> 17 </application> 18 19 </manifest>
范例:采用aidl挂断电话
1 import java.lang.reflect.Method; 2 import com.android.internal.telephony.ITelephony; 3 import android.app.Activity; 4 import android.os.Bundle; 5 import android.os.IBinder; 6 import android.os.RemoteException; 7 import android.view.View; 8 9 /** 10 * 采用aidl挂断电话 11 * @author dr 12 */ 13 public class DemoActivity extends Activity { 14 ITelephony iTelephony; 15 16 /** Called when the activity is first created. */ 17 @Override 18 public void onCreate(Bundle savedInstanceState) { 19 super.onCreate(savedInstanceState); 20 setContentView(R.layout.main); 21 22 try { 23 // 获取系统电话管理的服务 24 Method method = Class.forName("android.os.ServiceManager") 25 .getMethod("getService", String.class); 26 IBinder binder = (IBinder) method.invoke(null, 27 new Object[] { TELEPHONY_SERVICE }); 28 iTelephony = ITelephony.Stub.asInterface(binder); 29 } catch (Exception e) { 30 e.printStackTrace(); 31 } 32 } 33 34 public void endcall(View view) { 35 try { 36 iTelephony.call("123"); 37 } catch (RemoteException e) { 38 e.printStackTrace(); 39 } 40 // iTelephony.call("123"); 41 } 42 }
1 /* //device/java/android/android/content/Intent.aidl 2 ** 3 ** Copyright 2007, The Android Open Source Project 4 ** 5 ** Licensed under the Apache License, Version 2.0 (the "License"); 6 ** you may not use this file except in compliance with the License. 7 ** You may obtain a copy of the License at 8 ** 9 ** http://www.apache.org/licenses/LICENSE-2.0 10 ** 11 ** Unless required by applicable law or agreed to in writing, software 12 ** distributed under the License is distributed on an "AS IS" BASIS, 13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 ** See the License for the specific language governing permissions and 15 ** limitations under the License. 16 */ 17 18 // NeighboringCellInfo.aidl 19 package android.telephony; 20 21 parcelable NeighboringCellInfo;
1 <uses-permission android:name="android.permission.CALL_PHONE" />