标题: Android U 多任务启动分屏——团体流程先容 [打印本页] 作者: 钜形不锈钢水箱 时间: 2025-1-5 05:17 标题: Android U 多任务启动分屏——团体流程先容 序
原生的分屏功能是在多任务中,点击应用图标选择分屏,在选择多任务中的其他应用进行分屏
代码分析思路
进入上分屏代码分析
我们有两种分析方法,一种是通过Split screen文字查找对应的onClick事件跟踪代码流程
另一种是通过,点击进入到上分屏之后,Toast弹出的文字Tap another app to use split screen来分析
推荐使用第二种方式,如果使用第一种从点击事件开始跟踪比较复杂且轻易出错,但是第二种是在操纵竣事的地方才会有这个打印,我们只需找到打印这个Toast的地方加堆栈即可。
这里我们以这里点击进入到分屏后,Toast弹出的文字Tap another app to use split screen来分析,在多任务中点击Split screen的流程。
字符串一样平常都在XML文件中,我们在代码中找下
SplitScreen: at com.android.wm.shell.common.split.SplitLayout.<init>(go/retraceme a9a41fad2b076569b5dcce5872086854a2b8f379c7dc07dcce654ce543da67bb:137)
SplitScreen: at com.android.wm.shell.splitscreen.StageCoordinator.onTaskAppeared(go/retraceme a9a41fad2b076569b5dcce5872086854a2b8f379c7dc07dcce654ce543da67bb:1762)
SplitScreen: at com.android.wm.shell.ShellTaskOrganizer.onTaskAppeared(go/retraceme a9a41fad2b076569b5dcce5872086854a2b8f379c7dc07dcce654ce543da67bb:490)
SplitScreen: at com.android.wm.shell.ShellTaskOrganizer.onTaskAppeared(go/retraceme a9a41fad2b076569b5dcce5872086854a2b8f379c7dc07dcce654ce543da67bb:477)
SplitScreen: at android.window.TaskOrganizer$1.lambda$onTaskAppeared$4(TaskOrganizer.java:325)
SplitScreen: at android.window.TaskOrganizer$1.$r8$lambda$Z3SZqVKLE-2zO9NE5htsmlBghFs(Unknown Source:0)
SplitScreen: at android.window.TaskOrganizer$1$$ExternalSyntheticLambda5.run(Unknown Source:6)
SplitScreen: at android.os.Handler.handleCallback(Handler.java:958)
SplitScreen: at android.os.Handler.dispatchMessage(Handler.java:99)
SplitScreen: at android.os.Looper.loopOnce(Looper.java:205)
SplitScreen: at android.os.Looper.loop(Looper.java:294)
SplitScreen: at android.os.HandlerThread.run(HandlerThread.java:67)
Launcher: at com.android.quickstep.util.SplitSelectStateController.launchTasksRefactored(SplitSelectStateController.java:412)
Launcher: at com.android.quickstep.util.SplitSelectStateController.launchTasks(SplitSelectStateController.java:329)
Launcher: at com.android.quickstep.util.SplitSelectStateController.launchSplitTasks(SplitSelectStateController.java:258)
Launcher: at com.android.quickstep.views.RecentsView.lambda$confirmSplitSelect$34(RecentsView.java:4718)
Launcher: at com.android.quickstep.views.RecentsView.$r8$lambda$uSHMT-0i9azkpL6YW9McOOFyjVQ(Unknown Source:0)
Launcher: at com.android.quickstep.views.RecentsView$$ExternalSyntheticLambda26.accept(Unknown Source:4)
Launcher: at com.android.launcher3.anim.AnimatorListeners$EndStateCallbackWrapper.onAnimationEnd(AnimatorListeners.java:80)
Launcher: at android.animation.Animator$AnimatorListener.onAnimationEnd(Animator.java:711)
Launcher: at android.animation.Animator$AnimatorCaller$$ExternalSyntheticLambda1.call(Unknown Source:4)
Launcher: at android.animation.Animator.callOnList(Animator.java:669)
Launcher: at android.animation.Animator.notifyListeners(Animator.java:608)
Launcher: at android.animation.Animator.notifyEndListeners(Animator.java:633)
Launcher: at android.animation.ValueAnimator.endAnimation(ValueAnimator.java:1306)
Launcher: at android.animation.ValueAnimator.doAnimationFrame(ValueAnimator.java:1566)
Launcher: at android.animation.ValueAnimator.pulseAnimationFrame(ValueAnimator.java:1582)
Launcher: at android.animation.AnimatorSet.pulseFrame(AnimatorSet.java:1314)
Launcher: at android.animation.AnimatorSet.handleAnimationEvents(AnimatorSet.java:1297)
Launcher: at android.animation.AnimatorSet.doAnimationFrame(AnimatorSet.java:1197)
Launcher: at android.animation.AnimationHandler.doAnimationFrame(AnimationHandler.java:328)
Launcher: at android.animation.AnimationHandler.-$$Nest$mdoAnimationFrame(Unknown Source:0)
Launcher: at android.animation.AnimationHandler$1.doFrame(AnimationHandler.java:86)
Launcher: at android.view.Choreographer$CallbackRecord.run(Choreographer.java:1337)
Launcher: at android.view.Choreographer$CallbackRecord.run(Choreographer.java:1348)
Launcher: at android.view.Choreographer.doCallbacks(Choreographer.java:952)
Launcher: at android.view.Choreographer.doFrame(Choreographer.java:878)
Launcher: at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:1322)
Launcher: at android.os.Handler.handleCallback(Handler.java:958)
Launcher: at android.os.Handler.dispatchMessage(Handler.java:99)
Launcher: at android.os.Looper.loopOnce(Looper.java:205)
Launcher: at android.os.Looper.loop(Looper.java:294)
Launcher: at android.app.ActivityThread.main(ActivityThread.java:8177)
Launcher: at java.lang.reflect.Method.invoke(Native Method)
Launcher: at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:552)
Launcher: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:971)
复制代码
此中Launcher: at com.android.quickstep.views.RecentsView.lambda$confirmSplitSelect$34(RecentsView.java:4718)开始lambda表达式,我们找到这里RecentsView.confirmSplitSelect方法的第4718行
只需要继承在RecentsView.confirmSplitSelect方法添加堆栈,我们得到
Launcher: at com.android.quickstep.views.RecentsView.confirmSplitSelect(RecentsView.java:4716)
Launcher: at com.android.quickstep.views.TaskView.confirmSecondSplitSelectApp(TaskView.java:762)
Launcher: at com.android.quickstep.views.TaskView.onClick(TaskView.java:746)
Launcher: at com.android.quickstep.views.TaskView.$r8$lambda$2dErZAYzRAWboZR0vn31kIz_HGY(Unknown Source:0)
Launcher: at com.android.quickstep.views.TaskView$$ExternalSyntheticLambda2.onClick(Unknown Source:2)
Launcher: at android.view.View.performClick(View.java:7659)
Launcher: at android.view.View.performClickInternal(View.java:7636)
Launcher: at android.view.View.-$$Nest$mperformClickInternal(Unknown Source:0)
Launcher: at android.view.View$PerformClick.run(View.java:30156)
Launcher: at android.os.Handler.handleCallback(Handler.java:958)
Launcher: at android.os.Handler.dispatchMessage(Handler.java:99)
Launcher: at android.os.Looper.loopOnce(Looper.java:205)
Launcher: at android.os.Looper.loop(Looper.java:294)
Launcher: at android.app.ActivityThread.main(ActivityThread.java:8177)
Launcher: at java.lang.reflect.Method.invoke(Native Method)
Launcher: at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:552)
Launcher: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:971)
复制代码
关键在这里Launcher: at com.android.quickstep.views.TaskView.onClick(TaskView.java:746)
我们终于找到点击下分屏调用的onClick方法,自此分屏的触发流程竣事。
这个查找过程中我们也确定了桌面与SystemUI的跨进程通信方式,即通过ISplitScreen.aidl,SystemUI侧的流程查找不再赘述。
分割线布局
SplitScreen: at android.window.WindowOrganizer.startNewTransition(WindowOrganizer.java:94)
SplitScreen: at com.android.wm.shell.transition.Transitions.startTransition(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:1121)
SplitScreen: at com.android.wm.shell.splitscreen.SplitScreenTransitions.startEnterTransition(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:345)
SplitScreen: at com.android.wm.shell.splitscreen.StageCoordinator.startWithTask(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:701)
SplitScreen: at com.android.wm.shell.splitscreen.StageCoordinator.startTasks(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:623)
SplitScreen: at com.android.wm.shell.splitscreen.SplitScreenController$ISplitScreenImpl.lambda$startTasks$11(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:1157)
SplitScreen: at com.android.wm.shell.splitscreen.SplitScreenController$ISplitScreenImpl.$r8$lambda$UuHBVv3bzz4CDOdyAqlv4kaRHgY(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:0)
SplitScreen: at com.android.wm.shell.splitscreen.SplitScreenController$ISplitScreenImpl$$ExternalSyntheticLambda14.accept(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:0)
SplitScreen: at com.android.wm.shell.common.ExecutorUtils.lambda$executeRemoteCallWithTaskPermission$1(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:60)
SplitScreen: at com.android.wm.shell.common.ExecutorUtils.$r8$lambda$s8eUOdyrqpqzzyFwAMGxO-MaCg4(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:0)
SplitScreen: at com.android.wm.shell.common.ExecutorUtils$$ExternalSyntheticLambda1.run(go/retraceme d8ee0e3eecdad3cdc77c111ff5591ebe26372c47d62ba59187c5ecf96366b561:0)
SplitScreen: at android.os.Handler.handleCallback(Handler.java:958)
SplitScreen: at android.os.Handler.dispatchMessage(Handler.java:99)
SplitScreen: at android.os.Looper.loopOnce(Looper.java:205)
SplitScreen: at android.os.Looper.loop(Looper.java:294)
SplitScreen: at android.os.HandlerThread.run(HandlerThread.java:67)