第六天.AndroidService

优质
小牛编辑
127浏览
2023-12-01

第六天.AndroidService

6.1Service概述

6.1.1 Service概念及用途

服务是运行在后台的一段代码。 不是进程,也不是线程。 可以运行在它自己的进程,也可以运行在其他应用程序进程的上下文(context)里面,这取决于自身的需要。 Android中的服务,它与Activity不同,它是不能与用户交互的,不能自己启动的,运行在后台的程序。 媒体播放器的服务,当用户退出媒体选择用户界面,仍然希望音乐依然可以继续播放,这就是由服务(service)来保证当用户界面关闭时音乐继续播放的。 比如当我们一个应用的数据是通过网络获取的,不同时间的数据是不同的,这时候我们可以用Service在后台定时更新,而不用每打开应用的时候在去获取。

6.2 Service生命周期

  • onCreate() 在服务被创建时调用,该方法只会被调用一次,无论调用多少次startService()或bindService()方法,服务也只被创建一次。
  • onStart() 只有采用Context.startService()方法启动服务时才会回调该方法。该方法在服务开始运行时被调用。多次调用startService()方法尽管不会多次创建服务,但onStart() 方法会被多次调用。
  • onDestroy() 服务被终止时调用。
  • onBind() 只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务绑定时被调用,当调用者与服务已经绑定,多次调用Context.bindService()方法并不会导致该方法被多次调用。
  • onUnbind() 只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务解除绑定时被调用。 startService后,即使调用startService的进程结束了Service仍然还存在,直到有进程调用stopService,或者Service自己自杀(stopSelf())。 bindService后,Service就和调用bindService的进程同生共死了,也就是说当调用bindService的进程死了,那么它bind的Service也要跟着被结束,当然期间也可以调用unbindservice让Service结束。 两种方式混合使用时,比如说你startService了,我bindService了,那么只有你stopService了而且我也unbindservice了,这个Service才会被结束。

6.3启动与停止Service

6.3.1 Service开发步骤

第一步:继承Service类

public class MyService extends Service { 
}

第二步:在AndroidManifest.xml文件中的节点里对服务进行配置:

服务不能自己运行,使用startService()方法启用服务,调用者与服务之间没有关连,即使调用者退出了,服务仍然运行。使用bindService()方法启用服务,调用者与服务绑定在了一起,调用者一旦退出,服务也就终止,大有“不求同时生,必须同时死”的特点。 如果打算采用Context.startService()方法启动服务,在服务未被创建时,系统会先调用服务的onCreate()方法,接着调用onStart()方法。如果调用startService()方法前服务已经被创建,多次调用startService()方法并不会导致多次创建服务,但会导致多次调用onStart()方法。采用startService()方法启动的服务,只能调用Context.stopService()方法结束服务,服务结束时会调用onDestroy()方法。 如果打算采用Context.bindService()方法启动服务,在服务未被创建时,系统会先调用服务的onCreate()方法,接着调用onBind()方法。这个时候调用者和服务绑定在一起,调用者退出了,系统就会先调用服务的onUnbind()方法,接着调用onDestroy()方法。如果调用bindService()方法前服务已经被绑定,多次调用bindService()方法并不会导致多次创建服务及绑定(也就是说onCreate()和onBind()方法并不会被多次调用)。如果调用者希望与正在绑定的服务解除绑定,可以调用unbindService()方法,调用该方法也会导致系统调用服务的onUnbind()-->onDestroy()方法。

6.3.2 采用startService()启动服务

采用Context.startService()方法启动服务的代码如下:

public class HelloActivity extends Activity {

    public void onCreate(Bundle savedInstanceState) { 
        ......
        Button button =(Button) this.findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener(){
        public void onClick(View v) {
                Intent intent = new Intent(HelloActivity.this, SMSService.class);
                startService(intent);
        }});        
    }
}

6.3.3 采用bindService()启动服务

采用Context.startService()方法启动服务的代码如下:

public class HelloActivity extends Activity {
     ServiceConnection conn = new ServiceConnection() {
        public void onServiceConnected(ComponentName name, IBinder service) {
        }
        public void onServiceDisconnected(ComponentName name) {
        }
     };
public void onCreate(Bundle savedInstanceState) {  
        Button button =(Button) this.findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener(){
        public void onClick(View v) {
                Intent intent = new Intent(HelloActivity.this, SMSService.class);
                bindService(intent, conn, Context.BIND_AUTO_CREATE);
                //unbindService(conn);//解除绑定
        }});        
    }
}

6.3.4 Service服务演示

  1. 新建一个Android工程ServiceDemo
  2. 修改main.xml代码,增加二个按钮
  3. 新建一个Service,命名为MyService.java
  4. 新建ServiceDemo.java
  5. 配置AndroidManifest.xml
  6. 执行上述工程, 用Logcat查看日志
  7. 按HOME键进入Settings(设置)àApplications(应用)àRunningServices(正在运行的服务)

main.xml

<?xml version="1.0" encoding="utf-8"?>   
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent">  
    <TextView   
        android:id="@+id/text"     
        android:layout_width="fill_parent"    
        android:layout_height="wrap_content"    
        android:text="@string/hello" />   
    <Button   
        android:id="@+id/startservice"  
        android:layout_width="fill_parent"  
        android:layout_height="wrap_content"  
        android:text="startService"  />
<Button   
        android:id="@+id/stopservice"  
        android:layout_width="fill_parent"  
        android:layout_height="wrap_content"  
        android:text="stopService"  />    
</LinearLayout>

MyService.java

public class MyService extends Service {   
    //定义个一个Tag标签   
    private static final String TAG = "MyService";   
    //一个Binder类,用在onBind() 方法里,这样Activity那边可以获取到   
    private MyBinder mBinder = new MyBinder();     
    public IBinder onBind(Intent intent) {   
        Log.e(TAG, "start IBinder~~~");   
        return mBinder;   
    }      
    public void onCreate() {   
        Log.e(TAG, "start onCreate~~~");   
        super.onCreate();   
    }    
    public void onStart(Intent intent, int startId) {   
        Log.e(TAG, "start onStart~~~");   
        super.onStart(intent, startId);    
    }
public void onDestroy() {   
        Log.e(TAG, "start onDestroy~~~");   
        super.onDestroy();   
    }        
    public boolean onUnbind(Intent intent) {   
        Log.e(TAG, "start onUnbind~~~");   
        return super.onUnbind(intent);   
    }      
    public String getSystemTime(){           
        Time t = new Time();   
        t.setToNow();   
        return t.toString();   
    }        
    public class MyBinder extends Binder{   
        MyService getService()   
        {   
            return MyService.this;   
        }   
    } }

ServiceDemo.java

public class ServiceDemo extends Activity implements OnClickListener {      
    private MyService  mMyService;   
    private TextView mTextView;   
    private Button startServiceButton;   
    private Button stopServiceButton;   

    private Context mContext;

    public void onCreate(Bundle savedInstanceState) {   
        super.onCreate(savedInstanceState);   
        setContentView(R.layout.main);   
        setupViews();   
    }
public void setupViews(){          
        mContext = ServiceDemo.this;   
        mTextView = (TextView)findViewById(R.id.text);        

        startServiceButton = (Button)findViewById(R.id.startservice);   
        stopServiceButton = (Button)findViewById(R.id.stopservice);   

        startServiceButton.setOnClickListener(this);   
        stopServiceButton.setOnClickListener(this);   

    }
public void onClick(View v) {         
        if(v == startServiceButton){   
            Intent i  = new Intent();   
            i.setClass(ServiceDemo.this, MyService.class);   
            mContext.startService(i);   
        }else if(v == stopServiceButton){   
            Intent i  = new Intent();   
            i.setClass(ServiceDemo.this, MyService.class);   
            mContext.stopService(i);   
        }
  }        
}

AndroidManifest.xml

<manifest xmlns:android="http://schemas.android.com/apk/res/android"  
      package="com.lxt008"  
      android:versionCode="1"  
      android:versionName="1.0">   
    <application android:icon="@drawable/icon" android:label="@string/app_name">   
        <activity android:name=".ServiceDemo"  
                  android:label="@string/app_name">   
            <intent-filter>   
                <action android:name="android.intent.action.MAIN" />   
                <category android:name="android.intent.category.LAUNCHER" />   
            </intent-filter>   
        </activity>   
        <service android:name=".MyService" android:exported="true"></service>   
    </application>   
    <uses-sdk android:minSdkVersion="7" />   
</manifest>

6.4Notification通知

如果需要查看消息,可以拖动状态栏到屏幕下方即可查看消息。 发送消息的代码如下:

//获取通知管理器
NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
int icon = android.R.drawable.stat_notify_chat;
long when = System.currentTimeMillis();
//新建一个通知,指定其图标和标题
//第一个参数为图标,第二个参数为标题,第三个为通知时间
Notification notification = new Notification(icon, null, when);

Intent openintent = new Intent(this, OtherActivity.class);
//当点击消息时就会向系统发送openintent意图
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, openintent, 0);
notification.setLatestEventInfo(this, “标题”, “我是内容", contentIntent);
mNotificationManager.notify(0, notification);

6.4.1 Android中的通知(Notification)

6.5案例分析

参考案例:NotificationDemo

源代码下载