android 学习随笔十八(广播与服务 )

来源:互联网 发布:小型交易网站源码 编辑:程序博客网 时间:2024/05/18 14:22
1、广播接收者注册

  • 清单文件注册(Android四大组件都要在清单文件中注册

 一旦应用部署,广播接收者就生效了,直到用户手动停止应用或者应用被删除

  • 广播接收者可以使用代码注册

 需要广播接收者运行时,使用代码注册,不需要时,可以使用代码解除注册
 特殊广播接收者,必须代码注册。电量改变、屏幕开关,必须使用代码注册

2、注册广播接收者

//创建广播接收者对象
receiver = new ScreenOnOffReceiver();
//通过IntentFilter对象指定广播接收者接收什么类型的广播
IntentFilter filter = new IntentFilter();
filter.addAction(Intent.ACTION_SCREEN_OFF);
filter.addAction(Intent.ACTION_SCREEN_ON);

//注册广播接收者
registerReceiver(receiver, filter);
* 解除注册广播接收者

unregisterReceiver(receiver);
* 解除注册之后,广播接收者将失去作用

 1 package com.itheima.register; 2  3 import android.content.BroadcastReceiver; 4 import android.content.Context; 5 import android.content.Intent; 6  7 public class ScreenOnOFFReceiver extends BroadcastReceiver { 8  9     @Override10     public void onReceive(Context context, Intent intent) {11         12         String action = intent.getAction();13         if(Intent.ACTION_SCREEN_ON.equals(action)){14             System.out.println("屏幕开啦啦");15         }16         else if(Intent.ACTION_SCREEN_OFF.equals(action)){17             System.out.println("屏幕关哇哇");18         }19 20     }21 22 }
View Code
 1 package com.itheima.register; 2  3 import android.app.Service; 4 import android.content.Intent; 5 import android.content.IntentFilter; 6 import android.os.IBinder; 7  8 public class RegisterService extends Service { 9 10     private ScreenOnOFFReceiver receiver;11 12     @Override13     public IBinder onBind(Intent intent) {14         // TODO Auto-generated method stub15         return null;16     }17 18     @Override19     public void onCreate() {20         super.onCreate();21         //1.创建广播接收者对象22         receiver = new ScreenOnOFFReceiver();23         //2.创建意图过滤器对象24         IntentFilter filter = new IntentFilter();25         //指定接收什么广播26         filter.addAction(Intent.ACTION_SCREEN_OFF);27         filter.addAction(Intent.ACTION_SCREEN_ON);28         //3.注册广播接收者29         registerReceiver(receiver, filter);30         31     }32     33     @Override34     public void onDestroy() {35         super.onDestroy();36         //反注册广播接收者37         unregisterReceiver(receiver);38     }39     40 }
View Code
 1 package com.itheima.register; 2  3 import android.os.Bundle; 4 import android.app.Activity; 5 import android.content.Intent; 6 import android.view.Menu; 7 import android.view.View; 8  9 public class MainActivity extends Activity {10 11     @Override12     protected void onCreate(Bundle savedInstanceState) {13         super.onCreate(savedInstanceState);14         setContentView(R.layout.activity_main);15     }16 17 18     public void start(View v){19         Intent intent = new Intent(this, RegisterService.class);20         startService(intent);21     }22     public void stop(View v){23         Intent intent = new Intent(this, RegisterService.class);24         stopService(intent);25     }26     27 }
View Code

 服务注册广播

3、服务的分类

  • 本地服务:服务和启动它的组件在同一个进程
  • 远程服务:服务和启动它的组件不在同一个进程
  • 远程服务只能隐式启动,类似隐式启动Activity,在清单文件中配置Service标签时,必须配置intent-filter子节点,并指定action子节点

远程服务

 1 package com.itheima.remoteservice; 2  3 import com.itheima.remoteservice.PublicBusiness.Stub; 4  5 import android.app.Service; 6 import android.content.Intent; 7 import android.os.Binder; 8 import android.os.IBinder; 9 10 public class RemoteService extends Service{11 12     @Override13     public IBinder onBind(Intent intent) {14         System.out.println("绑定");15         return new FengMiShu();16     }17 18     class FengMiShu extends Stub{19 20         @Override21         public void qianXian() {22             // TODO Auto-generated method stub23             remoteBanZheng();24         }25         26     }27     28     @Override29     public boolean onUnbind(Intent intent) {30         System.out.println("解绑");31         return super.onUnbind(intent);32     }33     34     @Override35     public void onCreate() {36         System.out.println("创建");37         super.onCreate();38     }39     40     @Override41     public int onStartCommand(Intent intent, int flags, int startId) {42         System.out.println("开始");43         return super.onStartCommand(intent, flags, startId);44     }45     46     @Override47     public void onDestroy() {48         System.out.println("摧毁");49         super.onDestroy();50     }51     52     public void remoteBanZheng(){53         System.out.println("苗领导在国外远程办证");54     }55 56 }
View Code
 1 package com.itheima.remoteservice; 2  3 import android.os.Bundle; 4 import android.app.Activity; 5 import android.view.Menu; 6  7 public class MainActivity extends Activity { 8  9     @Override10     protected void onCreate(Bundle savedInstanceState) {11         super.onCreate(savedInstanceState);12         setContentView(R.layout.activity_main);13     }14 15 16     @Override17     public boolean onCreateOptionsMenu(Menu menu) {18         // Inflate the menu; this adds items to the action bar if it is present.19         getMenuInflater().inflate(R.menu.main, menu);20         return true;21     }22     23 }
View Code
 1 <?xml version="1.0" encoding="utf-8"?> 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android" 3     package="com.itheima.remoteservice" 4     android:versionCode="1" 5     android:versionName="1.0" > 6  7     <uses-sdk 8         android:minSdkVersion="8" 9         android:targetSdkVersion="17" />10 11     <application12         android:allowBackup="true"13         android:icon="@drawable/ic_launcher"14         android:label="@string/app_name"15         android:theme="@style/AppTheme" >16         <activity17             android:name="com.itheima.remoteservice.MainActivity"18             android:label="@string/app_name" >19             <intent-filter>20                 <action android:name="android.intent.action.MAIN" />21 22                 <category android:name="android.intent.category.LAUNCHER" />23             </intent-filter>24         </activity>25         <service android:name="com.itheima.remoteservice.RemoteService">26             <intent-filter >27                 <action android:name="com.itheima.remote"/>28             </intent-filter>29         </service>30     </application>31 32 </manifest>
View Code

调用远程服务操作

package com.itheima.runremoteservice;public interface PublicBusiness {    void qianXian();}
 1 package com.itheima.runremoteservice; 2  3 import android.os.Bundle; 4 import android.os.IBinder; 5 import android.app.Activity; 6 import android.content.ComponentName; 7 import android.content.Intent; 8 import android.content.ServiceConnection; 9 import android.view.Menu;10 import android.view.View;11 12 public class MainActivity extends Activity {13 14     public PublicBusiness pb;15     private MyConn conn;16 17     @Override18     protected void onCreate(Bundle savedInstanceState) {19         super.onCreate(savedInstanceState);20         setContentView(R.layout.activity_main);21         22         conn = new MyConn();23     }24 25 26     public void start(View v){27         Intent intent = new Intent();28         intent.setAction("com.itheima.remote");29         startService(intent);30     }31     public void stop(View v){32         Intent intent = new Intent();33         intent.setAction("com.itheima.remote");34         stopService(intent);35     }36     public void bind(View v){37         Intent intent = new Intent();38         intent.setAction("com.itheima.remote");39         bindService(intent, conn, BIND_AUTO_CREATE);40     }41     42     public void unbind(View v){43         unbindService(conn);44     }45     class MyConn implements ServiceConnection{46 47         @Override48         public void onServiceConnected(ComponentName name, IBinder service) {49             pb = (PublicBusiness) service;50             51         }52 53         @Override54         public void onServiceDisconnected(ComponentName name) {55             // TODO Auto-generated method stub56             57         }58         59     }60     61     public void banZheng(View v){62         pb.qianXian();63     }64 }
View Code

 

4、AIDL  Android interface definition language,在Android中用于进程间通讯

* 安卓接口定义语言
* 作用:跨进程通信
* 应用场景:远程服务中的中间人对象,其他应用是拿不到的,那么在通过绑定服务获取中间人对象时,就无法强制转换,使用aidl,就可以在其他应用中拿到中间人类所实现的接口

步骤

远程服务
1. 把接口文件的后缀名改成aidl(在gen目录下会根据aidl文件生成一个.java文件)
2. aidl文件中所有东西都是public的,不需要也不能自己定义访问修饰符
3. 中间人对象继承Stub,这个对象已经继承了Binder并实现了PublicBusiness接口(自定义接口)

启动调用远程服务
1. 把远程服务项目的aidl文件复制到启动调用远程服务项目(先创建一个和服务aidl所在包相同的包名),然后aidl所在的包名远程服务启动调用远程服务项目必须一致(在gen目录下会根据aidl文件生成一个.java文件)
2. 把启动调用远程服务项目获取到的中间人对象使用Stub.asInterface强转

public void onServiceConnected(ComponentName name, IBinder service) {
pb = Stub.asInterface(service);
}

 例:

  • 支付宝远程服务

1. 定义支付宝的服务,在服务中定义pay方法
2. 定义中间人对象,把pay方法抽取成接口
3. 把抽取出来的接口后缀名改成aidl
4. 中间人对象直接继承Stub对象
5. 注册这个支付宝服务,定义它的intent-Filter

  • 需要支付的应用

1. 把刚才定义好的aidl文件拷贝过来,注意aidl文件所在的包名必须跟原包名一致
2. 远程绑定支付宝的服务,通过onServiceConnected方法我们可以拿到中间人对象
3. 把中间人对象通过Stub.asInterface方法强转成定义了pay方法的接口
4. 调用中间人的pay方法

 1 package com.itheima.paybaby; 2  3 import com.itheima.paybaby.PayInterface.Stub; 4  5 import android.app.Service; 6 import android.content.Intent; 7 import android.os.IBinder; 8 import android.os.RemoteException; 9 10 public class PayService extends Service {11 12     @Override13     public IBinder onBind(Intent intent) {14         // TODO Auto-generated method stub15         return new PayController();16     }17 18     class PayController extends Stub{19 20         @Override21         public void pay() throws RemoteException {22             PayService.this.pay();23             24         }25         26     }27     28     private void pay() {29         System.out.println("检查支付环境");30         System.out.println("加密账号密码");31         System.out.println("上传账号密码");32         System.out.println("完成支付");33 34     }35 }
View Code
 1 package com.itheima.paybaby; 2  3 import android.os.Bundle; 4 import android.app.Activity; 5 import android.view.Menu; 6  7 public class MainActivity extends Activity { 8  9     @Override10     protected void onCreate(Bundle savedInstanceState) {11         super.onCreate(savedInstanceState);12         setContentView(R.layout.activity_main);13     }14 15 16     @Override17     public boolean onCreateOptionsMenu(Menu menu) {18         // Inflate the menu; this adds items to the action bar if it is present.19         getMenuInflater().inflate(R.menu.main, menu);20         return true;21     }22     23 }
View Code

调用

 1 package com.itheima.naocangame; 2  3 import com.itheima.paybaby.PayInterface; 4 import com.itheima.paybaby.PayInterface.Stub; 5  6 import android.os.Bundle; 7 import android.os.IBinder; 8 import android.os.RemoteException; 9 import android.app.Activity;10 import android.content.ComponentName;11 import android.content.Intent;12 import android.content.ServiceConnection;13 import android.view.Menu;14 import android.view.View;15 16 public class MainActivity extends Activity {17 18     PayInterface pi;19     @Override20     protected void onCreate(Bundle savedInstanceState) {21         super.onCreate(savedInstanceState);22         setContentView(R.layout.activity_main);23         24         //绑定远程服务25         Intent intent = new Intent("com.itheima.babypay");26         bindService(intent, new ServiceConnection() {27             28             @Override29             public void onServiceDisconnected(ComponentName name) {30                 // TODO Auto-generated method stub31                 32             }33             34             @Override35             public void onServiceConnected(ComponentName name, IBinder service) {36                 pi = Stub.asInterface(service);37                 38             }39         }, BIND_AUTO_CREATE);40         41     }42 43 44     public void click(View v){45         try {46             pi.pay();47         } catch (RemoteException e) {48             // TODO Auto-generated catch block49             e.printStackTrace();50         }51     }52     53 }
View Code

 5、进程优先级

  • 五种前台进程

1. activity执行了onresume方法,获得焦点
2. 拥有一个跟正在与用户交互的activity绑定的服务
3. 拥有一个服务执行了startForeground()方法
4. 拥有一个正在执行onCreate()、onStart()或者onDestroy()方法中的任意一个的服务
5. 拥有一个正在执行onReceive方法的广播接收者

  • 两种可见进程

1. activity执行了onPause方法,失去焦点,但是可见
2. 拥有一个跟可见或前台activity绑定的服务

0 0
原创粉丝点击