• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2020 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.settings.testutils;
18 
19 import android.app.Activity;
20 import android.util.Log;
21 import android.view.View;
22 import android.view.ViewGroup;
23 
24 import androidx.fragment.app.FragmentActivity;
25 import androidx.test.runner.lifecycle.ActivityLifecycleMonitorRegistry;
26 import androidx.test.runner.lifecycle.Stage;
27 
28 import java.util.ArrayList;
29 import java.util.Collection;
30 import java.util.function.Supplier;
31 
32 public class UiUtils {
33     private static final String TAG = "UI_UTILS";
34 
waitUntilCondition(long timeoutInMillis, Supplier<Boolean> condition)35     public static void waitUntilCondition(long timeoutInMillis, Supplier<Boolean> condition) {
36         long start = System.nanoTime();
37         while (System.nanoTime() - start < (timeoutInMillis * 1000000)) {
38             try {
39                 //Eat NPE from condition because there's a concurrency issue that when calling
40                 //findViewById when the view hierarchy is still rendering, it sometimes encounter
41                 //null views that may exist few milliseconds before, and causes a NPE.
42                 if (condition.get()) {
43                     return;
44                 }
45             } catch (NullPointerException e) {
46                 e.printStackTrace();
47             }
48         }
49         if (System.nanoTime() - start >= (timeoutInMillis * 1000000)) {
50             Log.w(TAG, "Condition not match and timeout for waiting " + timeoutInMillis + "(ms).");
51         } else {
52             Log.d(TAG, "Condition matched.");
53         }
54     }
55 
waitForActivitiesInStage(long timeoutInMillis, Stage stage)56     public static boolean waitForActivitiesInStage(long timeoutInMillis, Stage stage) {
57         final Collection<Activity> activities = new ArrayList<>();
58         waitUntilCondition(Constants.ACTIVITY_LAUNCH_WAIT_TIMEOUT, () -> {
59             activities.addAll(
60                     ActivityLifecycleMonitorRegistry.getInstance().getActivitiesInStage(
61                             Stage.RESUMED));
62             return activities.size() > 0;
63         });
64 
65         return activities.size() > 0;
66     }
67 
dumpView(View view)68     public static void dumpView(View view) {
69         dumpViewRecursive(view, 0, 0, 0);
70     }
71 
getFirstViewFromActivity(Activity activity)72     public static View getFirstViewFromActivity(Activity activity) {
73         return ((FragmentActivity) activity).getSupportFragmentManager().getFragments().get(
74                 0).getView();
75     }
76 
dumpViewRecursive(View view, int layer, int index, int total)77     private static void dumpViewRecursive(View view, int layer, int index, int total) {
78         if (view instanceof ViewGroup) {
79             Log.i(TAG, "L[" + layer + "] PARENT -> " + (index + 1) + "/" + total + " >> "
80                     + view.toString());
81             System.out.println(
82                     TAG + " L[" + layer + "] PARENT -> " + (index + 1) + "/" + total + " >> "
83                             + view.toString());
84             for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) {
85                 dumpViewRecursive(((ViewGroup) view).getChildAt(i), layer + 1, i + 1,
86                         ((ViewGroup) view).getChildCount());
87             }
88         } else {
89             Log.i(TAG, "L[" + layer + "] =END=  -> " + (index + 1) + "/" + total + " >> "
90                     + view.toString());
91         }
92     }
93 }
94