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.emergency;
18 
19 import android.content.Context;
20 import android.content.Intent;
21 import android.content.pm.ApplicationInfo;
22 import android.content.pm.PackageManager;
23 import android.content.pm.ResolveInfo;
24 import android.text.TextUtils;
25 import android.util.Log;
26 
27 import androidx.annotation.VisibleForTesting;
28 import androidx.preference.Preference;
29 
30 import com.android.settings.R;
31 import com.android.settings.core.BasePreferenceController;
32 
33 /**
34  * Preference controller for emergency gesture setting's entyrpoint preference
35  */
36 public class EmergencyGestureEntrypointPreferenceController extends BasePreferenceController {
37     private static final String TAG = "EmergencyGestureEntry";
38 
39     @VisibleForTesting
40     static final String ACTION_EMERGENCY_GESTURE_SETTINGS =
41             "com.android.settings.action.emergency_gesture_settings";
42     @VisibleForTesting
43     Intent mIntent;
44 
45     private boolean mUseCustomIntent;
46 
EmergencyGestureEntrypointPreferenceController(Context context, String key)47     public EmergencyGestureEntrypointPreferenceController(Context context, String key) {
48         super(context, key);
49         final String emergencyGestureSettingsPackageName = context.getResources().getString(
50                 R.string.emergency_gesture_settings_package);
51         if (!TextUtils.isEmpty(emergencyGestureSettingsPackageName)) {
52             final Intent intent = new Intent(ACTION_EMERGENCY_GESTURE_SETTINGS)
53                     .setPackage(emergencyGestureSettingsPackageName);
54             if (canResolveIntent(intent)) {
55                 // Use custom intent if it's configured and system can resolve it.
56                 mUseCustomIntent = true;
57                 mIntent = intent;
58             }
59         }
60     }
61 
62     @Override
updateState(Preference preference)63     public void updateState(Preference preference) {
64         super.updateState(preference);
65         final boolean canHandleClicks = canHandleClicks();
66         if (preference != null) {
67             preference.setEnabled(canHandleClicks);
68         }
69     }
70 
71     @Override
handlePreferenceTreeClick(Preference preference)72     public boolean handlePreferenceTreeClick(Preference preference) {
73         if (TextUtils.equals(getPreferenceKey(), preference.getKey()) && mIntent != null) {
74             mIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
75             mContext.startActivity(mIntent);
76             return true;
77         }
78         return super.handlePreferenceTreeClick(preference);
79     }
80 
81     @Override
getAvailabilityStatus()82     public int getAvailabilityStatus() {
83         final boolean isConfigEnabled = mContext.getResources()
84                 .getBoolean(R.bool.config_show_emergency_gesture_settings);
85 
86         if (!isConfigEnabled) {
87             return UNSUPPORTED_ON_DEVICE;
88         }
89         if (!canHandleClicks()) {
90             return UNSUPPORTED_ON_DEVICE;
91         }
92         return AVAILABLE;
93     }
94 
95     @Override
getSummary()96     public CharSequence getSummary() {
97         if (mUseCustomIntent) {
98             final String packageName = mContext.getResources().getString(
99                     R.string.emergency_gesture_settings_package);
100             try {
101                 final PackageManager pm = mContext.getPackageManager();
102                 final ApplicationInfo appInfo = pm.getApplicationInfo(
103                         packageName, PackageManager.MATCH_DISABLED_COMPONENTS
104                                 | PackageManager.MATCH_DISABLED_UNTIL_USED_COMPONENTS);
105                 return mContext.getString(R.string.emergency_gesture_entrypoint_summary,
106                         appInfo.loadLabel(pm));
107             } catch (Exception e) {
108                 Log.d(TAG, "Failed to get custom summary, falling back.");
109                 return super.getSummary();
110             }
111         }
112 
113         return super.getSummary();
114     }
115 
116     /**
117      * Whether or not gesture page content should be suppressed from search.
118      */
shouldSuppressFromSearch()119     public boolean shouldSuppressFromSearch() {
120         return mUseCustomIntent;
121     }
122 
123     /**
124      * Whether or not this setting can react to user click
125      */
canHandleClicks()126     private boolean canHandleClicks() {
127         return !mUseCustomIntent || mIntent != null;
128     }
129 
canResolveIntent(Intent intent)130     private boolean canResolveIntent(Intent intent) {
131         final ResolveInfo resolveActivity = mContext.getPackageManager()
132                 .resolveActivity(intent, 0);
133         return resolveActivity != null;
134     }
135 }
136