向光明而行!
Service的基本概念
Service是Android的四大组件之一,在每一个应用程序中都扮演者非常重要的角色。
它主要用于在后台处理一些耗时的逻辑,或者去执行某些需要长期运行的任务。必要的时候,我们甚至可以在程序退出的情况下,让Service在后台继续保持运行状态。
既然都是被用于处理耗时的操作,那么我们什么时候使用Service,什么时候使用Thread呢?这就涉及到进程与线程之间的关系了,我们进入到下一节。
为什么要有Service
首先我们要知道,当一个应用开启后,并且没有任何其他的组件运行时,Android操作系统就给我们的应用开启了一个新的Linux进程并在里面创建了一个独立的线程。默认的,应用的所有组件都会运行在相同进程和线程(这个线程被称为”main”主线程)中运行。
进程创建后,就有了生命周期。Android操作系统会尽可能长时间的去维系一个应用进程保持运行。当然,如果为了创建一个新的或者更为重要的进程,Android操作系统也会移除旧的进程去释放内存。
根据进程中运行的组件和组件的状态,Andriod系统维护着一个”优先级关系“,来决定哪个进程被保持运行或者被杀死,最不重要的进程最先被杀死。
下面是优先级关系的列表(第一个进程最重要也是最后被杀死)
前台进程(Foreground process) 简单来说,当用户和应用程序交互时就是前台进程,此时会调用Activity的onResume()方法。可视进程 当一个应用程序不可以和用户交互,但是仍然可以被用户看到时就是可是进程,此时会调用Activity的onPause()方法。服务进程 当使用startService()开启一个服务时,这个服务就处于服务进程中。后台进程 当应用的Activity对当前用户都不可见时就是后台进程,此时会调用Activity的onStop()方法。空进程 应用进程中没有任何活动的组件时,就是空进程。当应用中没有服务,并且一直按返回键直到回到桌面时,这个应用就编程了空进程了。
当我们的应用开启了子线程并执行逻辑时,被用户按返回键变成了空进程时。如果有更重要的应用被启动,那么空进程可能会被Android操作系统杀死,我们的子线程中的逻辑也就会被中断,这样逻辑就不安全了。这是这个原因,Android才为我们提供了更稳定的Service方法。
Service的基本用法
Service最基本的用法自然就是如何启动一个Service了,启动Service的方法和启动Activity很类似,都需要借助Intent来实现,下面我们就通过一个具体的例子来看一下。
首先要明确,创建一个简单服务的基本步骤:①写一个类继承Service,并重写其中的onCreate()、onStartCommand()、onDestory()等生命周期方法。其中onBind()方法是服务和Activity通信使用的,后面在讲解。②Service是四大组件之一,需要在清单文件中声明。③使用startService(intent)启动服务和使用stopService(intent)停止服务。
接下来我们就创建一个简单的工程,画一个界面来操作一下。
首先,写一个类继承Service,并重写其中的onCreate()、onStartCommand()、onDestory()等生命周期方法,并在其中打印一些Log。代码如下:
{@Overridepublic IBinder onBind(Intent intent) {return null;}() {super.onCreate();System.out.println(“服务第一次被创建时调用”);}(Intent intent, int flags, int startId) {System.out.println(“服务启动了”);return super.onStartCommand(intent, flags, startId);}() {super.onDestroy();System.out.println(“服务销毁了”);}}
其次,在清单文件中声明服务。
<application… >…></application>
最后,做好以上这些操作后,我们就可以启动服务了。我们通过如下代码来启动和停止服务。
(View v) {// 准备好开启服务的意图Intent service = new Intent(this, MyService.class);// 开启服务startService(service);}(View v) {Intent service = new Intent(this, MyService.class);// 停止服务stopService(service);}
值得说明的是,当启动一个Service的时候,会调用该Service中的onCreate()和onStartCommand()方法。当我们再次点击启动服务按钮时,就只有onStartCommand()方法执行了,onCreate()方法并没有执行。
之所以这样是由于onCreate()方法只会在Service第一次被创建的时候调用,如果当前Service已经被创建过了,不管怎样调用启动服务的方法,onCreate()方法都不会再执行。
而当我们点击停止服务是,onDesctory()方法会被调用。请看一下,调用的测试图。
当我们启动服务后,我们可以在后台查看正在运行的服务。
电话窃听器的小案例
接下来,再通过一个小案例巩固一下服务、TelephonyManager和录音设备的使用。
开发的基本步骤是:①创建PhoneService类并继承Service;在AndroidManifest.xml文件中声明服务。②获取到电话管理服务器(TelephonyManager),,监听电话到来的状态;③判断电话的三种状态(空闲、响铃、接通),并在相应的方法中获取录音设备(MediaRecorder)、配置参数、录制、释放资源;④在应用启动时启动服务,退出时销毁服务。
第一步,创建PhoneService类并继承Service;在AndroidManifest.xml文件中声明服务。请看下面的简略代码;
{@Overridepublic IBinder onBind(Intent intent) {return null;}() {super.onCreate();System.out.println(“服务第一次被创建”);}(Intent intent, int flags, int startId) {System.out.println(“服务启动”);return super.onStartCommand(intent, flags, startId);}() {super.onDestroy();System.out.println(“服务销毁”);}}
在清单文件中声明服务:
>选择自己所爱的,爱自己所选择的。