Fix transition delay tracking when starting activity from recents

- Move logic to determine app switch etc. into ActivityMetricsLogger.
- Make sure the notify the tracker in startActivityFromRecentsInner

Bug: 27295491
Change-Id: Ic68058c88917e3f37183dded2f13cb35055323ee
diff --git a/services/core/java/com/android/server/am/ActivityMetricsLogger.java b/services/core/java/com/android/server/am/ActivityMetricsLogger.java
index fe085d7..be8f21d 100644
--- a/services/core/java/com/android/server/am/ActivityMetricsLogger.java
+++ b/services/core/java/com/android/server/am/ActivityMetricsLogger.java
@@ -18,6 +18,8 @@
 import com.android.internal.logging.MetricsLogger;
 import com.android.internal.logging.MetricsProto.MetricsEvent;
 
+import java.util.ArrayList;
+
 /**
  * Handles logging into Tron.
  */
@@ -99,6 +101,47 @@
     }
 
     /**
+     * Notifies the tracker that the activity is actually launching.
+     *
+     * @param resultCode one of the ActivityManager.START_* flags, indicating the result of the
+     *                   launch
+     * @param launchedActivity the activity that is being launched
+     */
+    void notifyActivityLaunched(int resultCode, ActivityRecord launchedActivity) {
+        final ProcessRecord processRecord = launchedActivity != null
+                ? mSupervisor.mService.mProcessNames.get(launchedActivity.processName,
+                        launchedActivity.appInfo.uid)
+                : null;
+        final boolean processRunning = processRecord != null;
+        final String componentName = launchedActivity != null
+                ? launchedActivity.shortComponentName
+                : null;
+
+        // We consider this a "process switch" if the process of the activity that gets launched
+        // didn't have an activity that was in started state. In this case, we assume that lot
+        // of caches might be purged so the time until it produces the first frame is very
+        // interesting.
+        final boolean processSwitch = processRecord == null
+                || !hasStartedActivity(processRecord, launchedActivity);
+
+        notifyActivityLaunched(resultCode, componentName, processRunning, processSwitch);
+    }
+
+    private boolean hasStartedActivity(ProcessRecord record, ActivityRecord launchedActivity) {
+        final ArrayList<ActivityRecord> activities = record.activities;
+        for (int i = activities.size() - 1; i >= 0; i--) {
+            final ActivityRecord activity = activities.get(i);
+            if (launchedActivity == activity) {
+                continue;
+            }
+            if (!activity.stopped) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    /**
      * Notifies the tracker the the activity is actually launching.
      *
      * @param resultCode one of the ActivityManager.START_* flags, indicating the result of the
@@ -109,7 +152,7 @@
      *                      activity that was stopped, i.e. the started activity is "switching"
      *                      processes
      */
-    void notifyActivityLaunched(int resultCode, @Nullable String componentName,
+    private void notifyActivityLaunched(int resultCode, @Nullable String componentName,
             boolean processRunning, boolean processSwitch) {
 
         if (resultCode < 0 || componentName == null || !processSwitch) {