免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 2746 | 回复: 0
打印 上一主题 下一主题

Android Service [转] [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2009-11-27 09:29 |只看该作者 |倒序浏览
Android Service Note
1、 概述
每个服务都继承Service基类。
可以连接到(或者bind to)一个正在运行的服务(如果没有在运行则启动它)。当连接成功后,你可以通过服务提供的接口来与它通信。服务通常产生另外的线程来进行占用时间长的任务。
Service是没有用户可见的界面,不与用户交互,而是在后台运行一段不确定的时间的应用程序组件。每个Service class 都必须在AndroidManifest.xml文件中有相应的声明。Service可以通过Context.startService()和Context.bindService()来启动。
注意,与其他程序中的对象一样,Service运行他们的主进程中。这意味着,如果服务要进行消耗CPU或者阻塞的操作,它应该产生新的线程,在新线程里进行这些工作。
2、Service 的生命周期
系统有两种启动Service的方法。如果调用Context.startService(),那么系统将会retrieve这个Service(如果必要则创建它并调用它的onCreate()方法),然后使用客户端传递的参数调用它的onStart(Intent,int)方法。这是Service开始运行直到Context.stopService()或者stopSelf()方法被调用。注意,多次调用Context.startservice()不会嵌套(即使会有相应的onStart()方法被调用),所以无论同一个服务被启动了多少次,一旦调用Context.stopService()或者stopSelf(),他都会被停止。
客户端也可以使用context.bindservice()来得到一个Service的永久链接。这个方法也会在服务没有运行的条件下创建服务(调用onCreate()),但是不调用onStart()。客户端会得到服务的onBind(Intent)方法返回的IBinder对象,用来允许客户端回调服务的方法。只要连接已经建立服务会一直运行下去(无论客户端是否保留服务的IBinder对象的引用)。通常返回的IBinder对象是aidl中定义的复杂接口。
A service can be both started and have connections bound to it.这种情况下,系统会为之Service运行只要它被启动或者有一个或者多个对它的使用Context.BIND_AUTO_CREATE flag的链接。一旦没有着这一个的情况发生,Service的哦呢Destroy()会被调用,Service会被有效的结束。所有的cleanup(停止线程,反注册receiver等)在onDestroy()返回的时候完成。
使用Service的两种方法:
1、It can be started and allowed to run until someone stops it or it stops itself. In this mode, it's started by calling Context.startService() and stopped by calling Context.stopService(). It can stop itself by calling Service.stopSelf() or Service.stopSelfResult(). Only one stopService() call is needed to stop the service, no matter how many times startService() was called.
2、It can be operated programmatically using an interface that it defines and exports. Clients establish a connection to the Service object and use that connection to call into the service. The connection is established by calling Context.bindService(), and is closed by calling Context.unbindService(). Multiple clients can bind to the same service. If the service has not already been launched, bindService() can optionally launch it.
也可以在startService()后bindService()。
你应该实现Service的方法( they are public):
void onCreate()
void onStart(Intent intent)
void onDestroy()
通过实现这些方法,你可以监视Service生命周期中的两个嵌套循环:
1、Service的完全生命时间(entire lifetime)是指从调用onCreate()开始到onDestroy()返回的这段时间。Service在onCreate()中进行初始化,在onDestroy()中释放资源。
2、Service的活动生命时间(active lifetime)从onStart()开始,onStart()会处理从startService()方法传递过来的Intent对象。
Service不存在onStop()方法。
注意:只有通过startService()启动Service才会调用它的onStart()方法,通过onBind()启动的Service不会调用。
The onCreate() and onDestroy() methods are called for all services, whether they're started by Context.startService() or Context.bindService(). However, onStart() is called only for services started by startService().
如果Service运气其他程序bind到它,你需要实现其他的回调方法。
IBinder onBind(Intent intent)
boolean onUnbind(Intent intent)
void onRebind(Intent intent)
传递给bindService()的Intent对象会传递给onBind(),传递给unbindService()的Intent对象会传递给onUnbind()方法。如果这个Service允许连接,onBind()返回客户端和Service交互的通信频道(the communications channel that clients use to interact with the service)。如果有新的客户端链接到Service,onUnbind()方法可以请求调用onRebind()。
3、权限(Permissions)
在manifest 文件中声明的Service可以被全局访问(所有的应用程序都可以访问这个Service)。为了可以访问这个Service,其他的程序需要在他们的manifest文件中声明相应的 来使用启动、停止或者绑定到这个Service。
另外,Service可以通过权限(通过在执行那个调用的实现之前调用checkCallingPermission(String))保护自己的IPC调用。
4、进程生命周期(Process LIfecycle)
Android系统会尽量保持使用Service的进程尽可能长(Service被启动或者有客户端绑定到Service)。当系统内存变低,系统需要kill现存的进程时,Service的hosting进程的优先级将会在下列的可能中保持更高。
If the service is currently executing code in its onCreate(), onStart(), or onDestroy() methods, then the hosting process will be a foreground process to ensure this code can execute without being killed.
If the service has been started, then its hosting process is considered to be less important than any processes that are currently visible to the user on-screen, but more important than any process not visible. Because only a few processes are generally visible to the user, this means that the service should not be killed except in extreme low memory conditions.
If there are clients bound to the service, then the service's hosting process is never less important than the most important client. That is, if one of its clients is visible to the user, then the service itself is considered to be visible.
注意:大多数时间你的Service是运行的,但在严重的内存压力下它也可能被系统kill。如果是这样,系统会在稍后尝试重新启动这个Service。An important consequence of this is that if you implement onStart()  to schedule work to be done asynchronously or in another thread, then you may want to write information about that work into persistent storage during the onStart() call so that it does not get lost if the service later gets killed.
Other application components running in the same process as the service (such as an Activity) can, of course, increase the importance of the overall process beyond just the importance of the service itself.
package test.service;
import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log;
public class MyTestService extends Service {
private static final String TAG = "MyTestService";
@Override
public IBinder onBind(Intent intent) {
// TODO Auto-generated method stub
Log.d(TAG, "onBind(Intent intent) called");
return null;
}
@Override
public void onCreate() {
// TODO Auto-generated method stub
super.onCreate();
Log.d(TAG, "onCreate() called");
}
@Override
public void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
Log.d(TAG, "onDestroy() called");
}
@Override
public void onStart(Intent intent, int startId) {
// TODO Auto-generated method stub
super.onStart(intent, startId);
Log.d(TAG, "onStart(Intent intent, int startId) called");
}
@Override
public boolean onUnbind(Intent intent) {
// TODO Auto-generated method stub
Log.d(TAG, "onUnbind(Intent intent) called");
return super.onUnbind(intent);
}
public class LocalBinder extends Binder {
public MyTestService getService() {
return MyTestService.this;
}
}
}
package test.service;
import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.util.Log;
import android.view.View;
import android.widget.Button;
public class ServiceDemo extends Activity {
private static final String TAG = "ServiceDemo";
private Button mBtnStart, mBtnStop, mBtnBind, mBtnUnbind;
private MyTestService mService;
private boolean isBinded;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mBtnStart = (Button) findViewById(R.id.btnStartService);
mBtnStop = (Button) findViewById(R.id.btnStopService);
mBtnBind = (Button) findViewById(R.id.btnBindService);
mBtnUnbind = (Button) findViewById(R.id.btnUbindService);
mBtnStart.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startService();
}
});
mBtnStop.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
stopService();
}
});
mBtnBind.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
bindService();
}
});
mBtnUnbind.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
unbindService();
}
});
}
private ServiceConnection mServiceConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
mService = ((MyTestService.LocalBinder)(service)).getService();
Log.i(TAG, "in onServiceConnected");
}
@Override
public void onServiceDisconnected(ComponentName name) {
mService = null;
Log.i(TAG, "in onServiceDisconnected");
}
};
private void startService() {
Intent i = new Intent(this, MyTestService.class);
startService(i);
}
private void stopService() {
Intent i = new Intent(this, MyTestService.class);
stopService(i);
}
private void bindService() {
Intent i = new Intent(this, MyTestService.class);
bindService(i, mServiceConnection, Context.BIND_AUTO_CREATE);
isBinded = true;
}
private void unbindService() {
if(isBinded) {
unbindService(mServiceConnection);
isBinded = false;
}
}
}



本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u/20442/showart_2105105.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP