和你一起终身学习,这里是程序员 Android

本篇文章主要介绍 Android 开发中的部分知识点,通过阅读本篇文章,您将收获以下内容:

一、Service 简介

二、Service 的注册

三、Service 的启动模式

四、Service的生命周期

五、启动模式使用举例

六、bind 服务介绍

七、bind 服务举例

八、服务的优先级

一、Service 简介

首先我们先了解一下Service的继承关系,方便我们更好的了解Service。 Service继承关系如下:

java.lang.Object

↳android.content.Context

↳android.content.ContextWrapper

↳android.app.Service

Service 是Android四大组件之一(Activity 活动,Service 服务,ContentProvider内容提供者,BroadcastReceiver 广播),与Activity相比,Service是运行在后台,无用户界面,用户无法看到,Activity则是运行在前台,用户可以看得见。

Service主要用于组件之间交互(例如:与Activity、ContentProvider、BroadcastReceiver进行交互)、执行后台任务等(例如下载文件,播放音乐等)。

注意:Service在主线程运行时长不能超过20s,否则会出现ANR,耗时操作一般建议在子线程或工作线程中进行操作。

二、Service 的注册

Service 是四大组件之一,必现在AndroidMainfest.xml中注册。

Service注册方法如下:

...

...

注意:

Service如不注册 ,不会像Activity那样会导致App Crash,Service 不注册 不会报异常信息,但是服务会起不来,如不注意很容易迷惑。

三、Service 的启动模式

Service启动模式主要分两种: 1. 启动模式。 2. 绑定模式。

1.启动模式

此模式通过 startService()方法启动,此服务可以在后台一直运行,不会随启动组件的消亡而消亡。

但是,此种启动模式只能执行单一操作,并且无法返回结果给调用方,主要常用于网络下载、上传文件,播放音乐等。

2.绑定模式

此模式通过绑定组件(Activity等)调用 bindService() 启动,此服务随绑定组件的消亡而解除绑定。

如果此时没有其它通过startService()启动,则此服务会随绑定组件的消亡而消亡。

多个组件不仅可以同时绑定一个Service,而且可以通过进程间通信(IPC)执行跨进程操作等。

两种服务可以同时运行

启动模式与绑定模式的服务可以同时运行,在销毁服务时,只有两种模式都不在使用Service时候,才可以销毁服务,否则会引起异常。

四、Service的生命周期

Service 有两种不同的启动模式 ,不同的启动模式对应不同生命周期。两种不同 Service模式的生命周期如下:

AAffA0nNPuCLAAAAAElFTkSuQmCC

五、启动模式使用举例

通过启动模式启动的Service,如不主动关闭,Service会一直在。

1.启动模式启动服务的方法

Intent mBindIntent = new Intent(ServiceMethods.this, BindServiceMethods.class);

startService(mStartIntent);

2.启动模式启动服务的生命周期

下面是验证启动模式启动服务的生命周期的方法,详细生命周期请查看上方Service的生命周期图。

01-03 17:16:36.147 23789-23789/com.android.program.programandroid I/StartService wjwj:: ----onCreate----

01-03 17:16:36.223 23789-23789/com.android.program.programandroid I/StartService wjwj:: ----onStartCommand----

01-03 17:16:38.174 23789-23789/com.android.program.programandroid I/StartService wjwj:: ----onDestroy----

3.启动模式 启动服务案例

此案例功能:启动服务,在服务中创建通知

// Service 创建方法

@Override

public void onCreate() {

super.onCreate();

Log.i(TAG, "----onCreate----");

}

// Service 启动方法

@Override

public int onStartCommand(Intent intent, int flags, int startId) {

Log.i(TAG, "----onStartCommand----");

// 获取NotificationManager实例

notifyManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);

// 实例化NotificationCompat.Builder并设置相关属性

NotificationCompat.Builder builder = new NotificationCompat.Builder(

this)

// 设置小图标

.setSmallIcon(R.drawable.ic_launcher)

.setLargeIcon(

BitmapFactory.decodeResource(getResources(),

R.drawable.ic_launcher))

// 设置通知标题

.setContentTitle("我是通过StartService服务启动的通知")

// 设置通知不能自动取消

.setAutoCancel(false).setOngoing(true)

// 设置通知时间,默认为系统发出通知的时间,通常不用设置

// .setWhen(System.currentTimeMillis())

// 设置通知内容

.setContentText("请使用StopService 方法停止服务");

// 通过builder.build()方法生成Notification对象,并发送通知,id=1

notifyManager.notify(1, builder.build());

return super.onStartCommand(intent, flags, startId);

}

// Service 销毁方法

@Override

public void onDestroy() {

Log.i(TAG, "----onDestroy----");

notifyManager.cancelAll();

super.onDestroy();

}

#六、 绑定服务介绍

绑定模式启动的服务会随着绑定逐渐的消亡而解除Service绑定,如果此时Service没有通过启动模式启动,则此服务将会被销毁。

1.启动绑定模式服务的方法

绑定模式,是通过其他组件调用bindService()方法启动的Service。

// 启动绑定服务处理方法

public void BtnStartBindService(View view) {

// 启动绑定服务处理方法

bindService(mBindIntent, serviceConnection, Context.BIND_AUTO_CREATE);

isBindService = true;

Toast.makeText(ServiceMethod.this, "启动 " + mBindCount + " 次绑定服务",

Toast.LENGTH_SHORT).show();

}

public void BtnSopBindService(View view) {

if (isBindService) {

// 解除绑定服务处理方法

unbindService(serviceConnection);

Toast.makeText(ServiceMethod.this, "解除 " + mUnBindCount + " 次绑定服务",

Toast.LENGTH_SHORT).show();

isBindService = false;

}

}

2.绑定服务 随绑定组件的消亡而消亡

如果绑定服务的组件被destory,这 bind 服务会走到onUnbind()方法。

##3. 绑定模式 生命周期回调代码如下:

// Service 创建方法

@Override

public void onCreate() {

super.onCreate();

Log.i(TAG, "----onCreate----");

}

// Service 绑定方法

@Override

public IBinder onBind(Intent intent) {

Log.i(TAG, "----onBind----");

MyBinder myBinder = new MyBinder();

return myBinder;

}

// Service 解除绑定方法

@Override

public boolean onUnbind(Intent intent) {

Log.i(TAG, "----onUnbind----");

return super.onUnbind(intent);

}

// Service 销毁方法

@Override

public void onDestroy() {

Log.i(TAG, "----onDestroy----");

super.onDestroy();

}

绑定服务的生命周期代码打印Log信息如下:

01-03 20:32:59.422 13306-13306/com.android.program.programandroid I/BindService wjwj:: ----onCreate----

01-03 20:32:59.423 13306-13306/com.android.program.programandroid I/BindService wjwj:: -----onBind-----

01-03 20:33:09.265 13306-13306/com.android.program.programandroid I/BindService wjwj:: ----onUnbind----

01-03 20:33:09.266 13306-13306/com.android.program.programandroid I/BindService wjwj:: ----onDestroy----

#七、bind 服务举例

功能:

获取绑定模式启动 绑定服务及解除绑定服务的次数

##1.绑定服务类

package com.android.program.programandroid.component.Service;

import android.app.Service;

import android.content.Intent;

import android.os.IBinder;

import android.util.Log;

public class BindServiceMethods extends Service {

private static final String TAG = "BindService wjwj:";

public BindServiceMethods() {

}

@Override

public void onCreate() {

super.onCreate();

Log.i(TAG, "----onCreate----");

}

@Override

public IBinder onBind(Intent intent) {

Log.i(TAG, "----onBind----");

MyBinder myBinder = new MyBinder();

return myBinder;

}

@Override

public boolean onUnbind(Intent intent) {

Log.i(TAG, "----onUnbind----");

return super.onUnbind(intent);

}

@Override

public void onDestroy() {

Log.i(TAG, "----onDestroy----");

super.onDestroy();

}

}

2.组件与绑定服务类之间的交互

// 启动绑定服务处理方法

public void BtnStartBindService(View view) {

bindService(mBindIntent, serviceConnection, Context.BIND_AUTO_CREATE);

isBindService = true;

Toast.makeText(ServiceMethods.this,"启动 "+mBindCount+" 次绑定服务",Toast.LENGTH_SHORT).show();

}

// 解除绑定服务处理方法

public void BtnSopBindService(View view) {

if (isBindService) {

unbindService(serviceConnection);

Toast.makeText(ServiceMethods.this,"解除 "+mUnBindCount+" 次绑定服务",Toast.LENGTH_SHORT).show();

isBindService=false;

}

}

3.组件之间交互所需的 Binder 接口类

/**

* 该类提供 绑定组件与绑定服务提供接口

* */

public class MyBinder extends Binder {

private int count = 0;

public int getBindCount() {

return ++count;

}

public int getUnBindCount() {

return count> 0 ? count-- : 0;

}

}

#八、服务的优先级

服务默认启动方式是后台服务,但是可以通过设置服务为前台服务,提高服务的优先级,进而避免手机内存紧张时,服务进程被杀掉。

设置服务优先级的方法如下:

1.设置为前台服务

//设置为前台服务

startForeground(int, Notification)

2.取消前台服务

//取消为前台服务

stopForeground(true);

##3.startForeground 前台服务案例

功能:前台服务绑定通知信息,提高服务进程优先级,否则取消通知信息

package com.android.program.programandroid.component.Service;

import android.app.NotificationManager;

import android.app.Service;

import android.content.Intent;

import android.graphics.BitmapFactory;

import android.os.IBinder;

import android.support.v4.app.NotificationCompat;

import com.android.program.programandroid.R;

public class MyStartForcegroundService extends Service {

public MyStartForcegroundService() {

}

@Override

public IBinder onBind(Intent intent) {

// TODO: Return the communication channel to the service.

throw new UnsupportedOperationException("Not yet implemented");

}

@Override

public void onCreate() {

super.onCreate();

}

@Override

public int onStartCommand(Intent intent, int flags, int startId) {

if (intent.getAction().equals("start_forceground_service")) {

// 获取NotificationManager实例

NotificationManager notifyManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);

// 实例化NotificationCompat.Builder并设置相关属性

NotificationCompat.Builder builder = new NotificationCompat.Builder(this)

// 设置小图标

.setSmallIcon(R.mipmap.ic_launcher)

.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher))

// 设置通知标题

.setContentTitle("我是通过startForeground 启动前台服务通知")

// 设置通知不能自动取消

.setAutoCancel(false)

.setOngoing(true)

// 设置通知时间,默认为系统发出通知的时间,通常不用设置

// .setWhen(System.currentTimeMillis())

// 设置通知内容

.setContentText("请使用stopForeground 方法改为后台服务");

//通过builder.build()方法生成Notification对象,并发送通知,id=1

// 设置为前台服务

startForeground(1, builder.build());

} else if (intent.getAction().equals("stop_forceground_service")) {

stopForeground(true);

}

return super.onStartCommand(intent, flags, startId);

}

}

至此,本篇已结束。转载网络的文章,小编觉得很优秀,欢迎点击阅读原文,支持原创作者,如有侵权,恳请联系小编删除,欢迎您的建议与指正。同时期待您的关注,感谢您的阅读,谢谢!

Logo

为开发者提供学习成长、分享交流、生态实践、资源工具等服务,帮助开发者快速成长。

更多推荐