Android 进阶之【chapter-11】 Service
android:enabled=”true” 能否被系统实例化
android:exported=”true” 能否被其他程序访问
工程:RemoteService和RemoteserviceAIDL
一:服务分两种(Service和IntentService,IntentService中的onHandlerInt是默认在一个线程里运行相当于ASYN的doinbackground)
- 1:本地的服务(LocalService)
- 2:远程服务:进程间的服务(比如后台播放音乐)(要在布局文件中加入android:process=”:yangjie.remoteservice”)//里面的名字可以随意,但是必须是小写,和:开头,加了这句代码之后,这个服务就会新开一个进程来运行了
二:服务被杀死的概率
foreground process
visible process
service process //所以说服务还是有很大的概率会被杀死的
background process
empty process
三:服务中onStrartcommand()方法中的返回值
- 1: START_STICKY_COMPATIBILITY 不保证被系统杀死之后,会自动启动
- 2: START_STICKY 服务被杀死后,系统会自动创建并且启动,但不会传输intent对象
- 3: START_NOT_STICKY 服务被杀死后系统不会重写创建和启动
- 4: START_REDELIVER_INTENT 服务被杀死后,系统会重写创建并启动,且会传输最近一次使用的intent
四:本地服务的绑定服务(只有通过绑定才能调用Service中的方法)
定义一个类继承于Binder
在服务中务中声明一个类的对象
定义一个该类的实列,并在onCreate()中实例化
在MainActivity中创建ServiceConnection接口,在Onserviceconnnected中调用服务
绑定服务
startService(new Intent(this, LocalService. class)); //只有startService才能启动onStartCommand()方法以及它的子类方法onHandleIntent();
bindService(new Intent(this, LocalService.class),coon ,BIND_AUTO_CREATE);//绑定服务
package com.example.yangjie.service;
import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
public class LocalService extends Service {
private LocalBinder mBinder=null;
public LocalService() {
}
@Override
public void onCreate() {
super .onCreate();
//3:在oncreate中实例化这个对象
mBinder =new LocalBinder();
}
@Override
public IBinder onBind(Intent intent) {//绑定服务和Activity绑定在一起
//4:在onBind()方法张返回该对象
return mBinder;
}
//1:定义一个类继承于Binder
public class LocalBinder extends Binder{
//2:在服务中声明一个类的对象
LocalService getService(){
return LocalService.this;
}
}
//要反回的一个字符串
public String getString(){
return "ABC";
}
}
=================================================
private ServiceConnection coon=new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
//服务连接成功调用次方法
//强制类型转换
LocalService.LocalBinder binder=(LocalService.LocalBinder)service;
LocalService ser=binder.getService();
String str=ser.getString();
Toast.makeText(MainActivity. this,str,Toast. LENGTH_SHORT).show();
}
@Override
public void onServiceDisconnected(ComponentName name) {
//断开连接成功调用次方法
}
};
五:远程服务的绑定以及回调(这个非常重要)
1:Messenger (Messenger代码是少于AIDL但功能却不如AIDL)
2:AIDL(只有AIDL才可以通过回调从Service传数据回Activity)Service代码
package com.example.yangjie.remoteserviceaidl;
import android.app.Notification;
import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.os.RemoteException;
import android.support.v7.app.NotificationCompat;
public class RemodeService extends Service {
private IRemoteCallback mcallback ;
@Override
public void onCreate() {
super .onCreate();
Notification notification=null;
NotificationCompat.Builder builder=new NotificationCompat.Builder(this);
builder.setSmallIcon(R.mipmap.ic_launcher);
builder.setContentTitle("计步器");
builder.setContentText("当前步数:0");
notification=builder.build();
startForeground(1 ,notification);//将服务转变为前台进程,这样就不容易被系统回收
}
public RemodeService() {
}
@Override
public IBinder onBind(Intent intent) {
return binder;
}
/**
* 第二步:实现AIDL文件同名Stub
*/
private IRemodeService.Stub binder=new IRemodeService.Stub() {
@Override
public void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat, double aDouble, String aString) throws RemoteException {
}
@Override
public boolean date(String content) throws RemoteException {
if("看电影".equals(content)){
//调用回调接口的方法,相当于反向调用Activity的方法
if(mcallback!=null){
mcallback.invite( "唱歌");
}
return false;
}else if("吃饭".equals(content)){
return true;
}
return false;
}
@Override
public void registcallback(IRemoteCallback callback) throws RemoteException {
mcallback=callback;
}
@Override
public void unregistcallback(IRemoteCallback callback) throws RemoteException {
mcallback=null;
}
@Override
public String getReuslt(String text) throws RemoteException {
if("a".equals(text)){
return "今天是个艳阳天" ;
}
return null;
}
@Override
public int add(int a, int b) throws RemoteException {
return addInt(a,b);
}
};
public int addInt(int a ,int b){
return a+b;
}
}
Activity代码
package com.example.yangjie.remoteserviceaidl;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.IBinder;
import android.os.RemoteException;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity {
private TextView mshow ,mfilm ,mfood ;
private IRemodeService iRemodeService;
private final static String LOG_TAG="MainActivity";
@Override
protected void onCreate(Bundle savedInstanceState) {
super .onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mshow =(TextView)findViewById(R.id.activity_main_btn_show);
mfilm =(TextView)findViewById(R.id.activity_main_btn_film);
mfood =(TextView)findViewById(R.id.activity_main_btn_food);
findViewById(R.id.activity_main_btn_start).setOnClickListener( new View.OnClickListener() {
@Override
public void onClick(View v) {
int a=519;
int b=1;
try {
int total= iRemodeService.add(a,b);
mshow.setText("两个数的和为:"+total+iRemodeService .getReuslt("a"));
} catch (RemoteException e) {
e.printStackTrace();
}
}
});
}
public void setOnclick(View view){
switch (view.getId()){
case R.id.activity_main_btn_film:
try {
boolean result=iRemodeService.date( "看电影");
if(result){
Toast. makeText(MainActivity.this,"女神和我去看电影",Toast.LENGTH_SHORT ).show();
}
} catch (RemoteException e) {
e.printStackTrace();
}
break;
case R.id.activity_main_btn_food:
try {
boolean result=iRemodeService.date( "吃饭");
if(result){
Toast. makeText(MainActivity.this,"女神和我去吃饭",Toast.LENGTH_SHORT ).show();
}
} catch (RemoteException e) {
e.printStackTrace();
}
break;
}
}
@Override
protected void onStart() {
super .onStart();
//绑定服务
Intent intent= new Intent( this,RemodeService. class);
bindService(intent,coon,BIND_AUTO_CREATE);
}
@Override
protected void onStop() {
super .onStop();
unbindService(coon);
}
private ServiceConnection coon =new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
iRemodeService=IRemodeService.Stub.asInterface(service);
try {
iRemodeService.registcallback( iRemoteCallback);
} catch (RemoteException e) {
e.printStackTrace();
}
}
@Override
public void onServiceDisconnected(ComponentName name) {
iRemodeService=null;
}
};
private IRemoteCallback iRemoteCallback =new IRemoteCallback.Stub() {
@Override
public void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat, double aDouble, String aString) throws RemoteException {
}
@Override
public void invite(String content) throws RemoteException {
//Toast.makeText(MainActivity.this,"女神邀请我去"+content,Toast.LENGTH_LONG).show();
Log.v(LOG_TAG ,"--------------->女神邀请我去" +content);
}
};
}
aidl代码
package com.example.yangjie.remoteserviceaidl;
import com.example.yangjie.remoteserviceaidl.IRemoteCallback;
interface IRemodeService {
void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,
double aDouble, String aString);
//第一步:定义要的函数
int add(int a,int b);
String getReuslt(String text);
boolean date(String content);
//注册回调方法
void registcallback(IRemoteCallback callback);
//解除回调方法
void unregistcallback(IRemoteCallback callback);
}
回调时的代码
package com.example.yangjie.remoteserviceaidl;
interface IRemoteCallback {
void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,
double aDouble, String aString);
void invite(String content);
}