1 /* 2 * Copyright (C) 2021 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.transition; 18 19 import static com.android.wm.shell.protolog.ShellProtoLogGroup.WM_SHELL_TRANSITIONS; 20 21 import android.annotation.NonNull; 22 import android.os.RemoteException; 23 import android.view.IRemoteAnimationFinishedCallback; 24 import android.view.IRemoteAnimationRunner; 25 import android.view.RemoteAnimationAdapter; 26 import android.view.RemoteAnimationTarget; 27 import android.view.SurfaceControl; 28 import android.view.WindowManager; 29 import android.window.IWindowContainerTransactionCallback; 30 31 import com.android.internal.protolog.common.ProtoLog; 32 33 /** 34 * Utilities and interfaces for transition-like usage on top of the legacy app-transition and 35 * synctransaction tools. 36 */ 37 public class LegacyTransitions { 38 39 /** 40 * Interface for a "legacy" transition. Effectively wraps a sync callback + remoteAnimation 41 * into one callback. 42 */ 43 public interface ILegacyTransition { 44 /** 45 * Called when both the associated sync transaction finishes and the remote animation is 46 * ready. 47 */ onAnimationStart(int transit, RemoteAnimationTarget[] apps, RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps, IRemoteAnimationFinishedCallback finishedCallback, SurfaceControl.Transaction t)48 void onAnimationStart(int transit, RemoteAnimationTarget[] apps, 49 RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps, 50 IRemoteAnimationFinishedCallback finishedCallback, SurfaceControl.Transaction t); 51 } 52 53 /** 54 * Makes sure that a remote animation and corresponding sync callback are called together 55 * such that the sync callback is called first. This assumes that both the callback receiver 56 * and the remoteanimation are in the same process so that order is preserved on both ends. 57 */ 58 public static class LegacyTransition { 59 private final ILegacyTransition mLegacyTransition; 60 private int mSyncId = -1; 61 private SurfaceControl.Transaction mTransaction; 62 private int mTransit; 63 private RemoteAnimationTarget[] mApps; 64 private RemoteAnimationTarget[] mWallpapers; 65 private RemoteAnimationTarget[] mNonApps; 66 private IRemoteAnimationFinishedCallback mFinishCallback = null; 67 private boolean mCancelled = false; 68 private final SyncCallback mSyncCallback = new SyncCallback(); 69 private final RemoteAnimationAdapter mAdapter = 70 new RemoteAnimationAdapter(new RemoteAnimationWrapper(), 0, 0); 71 LegacyTransition(@indowManager.TransitionType int type, @NonNull ILegacyTransition legacyTransition)72 public LegacyTransition(@WindowManager.TransitionType int type, 73 @NonNull ILegacyTransition legacyTransition) { 74 mLegacyTransition = legacyTransition; 75 mTransit = type; 76 } 77 getType()78 public @WindowManager.TransitionType int getType() { 79 return mTransit; 80 } 81 getSyncCallback()82 public IWindowContainerTransactionCallback getSyncCallback() { 83 return mSyncCallback; 84 } 85 getAdapter()86 public RemoteAnimationAdapter getAdapter() { 87 return mAdapter; 88 } 89 90 private class SyncCallback extends IWindowContainerTransactionCallback.Stub { 91 @Override onTransactionReady(int id, SurfaceControl.Transaction t)92 public void onTransactionReady(int id, SurfaceControl.Transaction t) 93 throws RemoteException { 94 ProtoLog.v(WM_SHELL_TRANSITIONS, 95 "LegacyTransitions.onTransactionReady(): syncId=%d", id); 96 mSyncId = id; 97 mTransaction = t; 98 checkApply(true /* log */); 99 } 100 } 101 102 private class RemoteAnimationWrapper extends IRemoteAnimationRunner.Stub { 103 @Override onAnimationStart(int transit, RemoteAnimationTarget[] apps, RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps, IRemoteAnimationFinishedCallback finishedCallback)104 public void onAnimationStart(int transit, RemoteAnimationTarget[] apps, 105 RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps, 106 IRemoteAnimationFinishedCallback finishedCallback) throws RemoteException { 107 mTransit = transit; 108 mApps = apps; 109 mWallpapers = wallpapers; 110 mNonApps = nonApps; 111 mFinishCallback = finishedCallback; 112 checkApply(false /* log */); 113 } 114 115 @Override onAnimationCancelled()116 public void onAnimationCancelled() throws RemoteException { 117 mCancelled = true; 118 mApps = mWallpapers = mNonApps = null; 119 checkApply(false /* log */); 120 } 121 } 122 123 checkApply(boolean log)124 private void checkApply(boolean log) throws RemoteException { 125 if (mSyncId < 0 || (mFinishCallback == null && !mCancelled)) { 126 if (log) { 127 ProtoLog.v(WM_SHELL_TRANSITIONS, "\tSkipping hasFinishedCb=%b canceled=%b", 128 mFinishCallback != null, mCancelled); 129 } 130 return; 131 } 132 if (log) { 133 ProtoLog.v(WM_SHELL_TRANSITIONS, "\tapply"); 134 } 135 mLegacyTransition.onAnimationStart(mTransit, mApps, mWallpapers, 136 mNonApps, mFinishCallback, mTransaction); 137 } 138 } 139 } 140