1/ Inject InteractionJankMonitor for unit test

This purpose of InteractionJankMonitor.begin() and
InteractionJankMonitor.end() is used for e2e tests
(scenario / latency / benchmark tests)

SysUI had setup dagger for InteractionJankMonitor,
it would be helpful on unittest if inject instance
in SysUI code directly.

Test: atest SystemUITests
Bug: 206720526
Change-Id: I59af3f444bbc836c2ae2c0ef0803f788dba9ab46
This commit is contained in:
Bill Lin
2021-11-18 15:31:32 +08:00
parent 083bd48e19
commit e12377c5eb
5 changed files with 66 additions and 23 deletions

View File

@@ -53,8 +53,12 @@ open class GhostedViewLaunchAnimatorController(
private val ghostedView: View,
/** The [InteractionJankMonitor.CujType] associated to this animation. */
private val cujType: Int? = null
private val cujType: Int? = null,
private var interactionJankMonitor: InteractionJankMonitor? = null
) : ActivityLaunchAnimator.Controller {
constructor(view: View, type: Int) : this(view, type, null)
/** The container to which we will add the ghost view and expanding background. */
override var launchContainer = ghostedView.rootView as ViewGroup
private val launchContainerOverlay: ViewGroupOverlay
@@ -170,7 +174,7 @@ open class GhostedViewLaunchAnimatorController(
val matrix = ghostView?.animationMatrix ?: Matrix.IDENTITY_MATRIX
matrix.getValues(initialGhostViewMatrixValues)
cujType?.let { InteractionJankMonitor.getInstance().begin(ghostedView, it) }
cujType?.let { interactionJankMonitor?.begin(ghostedView, it) }
}
override fun onLaunchAnimationProgress(
@@ -251,7 +255,7 @@ open class GhostedViewLaunchAnimatorController(
return
}
cujType?.let { InteractionJankMonitor.getInstance().end(it) }
cujType?.let { interactionJankMonitor?.end(it) }
backgroundDrawable?.wrapped?.alpha = startBackgroundAlpha

View File

@@ -820,6 +820,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
private final KeyguardStateController mKeyguardStateController;
private final Lazy<KeyguardUnlockAnimationController> mKeyguardUnlockAnimationControllerLazy;
private final InteractionJankMonitor mInteractionJankMonitor;
private boolean mWallpaperSupportsAmbientMode;
/**
@@ -845,7 +846,8 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
KeyguardStateController keyguardStateController,
Lazy<KeyguardUnlockAnimationController> keyguardUnlockAnimationControllerLazy,
UnlockedScreenOffAnimationController unlockedScreenOffAnimationController,
Lazy<NotificationShadeDepthController> notificationShadeDepthController) {
Lazy<NotificationShadeDepthController> notificationShadeDepthController,
InteractionJankMonitor interactionJankMonitor) {
super(context);
mFalsingCollector = falsingCollector;
mLockPatternUtils = lockPatternUtils;
@@ -882,6 +884,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
mKeyguardStateController = keyguardStateController;
mKeyguardUnlockAnimationControllerLazy = keyguardUnlockAnimationControllerLazy;
mUnlockedScreenOffAnimationController = unlockedScreenOffAnimationController;
mInteractionJankMonitor = interactionJankMonitor;
}
public void userActivity() {
@@ -2245,8 +2248,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
onKeyguardExitFinished();
mKeyguardViewControllerLazy.get().hide(0 /* startTime */,
0 /* fadeoutDuration */);
InteractionJankMonitor.getInstance()
.end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
mInteractionJankMonitor.end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
}
@Override
@@ -2255,7 +2257,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
}
};
try {
InteractionJankMonitor.getInstance().begin(
mInteractionJankMonitor.begin(
createInteractionJankMonitorConf("RunRemoteAnimation"));
runner.onAnimationStart(WindowManager.TRANSIT_KEYGUARD_GOING_AWAY, apps,
wallpapers, nonApps, callback);
@@ -2271,14 +2273,14 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
mSurfaceBehindRemoteAnimationFinishedCallback = finishedCallback;
mSurfaceBehindRemoteAnimationRunning = true;
InteractionJankMonitor.getInstance().begin(
mInteractionJankMonitor.begin(
createInteractionJankMonitorConf("DismissPanel"));
// Pass the surface and metadata to the unlock animation controller.
mKeyguardUnlockAnimationControllerLazy.get().notifyStartKeyguardExitAnimation(
apps[0], startTime, mSurfaceBehindRemoteAnimationRequested);
} else {
InteractionJankMonitor.getInstance().begin(
mInteractionJankMonitor.begin(
createInteractionJankMonitorConf("RemoteAnimationDisabled"));
mKeyguardViewControllerLazy.get().hide(startTime, fadeoutDuration);
@@ -2288,7 +2290,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
// supported, so it's always null.
mContext.getMainExecutor().execute(() -> {
if (finishedCallback == null) {
InteractionJankMonitor.getInstance().end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
mInteractionJankMonitor.end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
return;
}
@@ -2316,8 +2318,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
} catch (RemoteException e) {
Slog.e(TAG, "RemoteException");
} finally {
InteractionJankMonitor.getInstance()
.end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
mInteractionJankMonitor.end(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
}
}
@@ -2328,8 +2329,7 @@ public class KeyguardViewMediator extends CoreStartable implements Dumpable,
} catch (RemoteException e) {
Slog.e(TAG, "RemoteException");
} finally {
InteractionJankMonitor.getInstance()
.cancel(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
mInteractionJankMonitor.cancel(CUJ_LOCKSCREEN_UNLOCK_ANIMATION);
}
}
});

View File

@@ -22,6 +22,7 @@ import android.content.Context;
import android.content.pm.PackageManager;
import android.os.PowerManager;
import com.android.internal.jank.InteractionJankMonitor;
import com.android.internal.widget.LockPatternUtils;
import com.android.keyguard.KeyguardDisplayManager;
import com.android.keyguard.KeyguardUpdateMonitor;
@@ -97,7 +98,8 @@ public class KeyguardModule {
KeyguardStateController keyguardStateController,
Lazy<KeyguardUnlockAnimationController> keyguardUnlockAnimationController,
UnlockedScreenOffAnimationController unlockedScreenOffAnimationController,
Lazy<NotificationShadeDepthController> notificationShadeDepthController) {
Lazy<NotificationShadeDepthController> notificationShadeDepthController,
InteractionJankMonitor interactionJankMonitor) {
return new KeyguardViewMediator(
context,
falsingCollector,
@@ -120,7 +122,8 @@ public class KeyguardModule {
keyguardStateController,
keyguardUnlockAnimationController,
unlockedScreenOffAnimationController,
notificationShadeDepthController
notificationShadeDepthController,
interactionJankMonitor
);
}

View File

@@ -16,22 +16,53 @@
package com.android.systemui.animation
import android.graphics.drawable.Drawable
import android.testing.AndroidTestingRunner
import android.testing.TestableLooper
import android.widget.LinearLayout
import android.view.View
import android.view.ViewGroup
import android.view.ViewParent
import androidx.test.filters.SmallTest
import com.android.internal.jank.InteractionJankMonitor
import com.android.systemui.SysuiTestCase
import org.junit.Before
import org.junit.Test
import org.junit.runner.RunWith
import org.mockito.ArgumentMatchers.any
import org.mockito.ArgumentMatchers.anyInt
import org.mockito.Mock
import org.mockito.Mockito.`when` as whenever
import org.mockito.MockitoAnnotations
@SmallTest
@RunWith(AndroidTestingRunner::class)
@TestableLooper.RunWithLooper
class GhostedViewLaunchAnimatorControllerTest : SysuiTestCase() {
@Mock lateinit var interactionJankMonitor: InteractionJankMonitor
@Mock lateinit var view: View
@Mock lateinit var rootView: ViewGroup
@Mock lateinit var viewParent: ViewParent
@Mock lateinit var drawable: Drawable
lateinit var controller: GhostedViewLaunchAnimatorController
@Before
fun setup() {
MockitoAnnotations.initMocks(this)
whenever(view.rootView).thenReturn(rootView)
whenever(view.background).thenReturn(drawable)
whenever(view.height).thenReturn(0)
whenever(view.width).thenReturn(0)
whenever(view.parent).thenReturn(viewParent)
whenever(view.visibility).thenReturn(View.VISIBLE)
whenever(view.invalidate()).then { /* NO-OP */ }
whenever(view.getLocationOnScreen(any())).then { /* NO-OP */ }
whenever(interactionJankMonitor.begin(any(), anyInt())).thenReturn(true)
whenever(interactionJankMonitor.end(anyInt())).thenReturn(true)
controller = GhostedViewLaunchAnimatorController(view, 0, interactionJankMonitor)
}
@Test
fun animatingOrphanViewDoesNotCrash() {
val ghostedView = LinearLayout(mContext)
val controller = GhostedViewLaunchAnimatorController(ghostedView)
val state = LaunchAnimator.State(top = 0, bottom = 0, left = 0, right = 0)
controller.onIntentStarted(willAnimate = true)

View File

@@ -41,6 +41,7 @@ import android.testing.TestableLooper;
import androidx.test.filters.SmallTest;
import com.android.internal.jank.InteractionJankMonitor;
import com.android.internal.policy.IKeyguardDrawnCallback;
import com.android.internal.widget.LockPatternUtils;
import com.android.keyguard.KeyguardDisplayManager;
@@ -64,9 +65,6 @@ import com.android.systemui.util.DeviceConfigProxyFake;
import com.android.systemui.util.concurrency.FakeExecutor;
import com.android.systemui.util.time.FakeSystemClock;
import java.util.Optional;
import java.util.function.Function;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
@@ -75,6 +73,9 @@ import org.mockito.ArgumentMatchers;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import java.util.Optional;
import java.util.function.Function;
@RunWith(AndroidTestingRunner.class)
@TestableLooper.RunWithLooper
@SmallTest
@@ -103,6 +104,7 @@ public class KeyguardViewMediatorTest extends SysuiTestCase {
private @Mock KeyguardUnlockAnimationController mKeyguardUnlockAnimationController;
private @Mock UnlockedScreenOffAnimationController mUnlockedScreenOffAnimationController;
private @Mock IKeyguardDrawnCallback mKeyguardDrawnCallback;
private @Mock InteractionJankMonitor mInteractionJankMonitor;
private DeviceConfigProxy mDeviceConfig = new DeviceConfigProxyFake();
private FakeExecutor mUiBgExecutor = new FakeExecutor(new FakeSystemClock());
@@ -121,6 +123,8 @@ public class KeyguardViewMediatorTest extends SysuiTestCase {
.thenReturn(mUnfoldAnimationOptional);
when(mUnfoldAnimationOptional.isPresent()).thenReturn(true);
when(mUnfoldAnimationOptional.get()).thenReturn(mUnfoldAnimation);
when(mInteractionJankMonitor.begin(any(), anyInt())).thenReturn(true);
when(mInteractionJankMonitor.end(anyInt())).thenReturn(true);
mViewMediator = new KeyguardViewMediator(
mContext,
@@ -144,7 +148,8 @@ public class KeyguardViewMediatorTest extends SysuiTestCase {
mKeyguardStateController,
() -> mKeyguardUnlockAnimationController,
mUnlockedScreenOffAnimationController,
() -> mNotificationShadeDepthController);
() -> mNotificationShadeDepthController,
mInteractionJankMonitor);
mViewMediator.start();
}