Android神奇“控件”-----RemoteViews

本篇文章已授权微信公众号 guolin_blog (郭霖)独家发布
转载请注明 http://blog.csdn.net/wrg_20100512/article/details/53940485
  好久没有写博客了,主要是忙着找工作和做毕业设计,没有时间来看一些值得分享的东西。今天写这篇博客是因为我被安排了解下RemoteViews。说实话,这个东西真心没有看过,仅仅看《Android艺术开发探索》的时候知道有这么个“控件”,还记得任主席在群里说过这是他这本书中最自豪的一章,有没有之一我就不清楚啦!话不多说,那就开始Android神奇“控件”之旅吧!

RemoteViews是什么?

先从表层意思理解RemoteViews感觉它是一个view的集合,而且和远程有关系。那事实上它是什么呢?请看官方对它的说明:

这里写图片描述

从说明可以看出,RemoteViews是用来描述一个视图的,它描述的这个视图将显示在另外一个进程中,这也就符合了RemoteViews中Remote这层含义。同时说明里也说了RemoteViews提供了一些基本的操作方法来修改它描述的那个视图的内容。听起来它还真像是个“控件”,那它真的是吗?

看一下RemoteViews的类继承关系:

这里写图片描述

这里写图片描述

从图中发现,RemoteViews与View没有半毛钱的关系,它仅仅就是Object的一个子类,实现了Parcelable接口(这就为RemoteViews能够实现跨进程提供了条件)。所以从严格意义上来说,RemoteViews并不是一个控件,它仅仅是为生成控件和修改控件属性提供一系列的方法。

总结:RemoteViews就是为跨进程生成控件和修改控件属性提供一系列方法的一个类。

说了RemoteViews是什么之后,咱们来看看为什么要用RemoteViews!

为什么要用RemoteViews?

既然RemoteViews是用于跨进程更新UI的,那咱们就来创造这么一个场景:

同一个应用中有两个Activity,这两个Activity分别处在不同的进程中

这里写图片描述       这里写图片描述

            MainActivity                       TempActivity

这里写图片描述

其中MainActivity所属的进程为com.example.bjwangruigang.remoteviewstudy,TempActivity所属的进程为com.example.bjwangruigang.remoteviewstudy:remote。现在需要通过TempActivity来改变MainActivity中的视图,也就是实现跨进程更新UI这么一个功能。具体来说就是在MainActivity中添加两个Button。

传统方式实现跨进程更新UI

拿到这个场景需求,结合跨进程和更新UI的知识,有以下几个方案:

  1. TempActivity把要添加的两个Button的布局的ID值通过BroadcastRecriver发送,在MainActivity中注册该广播,同时获取其中的布局ID值,通过LayoutInflater来绘制那两个Button,最后添加到MainActivity的布局中去。

  2. TempActivity通过AIDL这种方式将要添加的两个Button的布局的ID值发送到AIDLService中,通过Handler来发送消息、处理消息。处理过程同样是通过LayoutInflater来绘制那两个Button,最后添加到MainActivity的布局中去。

其实这两种方案大同小异,无非采用的进程间通信方式不同,后续的添加视图是一模一样的。方案一采用广播的形式来进行IPC通信,而方案二则采用AIDL这种相对原生的IPC方式。为了重温AIDL,这里我采用AIDL 的方式来实现上述效果。

首先建立IViewManager.aidl。

interface IViewManager {
    void setTextViewText(in int id,in String text);//设置TextView的内容
    void addView(in int layoutId);                 //添加View视图
}

rebuild project让IDE工具自己生成AIDL借口对应的java文件。

建立ViewAIDLService文件。

public class ViewAIDLService extends Service {
   
    private static final String TAG = "ViewAIDLService";
    private Binder viewManager = new IViewManager.Stub(){
        @Override
        public void setTextViewText(int id, String text) throws RemoteException {
            Message message = new Message();
            message.what = 2;
            Bundle bundle = new Bundle();
            bundle.putInt("id",id);
            bundle.putString("text",text);
            message.setData(bundle);
            new MainActivity.MyHandler(ViewAIDLService.this,getMainLooper()).sendMessage(message);
        }

        @Override
        public void addView(int layoutId) throws RemoteException {
            Message message = new Message();
            message.what = 3;
            Bundle bundle = new Bundle();
            bundle.putInt("layoutId",layoutId);
            message.setData(bundle);
            Log.i(TAG,"thread name = "+Thread.currentThread().getName());
            new MainActivity.MyHandler(ViewAIDLService.this,getMainLooper()).sendMessage(message);
        }

    };
    public ViewAIDLService() {
    }

    @Override
    public IBinder onBind(Intent intent) {
        return viewManager;
    }
}

在TempActivity中绑定服务,并在绑定成功后,针对实现的功能调用不同的远程方法。

  private ServiceConnection viewServiceConnection = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            Log.i(TAG,"onServiceConnected");
            IViewManager viewsManager = IViewManager.Stub.asInterface(service);
            try {
                viewsManager.setTextViewText(R.id.text,"通过AIDL跨进程修改TextView内容");
                viewsManager.addView(R.layout.layout);
            } catch (RemoteException e) {
                e.printStackTrace();
            }
        }

        @Override
        
  • 7
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 9
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 9
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值