TaskView简述
TaskView简述
TaskView是什么
首先看一下官方的注释(基于Android12.0.0_r3版本的代码分析):
View that can display a task
是一个可以展示Task的视图。那有什么用呢?简单来说就是跨进程来展示UI。就比如我有两个进程,进程A和进程B。我想在进程A中启动进程B的Activity,这时候就可以使用TaskView来实现这个功能。
接着再来说TaskView是什么?
TaskView 是SurfaceView的子类,并且实现了
SurfaceHolder.Callback, ShellTaskOrganizer.TaskListener, ViewTreeObserver.OnComputeInternalInsetsListener这三个接口
首先说一下SurfaceView,这个用过的人都有些印象,比如摄像头的录制展示可以用SurfaceView来展示或者是一些需要即时更新的UI可以通过SurfaceView来进行展示。换大多数人的说法就是挖了个洞,也确实是,如果要是保证效率,没必要做那么多没用的操作,有个捷径何尝不是个好事情~。
接着是 SurfaceHolder.Callback,注册了这个Callback,就能够接受到Surface改变的回调,经典的三个方法surfaceCreated
,surfaceChanged
和surfaceDestroyed
,一般是和SurfaceView配合使用的。
说到这,可以把TaskView理解为一个SurfaceView。
接着说一下 ShellTaskOrganizer.TaskListener
这个接口,这个就属于是WindowManager/Shell
这一套的相关接口了。在系统的任务更改的时候,就能在这个监听中收到回调。在这里,TaskView是这个接口的实现类,那就说明,ShellTaskOrganizer
对TaskView进行管理,当有消息来时,就会去通知给TaskView。
最后说一下ViewTreeObserver.OnComputeInternalInsetsListener
这个接口,这个接口在源码中搜索了下,发现了一个熟悉的类VoiceInteractionSession
,接触到的项目对于语音助手的使用就是基于这个类的相关交互的,往下翻,发现熟悉的onShow
,onHide
方法等等。。。有点跑题了。布局完成的时候,如果实现了这个接口,就能够onComputeInternalInsets
接受到回调,语音助手收到后回去进行自己的UI绘制。
TaskView的创建
创建还不好说么,直接new一个,开句玩笑。具体如何创建,还得看谷歌源生代码是怎么使用的。
/** Interface to create TaskView. */
@ExternalThread
public interface TaskViewFactory {/** Creates an {@link TaskView} */void create(@UiContext Context context, Executor executor, Consumer<TaskView> onCreate);
}
搜索TaskView的构造方法,发现TaskViewFactory
,听名字就是一个TaskView的创建类,查看注释,更加确定就是通过这个接口来创建TaskView了。终归是一个接口,去看下具体实现。
/** Factory controller which can create {@link TaskView} */
public class TaskViewFactoryController {private final ShellTaskOrganizer mTaskOrganizer;private final ShellExecutor mShellExecutor;private final TaskViewFactory mImpl = new TaskViewFactoryImpl();public TaskViewFactoryController(ShellTaskOrganizer taskOrganizer,ShellExecutor shellExecutor) {mTaskOrganizer = taskOrganizer;mShellExecutor = shellExecutor;}public TaskViewFactory asTaskViewFactory() {return mImpl;}/** Creates an {@link TaskView} */public void create(@UiContext Context context, Executor executor, Consumer<TaskView> onCreate) {TaskView taskView = new TaskView(context, mTaskOrganizer);executor.execute(() -> {onCreate.accept(taskView);});}private class TaskViewFactoryImpl implements TaskViewFactory {@ExternalThreadpublic void create(@UiContext Context context,Executor executor, Consumer<TaskView> onCreate) {mShellExecutor.execute(() -> {TaskViewFactoryController.this.create(context, executor, onCreate);});}}
}
可以看到TaskViewFactoryController
的内部类TaskViewFactoryImpl
实现了TaskViewFactory
这个接口,并且交给TaskViewFactoryController
来进行TaskView的创建。到这里大概就知道了,创建TaskView时需要创建一个ShellTaskOrganizer
和一个ShellExecutor
对象,接着再来创建一个TaskView对象。这里留个猜测,等到TaskView启动的Activity的onCreate()执行后,才去创建TaskView对象。
再来看一下TaskView的构造函数干了些什么事情。
public TaskView(Context context, ShellTaskOrganizer organizer) {super(context, null, 0, 0, true /* disableBackgroundLayer */);mTaskOrganizer = organizer;mShellExecutor = organizer.getExecutor();setUseAlpha();getHolder().addCallback(this);// 用来打印警告的log,以及告诉关闭的方法名。要成对使用mGuard.open("release");
}
首先mTaskOrganizer
和mShellExecutor
在上面可以看到,都是在构造的时候需要的参数,接着setUseAlpha()
方法是用来设置透明度的。下面getHolder().addCallback(this)
是向其父类SurfaceView
注册SurfaceHolder.Callback
监听的。
到此为止,TaskView的创建暂时来个中场休息~
TaskView的使用
对于TaskView的使用,去启动界面使用startActivity
方法即可,向其传递一个PendingIntent对象,就能够让其在TaskView中去启动一个其他的Activity。但是这里先说一下另一个比较重要的点,startActivity
随后再说。这里说一下要进行注册的监听,也就是TaskView.Listener
,该监听是需要TaskView的setListener
方法去进行注册的。
TaskView.Listener
为什么要先说这个的?首先把状态的监听注册好,能够很好的去监听我们通过TaskView展示其他进程的Activity的状态,至少能够知道执行到了TaskView的哪一步,如果出现问题方便我们去很快的定位。
先看看这个监听都包含了哪些方法:
/** Callback for listening task state. */
public interface Listener {/** Called when the container is ready for launching activities. */default void onInitialized() {}/** Called when the container can no longer launch activities. */default void onReleased() {}/** Called when a task is created inside the container. */default void onTaskCreated(int taskId, ComponentName name) {}/** Called when a task visibility changes. */default void onTaskVisibilityChanged(int taskId, boolean visible) {}/** Called when a task is about to be removed from the stack inside the container. */default void onTaskRemovalStarted(int taskId) {}/** Called when a task is created inside the container. */default void onBackPressedOnTaskRoot(int taskId) {}
}
看一下官方的注释,这个监听就是用来监听Task的状态的。
onInitialized
这个方法说明当前的容器已经准备好去启动Activity了,当TaskView
收到了surfaceCreated
【SurfaceHolder.Callback】的回调之后,便会去给注册的监听发送onInitialized
的消息。
onTaskCreated
这个方法在Task已经被创建并且放入容器时,回去收到这个回调,当TaskView收到onTaskAppeared
【ShellTaskOrganizer.TaskListener】的回调后,会去告知Listener的onTaskCreated
onTaskVisibilityChanged
这个方法在调用updateTaskVisibility()
的方法时回去通知监听的可见性变化,也即surfaceCreated
,surfaceDestroyed
和onTaskAppeared
时会去更新可见性变化。
onReleased
这个方法在容器不在启动Activity的时候进行调用,一般我们在使用完后可以手动去release()
。
onTaskRemovalStarted
这个方法在Task在栈中即将移除时调用,即在onTaskVanished
【ShellTaskOrganizer.TaskListener】回调后去执行。
onBackPressedOnTaskRoot
当Task被创建并且放入容器时进行调用,即在onBackPressedOnTaskRoot
【ShellTaskOrganizer.TaskListener】回调后去执行。
上面提到的 【ShellTaskOrganizer.TaskListener】 都是在ShellTaskOrganizer这个类分发下来的,之后也会再继续整理整体的流程。而实现SurfaceHolder.Callback
的三个方法,是在其父类另一个父类SurfaceView
进行可见性调整的时候,会向其下发对应的回调。
startActivity
TaskView归根到底,还是去起一个Activity,只不过展示的位置变了。先看下源码:
/*** Launch a new activity.** @param pendingIntent Intent used to launch an activity.* @param fillInIntent Additional Intent data, see {@link Intent#fillIn Intent.fillIn()}* @param options options for the activity.* @param launchBounds the bounds (window size and position) that the activity should be* launched in, in pixels and in screen coordinates.*/
public void startActivity(@NonNull PendingIntent pendingIntent, @Nullable Intent fillInIntent,@NonNull ActivityOptions options, @Nullable Rect launchBounds) {prepareActivityOptions(options, launchBounds);try {pendingIntent.send(mContext, 0 /* code */, fillInIntent,null /* onFinished */, null /* handler */, null /* requiredPermission */,options.toBundle());} catch (Exception e) {throw new RuntimeException(e);}
}
需要传入四个参数,分别是一个PendingIntent,Intent,ActivityOptions和Rect。第一个参数是即将启动的Activity的Intent信息,第二个参数是Intent的补充信息,第三个参数是Activity的一些参数,最后一个参数是展示的大小以及位置。
而prepareActivityOptions
会将Rect数据存储到ActivityOptions当中去并且向ShellTaskOrganizer
注册自身【ShellTaskOrganizer.TaskListener】。
TaskView.Listener # onTaskCreated()
这里先简单记录一下和onTaskCreated()
方法的相关流程。
所谓的TaskView,现在终于算是到了Task了,到我现在分析的这个位置,Task类持有一个ActivityTaskManagerService对象,ActivityTaskManagerService又会持有一个 TaskOrganizerController对象,随后去进行跨进程通信。这里的数理逻辑是倒着来进行分析的。
在这个流程图中,以TaskOrganizerController作为一个参考线,在这个流程图的左侧,全都是属于客户端的范畴,而右侧是服务端的范畴,服务端跨进程向客户端进行数据的发送,我们在收到对应的回调后再进行相关的处理。
而正如其名,TaskOrganizerController就是用来进行Task分发的控制的。
TaskView简述相关推荐
- 简述计算机科学的核心内容,北京大学-计算机科学与技术(2018秋)作业及复习
59.(第十章)外排序是指在排序前后,数据在外存上,排序时数据调入内存进行的排序方法. 60.(第十章)在选择排序.冒泡排序.归并排序中, 归并排序是空间复杂度最大的. 三.简答和程序题(共10题,每 ...
- 设计模式学习1:设计模式简述和设计模式原则
设计模式简述 什么是设计模式? 软件工程中,设计模式(design pattern)是对软件设计中普遍存在(反复出现)的各种问题,所提出的解决方案. 设计模式的目的: 代码高可用(相同作用的代码能重复 ...
- Java中常见的锁简述
在Java的应用中,或多或少的都会接触到一些锁,那么问题就来了,在Java中,常见的锁有哪些,都有什么样的作用?? 这里给大家简单的简述一下这些学常见的锁. 本文件所涉及到的锁: 1.公平锁 / 非公 ...
- 简述DataInputStream和DataOuputStream
2019独角兽企业重金招聘Python工程师标准>>> Java开发中经常会用到IO流,那么就会碰到DataInputStream和DataOuputStream这两个包装类.下面就 ...
- 简要叙述matlab的含义,1,简述MATLAB组成部分? 2,说明使用M文件编辑/调试器的方法和优点? 3,存储在工作空间中的数组能编辑吗...
匿名用户 1级 2012-05-17 回答 我也考这个....祝你好运 1,简述MATLAB组成部分? (1)开发环境(development Environment); (2)MATLAB数学函数库 ...
- 简述Linux和Windows下Python搭建步骤
简述就Windows和Linux环境下安装Python的步骤. Python环境搭建首先到官网(www.python.org)下载相应的安装版本.主要分为Windows和Linux两种: 一.Linu ...
- 简述 OAuth 2.0 的运作流程
本文将以用户使用 github 登录网站留言为例,简述 OAuth 2.0 的运作流程. 假如我有一个网站,你是我网站上的访客,看了文章想留言表示「朕已阅」,留言时发现有这个网站的帐号才能够留言,此时 ...
- 简述机器指令与微指令之间的关系_自考《计算机组成原理》模拟试题(一)
一.单项选择题(本大题共 25小题,每小题1分,共25分)在每小题列出的四个选项中只有一个选项是符合题目要求的,请将正确选项前的字母填在题后的括号内. 1.-0的8位二进制补码是( ) A.10000 ...
- day1简述、输入输出、运算符、条件语句、文件读写、三元运算
文章目录 1.Python 简述 2.变量 3.输入输出 4.数据运算 5. 条件语句 if..else.elif 循环语句 for.while 6.文件读写 7.三元运算 1.Python 简述 ...
最新文章
- IOS开发中多线程的使用
- GDI+中发生一般性错误
- 教你写出可读性高的Python代码
- php将数字转化为中文大写人民币格式
- maven(6)仓库
- windows7下安装php的imagick和imagemagick扩展教程
- MongoDB Replication
- Linux指令:grep指令详解1
- 2020 数学建模国赛 B 题参考思路
- 边缘计算在物联网领域的发展前景
- 1082 射击比赛(JAVA)
- office安装双击setup后点击‘立即安装’无反应(闪退)
- 美团商品平台化之路—关于架构原则的思考
- [托业]TOEIC词汇汇总(完整篇)4
- Dell 服务器错误代码
- “云”中智控 IT管理新境界
- 怎么在pc端浏览器调试移动端页面
- 器件——TCRT5000参数与实际设计应用
- 使用PhoenixSuit.exe刷机失败的解决办法
- 关于mybatis中mapper文件resultMap中collection和association的使用