Android菜鸟的成长笔记(18)——绑定本地Service并与之通信
在上一篇中介绍了Service与Activity的区别及Service两种启动方式中的第一种启动方式startService().
我们会发现用startService()、stopService()方法启动和关闭一个Service时,Service与访问者之间基本上不存在太多的关联,因此Service和访问者之间也无法进行通信和数据交换。如果要实现Service与Activity之间的通信就要使用第二种启动方式(绑定启动)bindService()启动、unbindService()关闭。
下面我们来看一下bindService方法的各个参数的含义:(下图是API中关于该方法的说明)
官方说明地址:http://developer.android.com/reference/android/content/Context.html#bindService(android.content.Intent, android.content.ServiceConnection, int)
各个参数的大致含义如下:
service:通过Intent指定要启动的Service.
conn:该参数是一个ServiceConnection对象,该对象用于监听访问者与Service对象的onServiceConnected(ComponentName name, IBinder service)方法:当Service所在的宿主进程由于异常终止或者由其他原因终止,导致该Service与访问者之间断开连接时回调该ServiceConnection对象的onServiceDisconnected(ComponentName name)方法。
private ServiceConnection conn = new ServiceConnection() {
@Override
public void onServiceDisconnected(ComponentName name) {
System.out.println("--Service Disconnected--");
}
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
System.out.println("--Service Connected--");
binder = (MyBinder) service;
}
};
flags:指定绑定时是否自动创建Service.该参数为0则不自动创建,为BIND_AUTO_CREATE(自动创建)
注意:当调用者主动通过nubindService()方法断开与Service的连接时,ServiceConnection对象的onServiceDisconnected(ComponentName name)方法不会被调用。
可以看到上面onServiceConnected方法中有一个IBinder的参数对象,实际上Activity与Service之间的绑定是通过该参数进行绑定和通信的。这时候可能有的朋友就有点迷糊了,这到底是怎样实现通信的呢?
其实,当你在开发一个Service的时候Service类会强制你实现一个方法onBind(Intent intent).在绑定本地(没有跨越进程)Service的情况下,onBind(Intent intent)方法返回的IBinder对象将会传给上面介绍的bindService()方法参数ServiceConnection对象的o中的IBinder.这样访问者就可以通过操作该参数中IBinder对象来实现对Service中数据的读取。
在实际开发中通常会采用继承Binder(IBinder的实现类)的方式实现自己的IBinder对象。
下面我们来实现一个绑定的Service与Activity之间的通信:
(1)建立一个service返回Binder对象
package com.example.testservice; import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder; public class BindService extends Service{ private int count;
private boolean quit;
//定义onBinder方法所返回的对象
private MyBinder binder = new MyBinder();
//通过继承Binder来实现IBinder类
public class MyBinder extends Binder{
public int getCount(){
return count;
}
} @Override
public IBinder onBind(Intent intent) {
System.out.println("Service is Binded");
return binder;
} @Override
public void onCreate() { super.onCreate();
System.out.println("Service is Created");
new Thread(){
public void run() {
while(!quit){
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
count++;
}
};
}.start();
} @Override
public boolean onUnbind(Intent intent) {
System.out.println("Service is UnBinded");
return super.onUnbind(intent);
} @Override
public void onDestroy() {
super.onDestroy();
this.quit = true;
System.out.println("Service is Destroyed");
} }
(2)创建ServiceConnection接口实例对象,并将该对象的实例作为参数传给bindService()方法,通过调用ServiceConnection接口实例中的nServiceConnected方法的参数获得IBinder对象。
package com.example.testservice; import android.app.Activity;
import android.app.Service;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.IBinder;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.Toast; import com.example.testservice.BindService.MyBinder; public class BindServiceTest extends Activity{
Button bind, unbind, getServiceStatus; BindService.MyBinder binder; private ServiceConnection conn = new ServiceConnection() { @Override
public void onServiceDisconnected(ComponentName name) {
System.out.println("--Service Disconnected--");
} @Override
public void onServiceConnected(ComponentName name, IBinder service) {
System.out.println("--Service Connected--");
binder = (MyBinder) service;
}
}; protected void onCreate(android.os.Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main); bind = (Button)findViewById(R.id.button1);
unbind = (Button) findViewById(R.id.button2);
getServiceStatus = (Button) findViewById(R.id.button3); final Intent intent = new Intent(); intent.setAction("com.meritit.service.BIND_SERVICE"); bind.setOnClickListener(new OnClickListener() { @Override
public void onClick(View arg0) {
bindService(intent, conn, Service.BIND_AUTO_CREATE);
}
}); unbind.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) {
unbindService(conn);
}
}); getServiceStatus.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) {
Toast.makeText(BindServiceTest.this, "Service的count值是:" + binder.getCount(),
Toast.LENGTH_SHORT).show();
}
});
};
}
通过该方法Activity可以非常方便的访问到Service的运行状态,这里的IBinder可以看成Service组件所返回的代理对象。
下一篇将介绍:Service的生命周期
Android菜鸟的成长笔记(18)——绑定本地Service并与之通信的更多相关文章
- Android菜鸟的成长笔记(16)——Service简介
Service是Android四大组件之一 1.Service与Activity的区别在:Service一直在后台运行,没有用户界面. 2.选择Activity与Service的标准:如果某个程序组件 ...
- Android菜鸟的成长笔记(19)——Service的生命周期
前面两篇文章介绍了关于Service的两种启动方式,简要总结如下: Context.startService() Context.bindService() 1. startService()的目的是 ...
- Android菜鸟的成长笔记(17)—— 再看Android中的Unbounded Service
原文:Android菜鸟的成长笔记(17)-- 再看Android中的Unbounded Service 前面已经写过关于startService(Unbounded Service)的一篇文章:&l ...
- Android菜鸟的成长笔记(1)——Android开发环境搭建从入门到精通
原文:Android菜鸟的成长笔记(1)--Android开发环境搭建从入门到精通 今天在博客中看到好多Android的初学者对Android的开发环境的搭建不熟悉而导致不能进行学习,所以我决定自己写 ...
- Android菜鸟的成长笔记(7)——什么是Activity
原文:[置顶] Android菜鸟的成长笔记(7)——什么是Activity 前面我们做了一个小例子,在分析代码的时候我们提到了Activity,那么什么是Activity呢? Activity是An ...
- Android菜鸟的成长笔记(3)——给QQ登录界面说So Easy
原文:Android菜鸟的成长笔记(3)--给QQ登录界面说So Easy 上一篇:Android菜鸟的成长笔记(2)--第一个Android应用 我们前面已经做了第一个Android应用程序,虽然有 ...
- Android菜鸟的成长笔记(2)——第一个Android应用
原文:Android菜鸟的成长笔记(2)--第一个Android应用 上一篇:Android菜鸟的成长笔记(1)--Anddroid环境搭建从入门到精通 在上一篇Android菜鸟的成长笔记(1)中我 ...
- Android菜鸟的成长笔记(14)—— Android中的状态保存探究(上)
原文:[置顶] Android菜鸟的成长笔记(14)—— Android中的状态保存探究(上) 我们在用手机的时候可能会发现,即使应用被放到后台再返回到前台数据依然保留(比如说我们正在玩游戏,突然电话 ...
- Android菜鸟的成长笔记(13)——异步任务(Async Task)
原文:[置顶] Android菜鸟的成长笔记(13)——异步任务(Async Task) Android的UI线程主要负责处理用户的事件及图形显示,因此主线程UI不能阻塞,否则会弹出一个ANR(App ...
- Android菜鸟的成长笔记(12)——Handler、Loop、MessageQueue
原文:[置顶] Android菜鸟的成长笔记(12)——Handler.Loop.MessageQueue 当一个程序第一次启动时,Android会启动一条主线程(Main Thread),主线程主要 ...
随机推荐
- Android 关于java.util.NoSuchElementException错误
写了一个从A文件复制到B文件的例子,其中要求去掉重复的行. 于是想到了Set,这本来是很容易的事情,结果在向外写数据时抱错 Java.util.NoSuchElementException 网络上反复 ...
- window.location无法跳转页面的问题
最近在使用 window的location时碰到一个无法跳转页面的问题, 后来在location语句后加了一条这样的语句:window.event.returnValue = false;然后竟然可以 ...
- Mybatis的使用中的一些不太注意的技巧
以下就总结一下Mybatis的使用中的一些不太注意的技巧,算是Mybatis的总结笔 1.插入时主键返回 我们向数据库插入一条记录是,使用Mybatis的<insert>是无法返回插入的主 ...
- [WASM] Call a JavaScript Function from WebAssembly
Using WASM Fiddle, we show how to write a simple number logger function that calls a consoleLog func ...
- IQueryFielter接口
IQueryFilter基于属性查询过滤数据.需要定义一个where子句.可以指定要返回值的字段列表.如果没有指定列,将返回所有值.当需要根据属性值和属性的关系过滤数据时,使用该接口. 成员 AddF ...
- Android Studio SVN使用和VisualSVN-Server配置(图解)
转载请标明出处: http://blog.csdn.net/zq2114522/article/details/51078544: 本文出自:[梁大盛的博客] Android Studio SVN使用 ...
- ng-cli搭建angular项目框架
原文地址 https://www.jianshu.com/p/0a8f4b0f29b3 环境准备 以下步骤都不需要事先创建文件夹,只是环境的准备过程,只有到需要搭建项目的时候才需要创建文件夹用来存放项 ...
- 具体解释https是怎样确保安全的
Https 介绍 什么是Https HTTPS(全称:Hypertext Transfer Protocol over Secure Socket Layer).是以安全为目标的HTTP通道,简单讲是 ...
- [CSS] Draw Simple Icons with CSS
Using pseudo-elements like ::before and ::after we can draw some simple icons without having using i ...
- ios开发网络学八:NSURLSession相关代理方法
#import "ViewController.h" @interface ViewController ()<NSURLSessionDataDelegate> /* ...