1 /* <lambda>null2 * Copyright (C) 2024 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.wm.shell.desktopmode.minimize 18 19 import android.os.IBinder 20 import android.view.SurfaceControl 21 import android.view.WindowManager.TRANSIT_TO_BACK 22 import android.window.RemoteTransition 23 import android.window.TransitionInfo 24 import android.window.TransitionInfo.Change 25 import android.window.TransitionRequestInfo 26 import android.window.WindowContainerTransaction 27 import com.android.wm.shell.RootTaskDisplayAreaOrganizer 28 import com.android.wm.shell.common.ShellExecutor 29 import com.android.wm.shell.shared.TransitionUtil 30 import com.android.wm.shell.transition.OneShotRemoteHandler 31 import com.android.wm.shell.transition.Transitions 32 import com.android.wm.shell.transition.Transitions.TransitionHandler 33 34 /** 35 * Handles transitions that result in hitting the Desktop window limit, by performing some 36 * preparation work and then delegating to [remoteTransition]. 37 * 38 * This transition handler prepares the leash of the minimizing change referenced by 39 * [taskIdToMinimize], and then delegates to [remoteTransition] to perform the actual transition. 40 */ 41 class DesktopWindowLimitRemoteHandler( 42 mainExecutor: ShellExecutor, 43 private val rootTaskDisplayAreaOrganizer: RootTaskDisplayAreaOrganizer, 44 remoteTransition: RemoteTransition, 45 private val taskIdToMinimize: Int, 46 ) : TransitionHandler { 47 48 private val oneShotRemoteHandler = OneShotRemoteHandler(mainExecutor, remoteTransition) 49 private var transition: IBinder? = null 50 51 /** Sets the transition that will be handled - this must be called before [startAnimation]. */ 52 fun setTransition(transition: IBinder) { 53 this.transition = transition 54 oneShotRemoteHandler.setTransition(transition) 55 } 56 57 override fun handleRequest( 58 transition: IBinder, 59 request: TransitionRequestInfo, 60 ): WindowContainerTransaction? { 61 this.transition = transition 62 return oneShotRemoteHandler.handleRequest(transition, request) 63 } 64 65 override fun startAnimation( 66 transition: IBinder, 67 info: TransitionInfo, 68 startTransaction: SurfaceControl.Transaction, 69 finishTransaction: SurfaceControl.Transaction, 70 finishCallback: Transitions.TransitionFinishCallback, 71 ): Boolean { 72 if (transition != this.transition) return false 73 val minimizeChange = findMinimizeChange(info, taskIdToMinimize) ?: return false 74 // Reparent the minimize change back to the root task display area, so the minimizing window 75 // isn't shown in front of other windows. We do this here in Shell since Launcher doesn't 76 // have access to RootTaskDisplayAreaOrganizer. 77 applyMinimizeChangeReparenting(info, minimizeChange, startTransaction) 78 return oneShotRemoteHandler.startAnimation( 79 transition, 80 info, 81 startTransaction, 82 finishTransaction, 83 finishCallback, 84 ) 85 } 86 87 private fun applyMinimizeChangeReparenting( 88 info: TransitionInfo, 89 minimizeChange: Change, 90 startTransaction: SurfaceControl.Transaction, 91 ) { 92 val taskInfo = minimizeChange.taskInfo ?: return 93 if (taskInfo.isFreeform && TransitionUtil.isOpeningMode(info.type)) { 94 rootTaskDisplayAreaOrganizer.reparentToDisplayArea( 95 taskInfo.displayId, 96 minimizeChange.leash, 97 startTransaction, 98 ) 99 } 100 } 101 102 private fun findMinimizeChange(info: TransitionInfo, taskIdToMinimize: Int): Change? = 103 info.changes.find { change -> 104 change.taskInfo?.taskId == taskIdToMinimize && change.mode == TRANSIT_TO_BACK 105 } 106 } 107