<Android 基础(一)> Service
2016-05-22 20:42
621 查看
介绍
Service(服务)是一个没有用户界面的在后台运行执行耗时操作的应用组件。其他应用组件能够启动Service,并且当用户切换到另外的应用场景,Service将持续在后台运行。另外,一个组件能够绑定到一个service与之交互(IPC机制),例如,一个service可能会处理网络操作,播放音乐,操作文件I/O或者与内容提供者(content provider)交互,所有这些活动都是在后台进行。Service有两种状态,“启动的”和“绑定”。
使用方法
看下关于Service两张比较经典的图简单实例
AndroidManifest.xml<application android:label="@string/app_name" android:icon="@drawable/ic_launcher"> <activity android:name=".MyActivity" 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:enabled="true"/> <!--四大组件都要在AndroidManifest中申明一把 --> </application>
MyActivity.java
public class MyActivity extends Activity implements View.OnClickListener, ServiceConnection { public static String TAG = "MyActivity"; Intent intent; /** * Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); Log.e(TAG, "MyActivity OnCreate"); intent = new Intent(MyActivity.this, MyService.class); findViewById(R.id.bt_startservice).setOnClickListener(this); findViewById(R.id.bt_stopservice).setOnClickListener(this); findViewById(R.id.bt_bindservice).setOnClickListener(this); findViewById(R.id.bt_unbindservice).setOnClickListener(this); } //OnClick事件监听 public void onClick(View view) { Log.e(TAG,"OnClick"); switch (view.getId()) { case R.id.bt_startservice: Log.e(TAG, "start Service"); startService(intent); break; case R.id.bt_stopservice: stopService(intent); break; case R.id.bt_bindservice: bindService(intent, this, Context.BIND_AUTO_CREATE); break; case R.id.bt_unbindservice: unbindService(this); break; } } @Override //binderService成功后回调,带过来的IBinder可用于和Activity通信 public void onServiceConnected(ComponentName componentName, IBinder iBinder) { Log.e(TAG, "onServiceConnected"); } @Override //在服务崩溃或被杀死导致的连接中断时被调用 public void onServiceDisconnected(ComponentName componentName) { Log.e(TAG, "onServiceDisconnected"); } }
MyService.java
public class MyService extends Service { public static String TAG = "MyService"; @Override public void onCreate() { super.onCreate(); Log.e(TAG, "MyService onCreate"); } @Override public int onStartCommand(Intent intent, int flags, int startId) { Log.e(TAG, "onStartCommand"); //用来测试Service是否在后台有运行 /*new Thread(new Runnable() { @Override public void run() { while (true) { try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } Log.e(TAG, "Service is Running ..."); } } }).start();*/ return super.onStartCommand(intent, flags, startId); } @Override public void onDestroy() { super.onDestroy(); Log.e(TAG, "onDestroy"); } @Override public IBinder onBind(Intent intent) { Log.e(TAG, "onBind"); return new Binder();//new一个binder对象通过onServiceConnected回调,方便通信 } @Override public boolean onUnbind(Intent intent) { Log.e(TAG, "onUnbind"); return super.onUnbind(intent); } @Override //onRebind的调用时机和onUnbind的返回值有关系 public void onRebind(Intent intent) { Log.e(TAG, "onRebind"); super.onRebind(intent); } }
测试结果
启动服务,停止服务绑定服务,解绑服务
启动服务,绑定服务,解绑服务
注意:这里最后Service是没有onDestory的
启动服务,绑定服务,解绑服务,停止服务
5. Binder使用,这个很关键
MyService.java中修改
public IBinder onBind(Intent intent) { Log.e(TAG, "onBind"); return new MyBinder(); } class MyBinder extends Binder { public void sayHello() { Log.e(TAG,"I am a binder, hi"); } }
MyActivity.java中修改
public void onServiceConnected(ComponentName componentName, IBinder iBinder) { Log.e(TAG, "onServiceConnected"); MyService.MyBinder binder = (MyService.MyBinder) iBinder; ((MyService.MyBinder) iBinder).sayHello(); }
然后执行:绑定服务,解绑服务
通过这个Binder,再加上Callback,可以实现对Service内部状态的监听
先定义一个接口,然后创建get与set,在onBinder方法中定义一个线程不停的发送数据
public interface Callback() { public void onDateChanged(String data) { } } public void setCallback(Callback callback) { this.callback = callback; } public Callback getCallback() { return callback; }
public IBinder onBind(Intent intent) { Log.e(TAG, "onBind"); running = true;//running通过service的生命周期控制 new Thread(new Runnable() { @Override public void run() { while (running) { try { Thread.sleep(1000); i++; String str = "send: " + i ; callback.onDateChanged(str); } catch (InterruptedException e) { e.printStackTrace(); } Log.e(TAG, "Service is Running ... "); } } }).start(); return new MyBinder(); }
然后在MyBinder类中定义一个getService方法
public MyService getSetvice() { return MyService.this; }
然后在onServiceConnected中
public void onServiceConnected(ComponentName componentName, IBinder iBinder) { Log.e(TAG, "onServiceConnected"); MyService.MyBinder binder = (MyService.MyBinder) iBinder; MyService myservice = binder.getService(); myservice.setCallback(new MyService.Callback() { @Override public void onDateChanged(String str) {//非UI线程无法直接更新UI,需要通过handler机制 Message msg = new Message(); msg.arg1 = 1; Bundle bundle = new Bundle(); bundle.putString("data", str); msg.setData(bundle); handler.sendMessage(msg); } }); }
通过这种方式就可以实现Service和Activity的通信工作,不难看出,Binder在其中起着非常重要的角色。
Android中进程间通信,从JAVA到C++基本上都是用Binder来实现的,上层使用的AIDL下一篇介绍一下,
这个系列只关注基础内容,希望可以坚持下来。
相关文章推荐
- java/android 设计模式学习笔记(4)---抽象工厂模式
- Android Dynamic Action(动态Action)—像访问网页一样地访问Activity
- 如何“优雅”地给你的类命名
- onMeasure简单方法 完美解决ListView与ScollView冲突问题!
- Android 学习资源[转]
- [深入理解Android卷二 全文-第五章]深入理解PowerManagerService
- Android----EdgeEffect类边缘效果的实现
- PorterDuffXfermode实现Android刮刮卡效果
- Android日期时间类,解决其他时间类时间会出现误差的bug
- 【Android】安全退出应用程序
- Android中的线程机制(Handler Looper)(二)
- Android Activity生命周期详讲
- Android中 Matrix类
- Notification的几种用法(API不同)
- 关于Activity与Fragment混用中对于startActivityForResult方法的解析
- android中的线程机制
- 【Android 应用开发】GitHub 优秀的 Android 开源项目
- Android开发之Fragment的生命周期
- 安卓屏幕最大化
- android_socket_switch