MicroKibaco / CrazyDailyQuestion

每日一问: 水滴石穿,聚沙成塔,坚持数月, 必有收获~
35 stars 1 forks source link

2019-09-09 :Service和Activity是如何通信的? #32

Open gys0000 opened 5 years ago

TrampcR commented 5 years ago

1、通过 Binder 对象

Activity 调用 bindService(Intent service, ServiceConnection conn,int flags),Service 的 onBind() 方法会返回一个 Binder 对象,Activity 在 onServiceConnected() 中获取到该 Binder 对象实例,通过得到的这个对象实例可以访问 Service 中的方法。

2、通过 Broadcast

在 Activity 中注册 BroadcastReceiver,Service 中有状态发生变化时可以发送 Broadcast,Activity 中注册的 BroadcastReceiver 接收到 Broadcast 之后可以做相应的逻辑。如果有 Service 要向多个 Activity 发送同样的消息的情况,用这种方法就更好。

chinwetang commented 5 years ago

进程间通讯(IPC)的常用方法:

文件共享

我们知道不同进程不共享内存,但是磁盘是可以共享的,所以可以通过文件共享进行通讯,比如SharePreferences

1、 Intent中的Bundle,它实现了Parcelable接口,所以我们常用的Intent就是天然支持跨进程通信的。

2、MessengerHandler,也就是TrampcR提到的bindService(Intent service, ServiceConnection conn,int flags)

3、直接使用AIDL;

4、ContentProvider作为四大组件之一,存在感一直较其它三者弱,我们知道它可以用来获取其它应用的数据,这就是一种事实上的IPC;

Socket

以上内容整理自《Android开发艺术探索》,这本书真的挺不错,第二章【IPC机制】是精华!

gys0000 commented 5 years ago

1.通过Binder进行通信

在service中继承Binder,在onBind方法中返回自己定义的Binder类对象。 这种方式同样可以使用于进程间的通信。

2.通过回调接口进行通信

通过声明接口,然后通过接口回调进行service和activity之间的通信

3.通过EventBus进行简单的通信

使用EventBus框架进行通信

4.Intent

在调用service时,将要传给service的数据放到Intent中传递过去

5.Broadcast广播

通过一个发广播,一个接收广播进行通信

gys0000 commented 5 years ago

进程间通讯(IPC)的常用方法:

文件共享

我们知道不同进程不共享内存,但是磁盘是可以共享的,所以可以通过文件共享进行通讯,比如SharePreferences

  • 优点:操作和原理都很简单;
  • 缺点:数据同步会有问题,SharePreferences甚至还有内存缓存,不推荐使用。

AIDL

AIDL可以说是安卓的一大特色,也是我们最常见最推荐的进程间通讯方法。

1、 Intent中的Bundle,它实现了Parcelable接口,所以我们常用的Intent就是天然支持跨进程通信的。

  • 优点:操作简单;
  • 缺点:支持的类型有限,要传递的对象必须实现Parcelable/Serializable;

2、MessengerHandler,也就是TrampcR提到的bindService(Intent service, ServiceConnection conn,int flags)

  • 优点:通信非常灵活;
  • 缺点:用起来稍显复杂;

3、直接使用AIDL;

4、ContentProvider作为四大组件之一,存在感一直较其它三者弱,我们知道它可以用来获取其它应用的数据,这就是一种事实上的IPC;

Socket

以上内容整理自《Android开发艺术探索》,这本书真的挺不错,第二章【IPC机制】是精华!

这个稍微有点不对题,这个答案算是进程间的通信部分。😁

pioneerz commented 5 years ago

通过binder机制

1.创建service的binder对象 2.在Activity中创建ServiceConnection对象 3.获取所需的service对象 4.调用service相应的方法

// TODO 1.
class MyBinder extends Binder {
        public MyService getService() {
            return MyService.this;
        }
    }
// TODO 2.
class MyConn implements ServiceConnection {

        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            myService = ((MyService.MyBinder) service).getService();
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {

        }
    }
   // TODO 3.
    Intent intent = new Intent(this, MyService.class);
    bindService(intent, new MyConn(), BIND_AUTO_CREATE);
    // TODO 4.
 myService.println();

通过广播机制

1.在activity创建广播接收者,并注册广播 2.启动service,并发送广播 3.在activity处理该广播

通过回调的方式交互数据

创建一个接口,用于主动去获取数据。