Refactor DefaultAppPicker to a general radio button picker

Bug: 36557316
Test: make RunSettingsRoboTests
Change-Id: I52985e527e55697cf29f8d97d775d4bbed025beb
This commit is contained in:
Fan Zhang
2017-03-23 11:03:29 -07:00
parent b3f13f9f32
commit a278962dbc
37 changed files with 580 additions and 398 deletions

View File

@@ -79,31 +79,30 @@ public class DefaultAssistPicker extends DefaultAppPickerFragment {
continue; continue;
} }
packages.add(packageName); packages.add(packageName);
candidates.add(new DefaultAppInfo(mUserId, info.component)); candidates.add(new DefaultAppInfo(mPm, mUserId, info.component));
} }
return candidates; return candidates;
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
final ComponentName cn = getCurrentAssist(); final ComponentName cn = getCurrentAssist();
if (cn != null) { if (cn != null) {
return new DefaultAppInfo(mUserId, cn).getKey(); return new DefaultAppInfo(mPm, mUserId, cn).getKey();
} }
return null; return null;
} }
@Override @Override
protected String getConfirmationMessage(DefaultAppInfo appInfo) { protected String getConfirmationMessage(CandidateInfo appInfo) {
if (appInfo == null) { if (appInfo == null) {
return null; return null;
} }
return getContext().getString(R.string.assistant_security_warning, return getContext().getString(R.string.assistant_security_warning, appInfo.loadLabel());
appInfo.loadLabel(mPm.getPackageManager()));
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
if (TextUtils.isEmpty(key)) { if (TextUtils.isEmpty(key)) {
setAssistNone(); setAssistNone();
return true; return true;

View File

@@ -83,6 +83,6 @@ public class DefaultAssistPreferenceController extends DefaultAppPreferenceContr
if (cn == null) { if (cn == null) {
return null; return null;
} }
return new DefaultAppInfo(mUserId, cn); return new DefaultAppInfo(mPackageManager, mUserId, cn);
} }
} }

View File

@@ -19,12 +19,12 @@ package com.android.settings.applications.assist;
import android.content.ComponentName; import android.content.ComponentName;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.pm.PackageManager;
import android.provider.Settings; import android.provider.Settings;
import android.text.TextUtils; import android.text.TextUtils;
import com.android.internal.app.AssistUtils; import com.android.internal.app.AssistUtils;
import com.android.internal.logging.nano.MetricsProto; import com.android.internal.logging.nano.MetricsProto;
import com.android.settings.applications.PackageManagerWrapper;
import com.android.settings.applications.defaultapps.DefaultAppInfo; import com.android.settings.applications.defaultapps.DefaultAppInfo;
import com.android.settings.applications.defaultapps.DefaultAppPickerFragment; import com.android.settings.applications.defaultapps.DefaultAppPickerFragment;
@@ -61,19 +61,19 @@ public class DefaultVoiceInputPicker extends DefaultAppPickerFragment {
for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) { for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) {
final boolean enabled = TextUtils.equals(info.key, mAssistRestrict); final boolean enabled = TextUtils.equals(info.key, mAssistRestrict);
hasEnabled |= enabled; hasEnabled |= enabled;
candidates.add(new VoiceInputDefaultAppInfo(mUserId, info, enabled)); candidates.add(new VoiceInputDefaultAppInfo(mPm, mUserId, info, enabled));
} }
final boolean assistIsService = !hasEnabled; final boolean assistIsService = !hasEnabled;
for (VoiceInputHelper.RecognizerInfo info : mHelper.mAvailableRecognizerInfos) { for (VoiceInputHelper.RecognizerInfo info : mHelper.mAvailableRecognizerInfos) {
final boolean enabled = !assistIsService; final boolean enabled = !assistIsService;
candidates.add(new VoiceInputDefaultAppInfo(mUserId, info, enabled)); candidates.add(new VoiceInputDefaultAppInfo(mPm, mUserId, info, enabled));
} }
return candidates; return candidates;
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
final ComponentName currentService = getCurrentService(mHelper); final ComponentName currentService = getCurrentService(mHelper);
if (currentService == null) { if (currentService == null) {
return null; return null;
@@ -82,7 +82,7 @@ public class DefaultVoiceInputPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected boolean setDefaultAppKey(String value) { protected boolean setDefaultKey(String value) {
for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) { for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) {
if (TextUtils.equals(value, info.key)) { if (TextUtils.equals(value, info.key)) {
Settings.Secure.putString(getContext().getContentResolver(), Settings.Secure.putString(getContext().getContentResolver(),
@@ -132,9 +132,9 @@ public class DefaultVoiceInputPicker extends DefaultAppPickerFragment {
public VoiceInputHelper.BaseInfo mInfo; public VoiceInputHelper.BaseInfo mInfo;
public VoiceInputDefaultAppInfo(int userId, VoiceInputHelper.BaseInfo info, public VoiceInputDefaultAppInfo(PackageManagerWrapper pm, int userId,
boolean enabled) { VoiceInputHelper.BaseInfo info, boolean enabled) {
super(userId, info.componentName, null /* summary */, enabled); super(pm, userId, info.componentName, null /* summary */, enabled);
mInfo = info; mInfo = info;
} }
@@ -144,7 +144,7 @@ public class DefaultVoiceInputPicker extends DefaultAppPickerFragment {
} }
@Override @Override
public CharSequence loadLabel(PackageManager pm) { public CharSequence loadLabel() {
if (mInfo instanceof VoiceInputHelper.InteractionInfo) { if (mInfo instanceof VoiceInputHelper.InteractionInfo) {
return mInfo.appLabel; return mInfo.appLabel;
} else { } else {

View File

@@ -104,14 +104,14 @@ public class DefaultVoiceInputPreferenceController extends DefaultAppPreferenceC
} }
for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) { for (VoiceInputHelper.InteractionInfo info : mHelper.mAvailableInteractionInfos) {
if (TextUtils.equals(defaultKey, info.key)) { if (TextUtils.equals(defaultKey, info.key)) {
return new DefaultVoiceInputPicker.VoiceInputDefaultAppInfo( return new DefaultVoiceInputPicker.VoiceInputDefaultAppInfo(mPackageManager,
mUserId, info, true /* enabled */); mUserId, info, true /* enabled */);
} }
} }
for (VoiceInputHelper.RecognizerInfo info : mHelper.mAvailableRecognizerInfos) { for (VoiceInputHelper.RecognizerInfo info : mHelper.mAvailableRecognizerInfos) {
if (TextUtils.equals(defaultKey, info.key)) { if (TextUtils.equals(defaultKey, info.key)) {
return new DefaultVoiceInputPicker.VoiceInputDefaultAppInfo( return new DefaultVoiceInputPicker.VoiceInputDefaultAppInfo(mPackageManager,
mUserId, info, true /* enabled */); mUserId, info, true /* enabled */);
} }
} }

View File

@@ -26,91 +26,101 @@ import android.graphics.drawable.Drawable;
import android.os.RemoteException; import android.os.RemoteException;
import android.os.UserHandle; import android.os.UserHandle;
import com.android.settings.applications.PackageManagerWrapper;
import com.android.settings.widget.RadioButtonPickerFragment;
/** /**
* Data model representing an app in DefaultAppPicker UI. * Data model representing an app in DefaultAppPicker UI.
*/ */
public class DefaultAppInfo { public class DefaultAppInfo extends RadioButtonPickerFragment.CandidateInfo {
public final int userId; public final int userId;
public final ComponentName componentName; public final ComponentName componentName;
public final PackageItemInfo packageItemInfo; public final PackageItemInfo packageItemInfo;
public final String summary; public final String summary;
public final boolean enabled; protected final PackageManagerWrapper mPm;
public DefaultAppInfo(int uid, ComponentName cn) { public DefaultAppInfo(PackageManagerWrapper pm, int uid, ComponentName cn) {
this(uid, cn, null /* summary */); this(pm, uid, cn, null /* summary */);
} }
public DefaultAppInfo(int uid, ComponentName cn, String summary) { public DefaultAppInfo(PackageManagerWrapper pm, int uid, ComponentName cn, String summary) {
this(uid, cn, summary, true /* enabled */); this(pm, uid, cn, summary, true /* enabled */);
} }
public DefaultAppInfo(int uid, ComponentName cn, String summary, boolean enabled) { public DefaultAppInfo(PackageManagerWrapper pm, int uid, ComponentName cn, String summary,
boolean enabled) {
super(enabled);
mPm = pm;
packageItemInfo = null; packageItemInfo = null;
userId = uid; userId = uid;
componentName = cn; componentName = cn;
this.summary = summary; this.summary = summary;
this.enabled = enabled;
} }
public DefaultAppInfo(PackageItemInfo info, String summary, boolean enabled) { public DefaultAppInfo(PackageManagerWrapper pm, PackageItemInfo info, String summary,
boolean enabled) {
super(enabled);
mPm = pm;
userId = UserHandle.myUserId(); userId = UserHandle.myUserId();
packageItemInfo = info; packageItemInfo = info;
componentName = null; componentName = null;
this.summary = summary; this.summary = summary;
this.enabled = enabled;
} }
public DefaultAppInfo(PackageItemInfo info) { public DefaultAppInfo(PackageManagerWrapper pm, PackageItemInfo info) {
this(info, null /* summary */, true /* enabled */); this(pm, info, null /* summary */, true /* enabled */);
} }
public CharSequence loadLabel(PackageManager pm) { @Override
public CharSequence loadLabel() {
if (componentName != null) { if (componentName != null) {
try { try {
final ActivityInfo actInfo = AppGlobals.getPackageManager().getActivityInfo( final ActivityInfo actInfo = AppGlobals.getPackageManager().getActivityInfo(
componentName, 0, userId); componentName, 0, userId);
if (actInfo != null) { if (actInfo != null) {
return actInfo.loadLabel(pm); return actInfo.loadLabel(mPm.getPackageManager());
} else { } else {
final ApplicationInfo appInfo = pm.getApplicationInfoAsUser( final ApplicationInfo appInfo = mPm.getApplicationInfoAsUser(
componentName.getPackageName(), 0, userId); componentName.getPackageName(), 0, userId);
return appInfo.loadLabel(pm); return appInfo.loadLabel(mPm.getPackageManager());
} }
} catch (RemoteException | PackageManager.NameNotFoundException e) { } catch (RemoteException | PackageManager.NameNotFoundException e) {
return null; return null;
} }
} else if (packageItemInfo != null) { } else if (packageItemInfo != null) {
return packageItemInfo.loadLabel(pm); return packageItemInfo.loadLabel(mPm.getPackageManager());
} else { } else {
return null; return null;
} }
} }
public Drawable loadIcon(PackageManager pm) { @Override
public Drawable loadIcon() {
if (componentName != null) { if (componentName != null) {
try { try {
final ActivityInfo actInfo = AppGlobals.getPackageManager().getActivityInfo( final ActivityInfo actInfo = AppGlobals.getPackageManager().getActivityInfo(
componentName, 0, userId); componentName, 0, userId);
if (actInfo != null) { if (actInfo != null) {
return actInfo.loadIcon(pm); return actInfo.loadIcon(mPm.getPackageManager());
} else { } else {
final ApplicationInfo appInfo = pm.getApplicationInfoAsUser( final ApplicationInfo appInfo = mPm.getApplicationInfoAsUser(
componentName.getPackageName(), 0, userId); componentName.getPackageName(), 0, userId);
return appInfo.loadIcon(pm); return appInfo.loadIcon(mPm.getPackageManager());
} }
} catch (RemoteException | PackageManager.NameNotFoundException e) { } catch (RemoteException | PackageManager.NameNotFoundException e) {
return null; return null;
} }
} }
if (packageItemInfo != null) { if (packageItemInfo != null) {
return packageItemInfo.loadIcon(pm); return packageItemInfo.loadIcon(mPm.getPackageManager());
} else { } else {
return null; return null;
} }
} }
@Override
public String getKey() { public String getKey() {
if (componentName != null) { if (componentName != null) {
return componentName.flattenToString(); return componentName.flattenToString();

View File

@@ -24,113 +24,36 @@ import android.app.Fragment;
import android.content.Context; import android.content.Context;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.os.Bundle; import android.os.Bundle;
import android.os.UserHandle;
import android.os.UserManager;
import android.support.annotation.VisibleForTesting;
import android.support.v7.preference.Preference;
import android.support.v7.preference.PreferenceScreen;
import android.text.TextUtils; import android.text.TextUtils;
import android.util.ArrayMap;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import com.android.internal.logging.nano.MetricsProto; import com.android.internal.logging.nano.MetricsProto;
import com.android.settings.R; import com.android.settings.R;
import com.android.settings.Utils;
import com.android.settings.applications.PackageManagerWrapper; import com.android.settings.applications.PackageManagerWrapper;
import com.android.settings.applications.PackageManagerWrapperImpl; import com.android.settings.applications.PackageManagerWrapperImpl;
import com.android.settings.core.InstrumentedPreferenceFragment;
import com.android.settings.core.instrumentation.InstrumentedDialogFragment; import com.android.settings.core.instrumentation.InstrumentedDialogFragment;
import com.android.settings.widget.RadioButtonPickerFragment;
import com.android.settings.widget.RadioButtonPreference; import com.android.settings.widget.RadioButtonPreference;
import java.util.List;
import java.util.Map;
/** /**
* A generic app picker fragment that shows a list of app as radio button group. * A generic app picker fragment that shows a list of app as radio button group.
*/ */
public abstract class DefaultAppPickerFragment extends InstrumentedPreferenceFragment implements public abstract class DefaultAppPickerFragment extends RadioButtonPickerFragment {
RadioButtonPreference.OnClickListener {
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
static final String EXTRA_FOR_WORK = "for_work";
private final Map<String, DefaultAppInfo> mCandidates = new ArrayMap<>();
protected PackageManagerWrapper mPm; protected PackageManagerWrapper mPm;
protected UserManager mUserManager;
protected int mUserId;
@Override @Override
public void onAttach(Context context) { public void onAttach(Context context) {
super.onAttach(context); super.onAttach(context);
mPm = new PackageManagerWrapperImpl(context.getPackageManager()); mPm = new PackageManagerWrapperImpl(context.getPackageManager());
mUserManager = (UserManager) context.getSystemService(Context.USER_SERVICE);
final Bundle arguments = getArguments();
boolean mForWork = false;
if (arguments != null) {
mForWork = arguments.getBoolean(EXTRA_FOR_WORK);
}
final UserHandle managedProfile = Utils.getManagedProfile(mUserManager);
mUserId = mForWork && managedProfile != null
? managedProfile.getIdentifier()
: UserHandle.myUserId();
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
final View view = super.onCreateView(inflater, container, savedInstanceState);
setHasOptionsMenu(true);
return view;
}
@Override
public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
super.onCreatePreferences(savedInstanceState, rootKey);
addPreferencesFromResource(R.xml.app_picker_prefs);
updateCandidates();
}
@VisibleForTesting
public void updateCandidates() {
mCandidates.clear();
final List<? extends DefaultAppInfo> candidateList = getCandidates();
if (candidateList != null) {
for (DefaultAppInfo info : candidateList) {
mCandidates.put(info.getKey(), info);
}
}
final String defaultAppKey = getDefaultAppKey();
final String systemDefaultAppKey = getSystemDefaultAppKey();
final PreferenceScreen screen = getPreferenceScreen();
screen.removeAll();
if (shouldShowItemNone()) {
final RadioButtonPreference nonePref = new RadioButtonPreference(getPrefContext());
nonePref.setIcon(R.drawable.ic_remove_circle);
nonePref.setTitle(R.string.app_list_preference_none);
nonePref.setChecked(TextUtils.isEmpty(defaultAppKey));
nonePref.setOnClickListener(this);
screen.addPreference(nonePref);
}
for (Map.Entry<String, DefaultAppInfo> app : mCandidates.entrySet()) {
RadioButtonPreference pref = new RadioButtonPreference(getPrefContext());
configurePreferenceFromAppInfo(
pref, app.getKey(), app.getValue(), defaultAppKey, systemDefaultAppKey);
screen.addPreference(pref);
}
mayCheckOnlyRadioButton();
} }
@Override @Override
public void onRadioButtonClicked(RadioButtonPreference selected) { public void onRadioButtonClicked(RadioButtonPreference selected) {
final String selectedKey = selected.getKey(); final String selectedKey = selected.getKey();
final String confirmationMessage = getConfirmationMessage(mCandidates.get(selectedKey)); final String confirmationMessage = getConfirmationMessage(getCandidate(selectedKey));
final Activity activity = getActivity(); final Activity activity = getActivity();
if (TextUtils.isEmpty(confirmationMessage)) { if (TextUtils.isEmpty(confirmationMessage)) {
onRadioButtonConfirmed(selectedKey); super.onRadioButtonClicked(selected);
} else if (activity != null) { } else if (activity != null) {
final DialogFragment fragment = ConfirmationDialogFragment.newInstance( final DialogFragment fragment = ConfirmationDialogFragment.newInstance(
this, selectedKey, confirmationMessage); this, selectedKey, confirmationMessage);
@@ -138,63 +61,21 @@ public abstract class DefaultAppPickerFragment extends InstrumentedPreferenceFra
} }
} }
private void onRadioButtonConfirmed(String selectedKey) {
final boolean success = setDefaultAppKey(selectedKey);
if (success) {
updateCheckedState(selectedKey);
}
onSelectionPerformed(success);
}
@VisibleForTesting @Override
public void updateCheckedState(String selectedKey) { public void bindPreferenceExtra(RadioButtonPreference pref,
final PreferenceScreen screen = getPreferenceScreen(); String key, CandidateInfo info, String defaultKey, String systemDefaultKey) {
if (screen != null) { if (!(info instanceof DefaultAppInfo)) {
final int count = screen.getPreferenceCount(); return;
for (int i = 0; i < count; i++) { }
final Preference pref = screen.getPreference(i); if (TextUtils.equals(systemDefaultKey, key)) {
if (pref instanceof RadioButtonPreference) { pref.setSummary(R.string.system_app);
final RadioButtonPreference radioPref = (RadioButtonPreference) pref; } else if (!TextUtils.isEmpty(((DefaultAppInfo) info).summary)) {
final boolean newCheckedState = TextUtils.equals(pref.getKey(), selectedKey); pref.setSummary(((DefaultAppInfo) info).summary);
if (radioPref.isChecked() != newCheckedState) {
radioPref.setChecked(TextUtils.equals(pref.getKey(), selectedKey));
}
}
}
} }
} }
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE) protected String getConfirmationMessage(CandidateInfo info) {
void mayCheckOnlyRadioButton() {
final PreferenceScreen screen = getPreferenceScreen();
// If there is only 1 thing on screen, select it.
if (screen != null && screen.getPreferenceCount() == 1) {
final Preference onlyPref = screen.getPreference(0);
if (onlyPref instanceof RadioButtonPreference) {
((RadioButtonPreference) onlyPref).setChecked(true);
}
}
}
protected boolean shouldShowItemNone() {
return false;
}
protected String getSystemDefaultAppKey() {
return null;
}
protected abstract List<? extends DefaultAppInfo> getCandidates();
protected abstract String getDefaultAppKey();
protected abstract boolean setDefaultAppKey(String key);
// Called after the user tries to select an item.
protected void onSelectionPerformed(boolean success) {
}
protected String getConfirmationMessage(DefaultAppInfo appInfo) {
return null; return null;
} }
@@ -241,23 +122,4 @@ public abstract class DefaultAppPickerFragment extends InstrumentedPreferenceFra
} }
} }
} }
@VisibleForTesting
public RadioButtonPreference configurePreferenceFromAppInfo(RadioButtonPreference pref,
String appKey, DefaultAppInfo info, String defaultAppKey, String systemDefaultAppKey) {
pref.setTitle(info.loadLabel(mPm.getPackageManager()));
pref.setIcon(info.loadIcon(mPm.getPackageManager()));
pref.setKey(appKey);
if (TextUtils.equals(defaultAppKey, appKey)) {
pref.setChecked(true);
}
if (TextUtils.equals(systemDefaultAppKey, appKey)) {
pref.setSummary(R.string.system_app);
} else if (!TextUtils.isEmpty(info.summary)) {
pref.setSummary(info.summary);
}
pref.setEnabled(info.enabled);
pref.setOnClickListener(this);
return pref;
}
} }

View File

@@ -51,7 +51,7 @@ public abstract class DefaultAppPreferenceController extends PreferenceControlle
final DefaultAppInfo app = getDefaultAppInfo(); final DefaultAppInfo app = getDefaultAppInfo();
CharSequence defaultAppLabel = null; CharSequence defaultAppLabel = null;
if (app != null) { if (app != null) {
defaultAppLabel = app.loadLabel(mPackageManager.getPackageManager()); defaultAppLabel = app.loadLabel();
} }
if (!TextUtils.isEmpty(defaultAppLabel)) { if (!TextUtils.isEmpty(defaultAppLabel)) {
preference.setSummary(defaultAppLabel); preference.setSummary(defaultAppLabel);

View File

@@ -56,34 +56,34 @@ public class DefaultAutofillPicker extends DefaultAppPickerFragment {
final List<ResolveInfo> resolveInfos = mPm.getPackageManager() final List<ResolveInfo> resolveInfos = mPm.getPackageManager()
.queryIntentServices(AUTOFILL_PROBE, PackageManager.GET_META_DATA); .queryIntentServices(AUTOFILL_PROBE, PackageManager.GET_META_DATA);
for (ResolveInfo info : resolveInfos) { for (ResolveInfo info : resolveInfos) {
candidates.add(new DefaultAppInfo(mUserId, new ComponentName( candidates.add(new DefaultAppInfo(mPm, mUserId, new ComponentName(
info.serviceInfo.packageName, info.serviceInfo.name))); info.serviceInfo.packageName, info.serviceInfo.name)));
} }
final List<ResolveInfo> oldResolveInfos = mPm.getPackageManager() final List<ResolveInfo> oldResolveInfos = mPm.getPackageManager()
.queryIntentServices(OLD_AUTO_FILL_PROBE, PackageManager.GET_META_DATA); .queryIntentServices(OLD_AUTO_FILL_PROBE, PackageManager.GET_META_DATA);
for (ResolveInfo info : oldResolveInfos) { for (ResolveInfo info : oldResolveInfos) {
candidates.add(new DefaultAppInfo(mUserId, new ComponentName( candidates.add(new DefaultAppInfo(mPm, mUserId, new ComponentName(
info.serviceInfo.packageName, info.serviceInfo.name))); info.serviceInfo.packageName, info.serviceInfo.name)));
} }
return candidates; return candidates;
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return Settings.Secure.getString(getContext().getContentResolver(), SETTING); return Settings.Secure.getString(getContext().getContentResolver(), SETTING);
} }
@Override @Override
protected String getConfirmationMessage(DefaultAppInfo appInfo) { protected String getConfirmationMessage(CandidateInfo appInfo) {
if (appInfo == null) { if (appInfo == null) {
return null; return null;
} }
final CharSequence appName = appInfo.loadLabel(mPm.getPackageManager()); final CharSequence appName = appInfo.loadLabel();
return getContext().getString(R.string.autofill_confirmation_message, appName); return getContext().getString(R.string.autofill_confirmation_message, appName);
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
Settings.Secure.putString(getContext().getContentResolver(), SETTING, key); Settings.Secure.putString(getContext().getContentResolver(), SETTING, key);
return true; return true;
} }

View File

@@ -54,7 +54,7 @@ public class DefaultAutofillPreferenceController extends DefaultAppPreferenceCon
final String flattenComponent = Settings.Secure.getString(mContext.getContentResolver(), final String flattenComponent = Settings.Secure.getString(mContext.getContentResolver(),
DefaultAutofillPicker.SETTING); DefaultAutofillPicker.SETTING);
if (!TextUtils.isEmpty(flattenComponent)) { if (!TextUtils.isEmpty(flattenComponent)) {
DefaultAppInfo appInfo = new DefaultAppInfo( DefaultAppInfo appInfo = new DefaultAppInfo(mPackageManager,
mUserId, ComponentName.unflattenFromString(flattenComponent)); mUserId, ComponentName.unflattenFromString(flattenComponent));
return appInfo; return appInfo;
} }

View File

@@ -35,12 +35,12 @@ public class DefaultBrowserPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return mPm.getDefaultBrowserPackageNameAsUser(mUserId); return mPm.getDefaultBrowserPackageNameAsUser(mUserId);
} }
@Override @Override
protected boolean setDefaultAppKey(String packageName) { protected boolean setDefaultKey(String packageName) {
return mPm.setDefaultBrowserPackageNameAsUser(packageName, mUserId); return mPm.setDefaultBrowserPackageNameAsUser(packageName, mUserId);
} }
@@ -59,7 +59,7 @@ public class DefaultBrowserPicker extends DefaultAppPickerFragment {
continue; continue;
} }
try { try {
candidates.add(new DefaultAppInfo( candidates.add(new DefaultAppInfo(mPm,
mPm.getApplicationInfoAsUser(info.activityInfo.packageName, 0, mUserId))); mPm.getApplicationInfoAsUser(info.activityInfo.packageName, 0, mUserId)));
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
// Skip unknown packages. // Skip unknown packages.

View File

@@ -52,8 +52,7 @@ public class DefaultBrowserPreferenceController extends DefaultAppPreferenceCont
public void updateState(Preference preference) { public void updateState(Preference preference) {
super.updateState(preference); super.updateState(preference);
final DefaultAppInfo defaultApp = getDefaultAppInfo(); final DefaultAppInfo defaultApp = getDefaultAppInfo();
final CharSequence defaultAppLabel = defaultApp != null final CharSequence defaultAppLabel = defaultApp != null ? defaultApp.loadLabel() : null;
? defaultApp.loadLabel(mPackageManager.getPackageManager()) : null;
if (TextUtils.isEmpty(defaultAppLabel)) { if (TextUtils.isEmpty(defaultAppLabel)) {
final String onlyAppLabel = getOnlyAppLabel(); final String onlyAppLabel = getOnlyAppLabel();
if (!TextUtils.isEmpty(onlyAppLabel)) { if (!TextUtils.isEmpty(onlyAppLabel)) {
@@ -65,8 +64,9 @@ public class DefaultBrowserPreferenceController extends DefaultAppPreferenceCont
@Override @Override
protected DefaultAppInfo getDefaultAppInfo() { protected DefaultAppInfo getDefaultAppInfo() {
try { try {
return new DefaultAppInfo(mPackageManager.getPackageManager().getApplicationInfo( return new DefaultAppInfo(mPackageManager,
mPackageManager.getDefaultBrowserPackageNameAsUser(mUserId), 0)); mPackageManager.getPackageManager().getApplicationInfo(
mPackageManager.getDefaultBrowserPackageNameAsUser(mUserId), 0));
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
return null; return null;
} }

View File

@@ -49,7 +49,7 @@ public class DefaultEmergencyPicker extends DefaultAppPickerFragment {
final PackageInfo packageInfo = final PackageInfo packageInfo =
mPm.getPackageManager().getPackageInfo(info.activityInfo.packageName, 0); mPm.getPackageManager().getPackageInfo(info.activityInfo.packageName, 0);
final ApplicationInfo appInfo = packageInfo.applicationInfo; final ApplicationInfo appInfo = packageInfo.applicationInfo;
candidates.add(new DefaultAppInfo(appInfo)); candidates.add(new DefaultAppInfo(mPm, appInfo));
// Get earliest installed system app. // Get earliest installed system app.
if (isSystemApp(appInfo) && (bestMatch == null || if (isSystemApp(appInfo) && (bestMatch == null ||
bestMatch.firstInstallTime > packageInfo.firstInstallTime)) { bestMatch.firstInstallTime > packageInfo.firstInstallTime)) {
@@ -59,9 +59,9 @@ public class DefaultEmergencyPicker extends DefaultAppPickerFragment {
// Skip unknown packages. // Skip unknown packages.
} }
if (bestMatch != null) { if (bestMatch != null) {
final String defaultKey = getDefaultAppKey(); final String defaultKey = getDefaultKey();
if (TextUtils.isEmpty(defaultKey)) { if (TextUtils.isEmpty(defaultKey)) {
setDefaultAppKey(bestMatch.packageName); setDefaultKey(bestMatch.packageName);
} }
} }
} }
@@ -69,19 +69,19 @@ public class DefaultEmergencyPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getConfirmationMessage(DefaultAppInfo info) { protected String getConfirmationMessage(CandidateInfo info) {
return Utils.isPackageDirectBootAware(getContext(), info.getKey()) ? null return Utils.isPackageDirectBootAware(getContext(), info.getKey()) ? null
: getContext().getString(R.string.direct_boot_unaware_dialog_message); : getContext().getString(R.string.direct_boot_unaware_dialog_message);
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return Settings.Secure.getString(getContext().getContentResolver(), return Settings.Secure.getString(getContext().getContentResolver(),
Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION); Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION);
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
final ContentResolver contentResolver = getContext().getContentResolver(); final ContentResolver contentResolver = getContext().getContentResolver();
final String previousValue = Settings.Secure.getString(contentResolver, final String previousValue = Settings.Secure.getString(contentResolver,
Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION); Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION);

View File

@@ -68,14 +68,15 @@ public class DefaultHomePicker extends DefaultAppPickerFragment {
} else { } else {
summary = null; summary = null;
} }
final DefaultAppInfo candidate = new DefaultAppInfo(mUserId, activityName, summary); final DefaultAppInfo candidate =
new DefaultAppInfo(mPm, mUserId, activityName, summary);
candidates.add(candidate); candidates.add(candidate);
} }
return candidates; return candidates;
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
final ArrayList<ResolveInfo> homeActivities = new ArrayList<>(); final ArrayList<ResolveInfo> homeActivities = new ArrayList<>();
final ComponentName currentDefaultHome = mPm.getHomeActivities(homeActivities); final ComponentName currentDefaultHome = mPm.getHomeActivities(homeActivities);
if (currentDefaultHome != null) { if (currentDefaultHome != null) {
@@ -85,7 +86,7 @@ public class DefaultHomePicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
if (!TextUtils.isEmpty(key)) { if (!TextUtils.isEmpty(key)) {
final ComponentName component = ComponentName.unflattenFromString(key); final ComponentName component = ComponentName.unflattenFromString(key);
final List<ResolveInfo> homeActivities = new ArrayList<>(); final List<ResolveInfo> homeActivities = new ArrayList<>();

View File

@@ -60,8 +60,7 @@ public class DefaultHomePreferenceController extends DefaultAppPreferenceControl
public void updateState(Preference preference) { public void updateState(Preference preference) {
super.updateState(preference); super.updateState(preference);
final DefaultAppInfo defaultApp = getDefaultAppInfo(); final DefaultAppInfo defaultApp = getDefaultAppInfo();
final CharSequence defaultAppLabel = defaultApp != null final CharSequence defaultAppLabel = defaultApp != null ? defaultApp.loadLabel() : null;
? defaultApp.loadLabel(mPackageManager.getPackageManager()) : null;
if (TextUtils.isEmpty(defaultAppLabel)) { if (TextUtils.isEmpty(defaultAppLabel)) {
final String onlyAppLabel = getOnlyAppLabel(); final String onlyAppLabel = getOnlyAppLabel();
if (!TextUtils.isEmpty(onlyAppLabel)) { if (!TextUtils.isEmpty(onlyAppLabel)) {
@@ -75,7 +74,7 @@ public class DefaultHomePreferenceController extends DefaultAppPreferenceControl
final ArrayList<ResolveInfo> homeActivities = new ArrayList<>(); final ArrayList<ResolveInfo> homeActivities = new ArrayList<>();
final ComponentName currentDefaultHome = mPackageManager.getHomeActivities(homeActivities); final ComponentName currentDefaultHome = mPackageManager.getHomeActivities(homeActivities);
return new DefaultAppInfo(mUserId, currentDefaultHome); return new DefaultAppInfo(mPackageManager, mUserId, currentDefaultHome);
} }
private String getOnlyAppLabel() { private String getOnlyAppLabel() {

View File

@@ -43,12 +43,12 @@ public class DefaultNotificationAssistantPicker extends DefaultAppPickerFragment
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return Settings.Secure.getString(getContext().getContentResolver(), mConfig.setting); return Settings.Secure.getString(getContext().getContentResolver(), mConfig.setting);
} }
@Override @Override
protected boolean setDefaultAppKey(String value) { protected boolean setDefaultKey(String value) {
Settings.Secure.putString(getContext().getContentResolver(), mConfig.setting, value); Settings.Secure.putString(getContext().getContentResolver(), mConfig.setting, value);
return true; return true;
} }
@@ -75,7 +75,7 @@ public class DefaultNotificationAssistantPicker extends DefaultAppPickerFragment
continue; continue;
} }
candidates.add(new DefaultAppInfo( candidates.add(new DefaultAppInfo(mPm,
mUserId, new ComponentName(info.packageName, info.name))); mUserId, new ComponentName(info.packageName, info.name)));
} }
return candidates; return candidates;

View File

@@ -50,7 +50,7 @@ public class DefaultPhonePicker extends DefaultAppPickerFragment {
DefaultDialerManager.getInstalledDialerApplications(getContext(), mUserId); DefaultDialerManager.getInstalledDialerApplications(getContext(), mUserId);
for (String packageName : dialerPackages) { for (String packageName : dialerPackages) {
try { try {
candidates.add(new DefaultAppInfo( candidates.add(new DefaultAppInfo(mPm,
mPm.getApplicationInfoAsUser(packageName, 0, mUserId))); mPm.getApplicationInfoAsUser(packageName, 0, mUserId)));
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
// Skip unknown packages. // Skip unknown packages.
@@ -60,18 +60,18 @@ public class DefaultPhonePicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return mDefaultKeyUpdater.getDefaultDialerApplication(getContext(), mUserId); return mDefaultKeyUpdater.getDefaultDialerApplication(getContext(), mUserId);
} }
@Override @Override
protected String getSystemDefaultAppKey() { protected String getSystemDefaultKey() {
return mDefaultKeyUpdater.getSystemDialerPackage(); return mDefaultKeyUpdater.getSystemDialerPackage();
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
if (!TextUtils.isEmpty(key) && !TextUtils.equals(key, getDefaultAppKey())) { if (!TextUtils.isEmpty(key) && !TextUtils.equals(key, getDefaultKey())) {
return mDefaultKeyUpdater.setDefaultDialerApplication(getContext(), key, mUserId); return mDefaultKeyUpdater.setDefaultDialerApplication(getContext(), key, mUserId);
} }
return false; return false;

View File

@@ -57,8 +57,10 @@ public class DefaultPhonePreferenceController extends DefaultAppPreferenceContro
@Override @Override
protected DefaultAppInfo getDefaultAppInfo() { protected DefaultAppInfo getDefaultAppInfo() {
try { try {
return new DefaultAppInfo(mPackageManager.getPackageManager().getApplicationInfo( return new DefaultAppInfo(mPackageManager,
DefaultDialerManager.getDefaultDialerApplication(mContext, mUserId), 0)); mPackageManager.getPackageManager().getApplicationInfo(
DefaultDialerManager.getDefaultDialerApplication(mContext, mUserId),
0));
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
return null; return null;
} }

View File

@@ -47,7 +47,7 @@ public class DefaultSmsPicker extends DefaultAppPickerFragment {
for (SmsApplication.SmsApplicationData smsApplicationData : smsApplications) { for (SmsApplication.SmsApplicationData smsApplicationData : smsApplications) {
try { try {
candidates.add(new DefaultAppInfo( candidates.add(new DefaultAppInfo(mPm,
mPm.getApplicationInfoAsUser(smsApplicationData.mPackageName, 0, mUserId))); mPm.getApplicationInfoAsUser(smsApplicationData.mPackageName, 0, mUserId)));
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
// Skip unknown packages. // Skip unknown packages.
@@ -58,13 +58,13 @@ public class DefaultSmsPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return mDefaultKeyUpdater.getDefaultApplication(getContext()); return mDefaultKeyUpdater.getDefaultApplication(getContext());
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
if (!TextUtils.isEmpty(key) && !TextUtils.equals(key, getDefaultAppKey())) { if (!TextUtils.isEmpty(key) && !TextUtils.equals(key, getDefaultKey())) {
mDefaultKeyUpdater.setDefaultApplication(getContext(), key); mDefaultKeyUpdater.setDefaultApplication(getContext(), key);
return true; return true;
} }
@@ -72,7 +72,7 @@ public class DefaultSmsPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getConfirmationMessage(DefaultAppInfo info) { protected String getConfirmationMessage(CandidateInfo info) {
return Utils.isPackageDirectBootAware(getContext(), info.getKey()) ? null return Utils.isPackageDirectBootAware(getContext(), info.getKey()) ? null
: getContext().getString(R.string.direct_boot_unaware_dialog_message); : getContext().getString(R.string.direct_boot_unaware_dialog_message);
} }

View File

@@ -47,7 +47,7 @@ public class DefaultSmsPreferenceController extends DefaultAppPreferenceControll
protected DefaultAppInfo getDefaultAppInfo() { protected DefaultAppInfo getDefaultAppInfo() {
final ComponentName app = SmsApplication.getDefaultSmsApplication(mContext, true); final ComponentName app = SmsApplication.getDefaultSmsApplication(mContext, true);
if (app != null) { if (app != null) {
return new DefaultAppInfo(mUserId, app); return new DefaultAppInfo(mPackageManager, mUserId, app);
} }
return null; return null;
} }

View File

@@ -16,6 +16,8 @@
package com.android.settings.location; package com.android.settings.location;
import static com.android.settingslib.RestrictedLockUtils.EnforcedAdmin;
import android.app.Activity; import android.app.Activity;
import android.content.BroadcastReceiver; import android.content.BroadcastReceiver;
import android.content.Context; import android.content.Context;
@@ -49,8 +51,6 @@ import java.util.Collections;
import java.util.Comparator; import java.util.Comparator;
import java.util.List; import java.util.List;
import static com.android.settingslib.RestrictedLockUtils.EnforcedAdmin;
/** /**
* System location settings (Settings &gt; Location). The screen has three parts: * System location settings (Settings &gt; Location). The screen has three parts:
* <ul> * <ul>

View File

@@ -19,17 +19,18 @@ package com.android.settings.webview;
import static android.provider.Settings.ACTION_WEBVIEW_SETTINGS; import static android.provider.Settings.ACTION_WEBVIEW_SETTINGS;
import android.app.Activity; import android.app.Activity;
import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.pm.ApplicationInfo; import android.content.pm.ApplicationInfo;
import android.content.pm.PackageItemInfo;
import android.content.pm.PackageInfo; import android.content.pm.PackageInfo;
import android.content.pm.PackageItemInfo;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.content.Context;
import android.support.annotation.VisibleForTesting; import android.support.annotation.VisibleForTesting;
import android.text.TextUtils; import android.text.TextUtils;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.settings.R; import com.android.settings.R;
import com.android.settings.applications.PackageManagerWrapper;
import com.android.settings.applications.defaultapps.DefaultAppInfo; import com.android.settings.applications.defaultapps.DefaultAppInfo;
import com.android.settings.applications.defaultapps.DefaultAppPickerFragment; import com.android.settings.applications.defaultapps.DefaultAppPickerFragment;
@@ -61,7 +62,7 @@ public class WebViewAppPicker extends DefaultAppPickerFragment {
List<ApplicationInfo> pkgs = List<ApplicationInfo> pkgs =
getWebViewUpdateServiceWrapper().getValidWebViewApplicationInfos(getContext()); getWebViewUpdateServiceWrapper().getValidWebViewApplicationInfos(getContext());
for (ApplicationInfo ai : pkgs) { for (ApplicationInfo ai : pkgs) {
packageInfoList.add(createDefaultAppInfo(ai, packageInfoList.add(createDefaultAppInfo(mPm, ai,
getDisabledReason(getWebViewUpdateServiceWrapper(), getDisabledReason(getWebViewUpdateServiceWrapper(),
getContext(), ai.packageName))); getContext(), ai.packageName)));
} }
@@ -69,12 +70,12 @@ public class WebViewAppPicker extends DefaultAppPickerFragment {
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
PackageInfo currentPackage = getWebViewUpdateServiceWrapper().getCurrentWebViewPackage(); PackageInfo currentPackage = getWebViewUpdateServiceWrapper().getCurrentWebViewPackage();
return currentPackage == null ? null : currentPackage.packageName; return currentPackage == null ? null : currentPackage.packageName;
} }
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
boolean success = getWebViewUpdateServiceWrapper().setWebViewProvider(key); boolean success = getWebViewUpdateServiceWrapper().setWebViewProvider(key);
return success; return success;
} }
@@ -110,25 +111,28 @@ public class WebViewAppPicker extends DefaultAppPickerFragment {
} }
private static class WebViewAppInfo extends DefaultAppInfo { private static class WebViewAppInfo extends DefaultAppInfo {
public WebViewAppInfo(PackageItemInfo packageItemInfo, String summary, boolean enabled) { public WebViewAppInfo(PackageManagerWrapper pm, PackageItemInfo packageItemInfo,
super(packageItemInfo, summary, enabled); String summary, boolean enabled) {
super(pm, packageItemInfo, summary, enabled);
} }
@Override @Override
public CharSequence loadLabel(PackageManager pm) { public CharSequence loadLabel() {
String versionName = ""; String versionName = "";
try { try {
versionName = pm.getPackageInfo(packageItemInfo.packageName, 0).versionName; versionName = mPm.getPackageManager().
getPackageInfo(packageItemInfo.packageName, 0).versionName;
} catch (PackageManager.NameNotFoundException e) { } catch (PackageManager.NameNotFoundException e) {
} }
return String.format("%s %s", super.loadLabel(pm), versionName); return String.format("%s %s", super.loadLabel(), versionName);
} }
} }
@VisibleForTesting @VisibleForTesting
DefaultAppInfo createDefaultAppInfo(PackageItemInfo packageItemInfo, String disabledReason) { DefaultAppInfo createDefaultAppInfo(PackageManagerWrapper pm, PackageItemInfo packageItemInfo,
return new WebViewAppInfo(packageItemInfo, disabledReason, String disabledReason) {
return new WebViewAppInfo(pm, packageItemInfo, disabledReason,
TextUtils.isEmpty(disabledReason) /* enabled */); TextUtils.isEmpty(disabledReason) /* enabled */);
} }
@@ -139,7 +143,6 @@ public class WebViewAppPicker extends DefaultAppPickerFragment {
@VisibleForTesting @VisibleForTesting
String getDisabledReason(WebViewUpdateServiceWrapper webviewUpdateServiceWrapper, String getDisabledReason(WebViewUpdateServiceWrapper webviewUpdateServiceWrapper,
Context context, String packageName) { Context context, String packageName) {
StringBuilder disabledReason = new StringBuilder();
List<UserPackageWrapper> userPackages = List<UserPackageWrapper> userPackages =
webviewUpdateServiceWrapper.getPackageInfosAllUsers(context, packageName); webviewUpdateServiceWrapper.getPackageInfosAllUsers(context, packageName);
for (UserPackageWrapper userPackage : userPackages) { for (UserPackageWrapper userPackage : userPackages) {
@@ -150,7 +153,7 @@ public class WebViewAppPicker extends DefaultAppPickerFragment {
} else if (!userPackage.isEnabledPackage()) { } else if (!userPackage.isEnabledPackage()) {
// Package disabled // Package disabled
return context.getString( return context.getString(
R.string.webview_disabled_for_user, userPackage.getUserInfo().name); R.string.webview_disabled_for_user, userPackage.getUserInfo().name);
} }
} }
return null; return null;

View File

@@ -26,9 +26,9 @@ public class WebViewAppPreferenceController extends DefaultAppPreferenceControll
private static final String WEBVIEW_APP_KEY = "select_webview_provider"; private static final String WEBVIEW_APP_KEY = "select_webview_provider";
private Context mContext; private final Context mContext;
private Preference mPreference;
private final WebViewUpdateServiceWrapper mWebViewUpdateServiceWrapper; private final WebViewUpdateServiceWrapper mWebViewUpdateServiceWrapper;
private Preference mPreference;
public WebViewAppPreferenceController(Context context) { public WebViewAppPreferenceController(Context context) {
this(context, new WebViewUpdateServiceWrapper()); this(context, new WebViewUpdateServiceWrapper());
@@ -44,7 +44,8 @@ public class WebViewAppPreferenceController extends DefaultAppPreferenceControll
@Override @Override
public DefaultAppInfo getDefaultAppInfo() { public DefaultAppInfo getDefaultAppInfo() {
PackageInfo currentPackage = mWebViewUpdateServiceWrapper.getCurrentWebViewPackage(); PackageInfo currentPackage = mWebViewUpdateServiceWrapper.getCurrentWebViewPackage();
return new DefaultAppInfo(currentPackage == null ? null : currentPackage.applicationInfo); return new DefaultAppInfo(mPackageManager,
currentPackage == null ? null : currentPackage.applicationInfo);
} }
@Override @Override

View File

@@ -0,0 +1,221 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.settings.widget;
import android.content.Context;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.os.UserHandle;
import android.os.UserManager;
import android.support.annotation.VisibleForTesting;
import android.support.v7.preference.Preference;
import android.support.v7.preference.PreferenceScreen;
import android.text.TextUtils;
import android.util.ArrayMap;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import com.android.settings.R;
import com.android.settings.Utils;
import com.android.settings.core.InstrumentedPreferenceFragment;
import java.util.List;
import java.util.Map;
public abstract class RadioButtonPickerFragment extends InstrumentedPreferenceFragment implements
RadioButtonPreference.OnClickListener {
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
static final String EXTRA_FOR_WORK = "for_work";
private final Map<String, CandidateInfo> mCandidates = new ArrayMap<>();
protected UserManager mUserManager;
protected int mUserId;
@Override
public void onAttach(Context context) {
super.onAttach(context);
mUserManager = (UserManager) context.getSystemService(Context.USER_SERVICE);
final Bundle arguments = getArguments();
boolean mForWork = false;
if (arguments != null) {
mForWork = arguments.getBoolean(EXTRA_FOR_WORK);
}
final UserHandle managedProfile = Utils.getManagedProfile(mUserManager);
mUserId = mForWork && managedProfile != null
? managedProfile.getIdentifier()
: UserHandle.myUserId();
}
@Override
public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
super.onCreatePreferences(savedInstanceState, rootKey);
addPreferencesFromResource(R.xml.placeholder_prefs);
updateCandidates();
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
final View view = super.onCreateView(inflater, container, savedInstanceState);
setHasOptionsMenu(true);
return view;
}
@Override
public void onRadioButtonClicked(RadioButtonPreference selected) {
final String selectedKey = selected.getKey();
onRadioButtonConfirmed(selectedKey);
}
/**
* Called after the user tries to select an item.
*/
protected void onSelectionPerformed(boolean success) {
}
/**
* Whether the UI should show a "None" item selection.
*/
protected boolean shouldShowItemNone() {
return false;
}
protected CandidateInfo getCandidate(String key) {
return mCandidates.get(key);
}
protected void onRadioButtonConfirmed(String selectedKey) {
final boolean success = setDefaultKey(selectedKey);
if (success) {
updateCheckedState(selectedKey);
}
onSelectionPerformed(success);
}
/**
* A chance for subclasses to bind additional things to the preference.
*/
@VisibleForTesting(otherwise = VisibleForTesting.PROTECTED)
public void bindPreferenceExtra(RadioButtonPreference pref,
String key, CandidateInfo info, String defaultKey, String systemDefaultKey) {
}
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
public void updateCandidates() {
mCandidates.clear();
final List<? extends CandidateInfo> candidateList = getCandidates();
if (candidateList != null) {
for (CandidateInfo info : candidateList) {
mCandidates.put(info.getKey(), info);
}
}
final String defaultKey = getDefaultKey();
final String systemDefaultKey = getSystemDefaultKey();
final PreferenceScreen screen = getPreferenceScreen();
screen.removeAll();
if (shouldShowItemNone()) {
final RadioButtonPreference nonePref = new RadioButtonPreference(getPrefContext());
nonePref.setIcon(R.drawable.ic_remove_circle);
nonePref.setTitle(R.string.app_list_preference_none);
nonePref.setChecked(TextUtils.isEmpty(defaultKey));
nonePref.setOnClickListener(this);
screen.addPreference(nonePref);
}
for (Map.Entry<String, CandidateInfo> app : mCandidates.entrySet()) {
RadioButtonPreference pref = new RadioButtonPreference(getPrefContext());
bindPreference(
pref, app.getKey(), app.getValue(), defaultKey);
bindPreferenceExtra(pref, app.getKey(), app.getValue(), defaultKey, systemDefaultKey);
screen.addPreference(pref);
}
mayCheckOnlyRadioButton();
}
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
public RadioButtonPreference bindPreference(RadioButtonPreference pref,
String key, CandidateInfo info, String defaultKey) {
pref.setTitle(info.loadLabel());
pref.setIcon(info.loadIcon());
pref.setKey(key);
if (TextUtils.equals(defaultKey, key)) {
pref.setChecked(true);
}
pref.setEnabled(info.enabled);
pref.setOnClickListener(this);
return pref;
}
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
public void updateCheckedState(String selectedKey) {
final PreferenceScreen screen = getPreferenceScreen();
if (screen != null) {
final int count = screen.getPreferenceCount();
for (int i = 0; i < count; i++) {
final Preference pref = screen.getPreference(i);
if (pref instanceof RadioButtonPreference) {
final RadioButtonPreference radioPref = (RadioButtonPreference) pref;
final boolean newCheckedState = TextUtils.equals(pref.getKey(), selectedKey);
if (radioPref.isChecked() != newCheckedState) {
radioPref.setChecked(TextUtils.equals(pref.getKey(), selectedKey));
}
}
}
}
}
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
public void mayCheckOnlyRadioButton() {
final PreferenceScreen screen = getPreferenceScreen();
// If there is only 1 thing on screen, select it.
if (screen != null && screen.getPreferenceCount() == 1) {
final Preference onlyPref = screen.getPreference(0);
if (onlyPref instanceof RadioButtonPreference) {
((RadioButtonPreference) onlyPref).setChecked(true);
}
}
}
protected abstract List<? extends CandidateInfo> getCandidates();
protected abstract String getDefaultKey();
protected abstract boolean setDefaultKey(String key);
protected String getSystemDefaultKey() {
return null;
}
public static abstract class CandidateInfo {
public final boolean enabled;
public CandidateInfo(boolean enabled) {
this.enabled = enabled;
}
public abstract CharSequence loadLabel();
public abstract Drawable loadIcon();
public abstract String getKey();
}
}

View File

@@ -61,12 +61,12 @@ public class DefaultAssistPickerTest {
final List<DefaultAssistPicker.Info> assistants = new ArrayList<>(); final List<DefaultAssistPicker.Info> assistants = new ArrayList<>();
assistants.add(new DefaultAssistPicker.Info(TEST_ASSIST)); assistants.add(new DefaultAssistPicker.Info(TEST_ASSIST));
ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants); ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants);
mPicker.setDefaultAppKey(TEST_ASSIST.flattenToString()); mPicker.setDefaultKey(TEST_ASSIST.flattenToString());
assertThat(Settings.Secure.getString(mContext.getContentResolver(), assertThat(Settings.Secure.getString(mContext.getContentResolver(),
Settings.Secure.ASSISTANT)) Settings.Secure.ASSISTANT))
.isEqualTo(TEST_ASSIST.flattenToString()); .isEqualTo(TEST_ASSIST.flattenToString());
assertThat(mPicker.getDefaultAppKey()) assertThat(mPicker.getDefaultKey())
.isEqualTo(TEST_ASSIST.flattenToString()); .isEqualTo(TEST_ASSIST.flattenToString());
} }
@@ -74,12 +74,12 @@ public class DefaultAssistPickerTest {
public void setDefaultAppKey_noAvaialbleAssit_shouldClearDefaultAssist() { public void setDefaultAppKey_noAvaialbleAssit_shouldClearDefaultAssist() {
final List<DefaultAssistPicker.Info> assistants = new ArrayList<>(); final List<DefaultAssistPicker.Info> assistants = new ArrayList<>();
ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants); ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants);
mPicker.setDefaultAppKey(TEST_ASSIST.flattenToString()); mPicker.setDefaultKey(TEST_ASSIST.flattenToString());
assertThat(Settings.Secure.getString(mContext.getContentResolver(), assertThat(Settings.Secure.getString(mContext.getContentResolver(),
Settings.Secure.ASSISTANT)) Settings.Secure.ASSISTANT))
.isEmpty(); .isEmpty();
assertThat(mPicker.getDefaultAppKey()) assertThat(mPicker.getDefaultKey())
.isNull(); .isNull();
} }
@@ -88,12 +88,12 @@ public class DefaultAssistPickerTest {
final List<DefaultAssistPicker.Info> assistants = new ArrayList<>(); final List<DefaultAssistPicker.Info> assistants = new ArrayList<>();
assistants.add(new DefaultAssistPicker.Info(TEST_ASSIST)); assistants.add(new DefaultAssistPicker.Info(TEST_ASSIST));
ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants); ReflectionHelpers.setField(mPicker, "mAvailableAssistants", assistants);
mPicker.setDefaultAppKey(null); mPicker.setDefaultKey(null);
assertThat(Settings.Secure.getString(mContext.getContentResolver(), assertThat(Settings.Secure.getString(mContext.getContentResolver(),
Settings.Secure.ASSISTANT)) Settings.Secure.ASSISTANT))
.isEmpty(); .isEmpty();
assertThat(mPicker.getDefaultAppKey()) assertThat(mPicker.getDefaultKey())
.isNull(); .isNull();
} }
} }

View File

@@ -17,13 +17,17 @@
package com.android.settings.applications.defaultapps; package com.android.settings.applications.defaultapps;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import android.content.ComponentName; import android.content.ComponentName;
import android.content.pm.ActivityInfo; import android.content.pm.PackageItemInfo;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import com.android.settings.SettingsRobolectricTestRunner; import com.android.settings.SettingsRobolectricTestRunner;
import com.android.settings.TestConfig; import com.android.settings.TestConfig;
import com.android.settings.applications.PackageManagerWrapper;
import org.junit.Before; import org.junit.Before;
import org.junit.Test; import org.junit.Test;
@@ -32,60 +36,44 @@ import org.mockito.Mock;
import org.mockito.MockitoAnnotations; import org.mockito.MockitoAnnotations;
import org.robolectric.annotation.Config; import org.robolectric.annotation.Config;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@RunWith(SettingsRobolectricTestRunner.class) @RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
public class DefaultAppInfoTest { public class DefaultAppInfoTest {
@Mock @Mock
private ActivityInfo mActivityInfo; private PackageItemInfo mPackageItemInfo;
@Mock
private ApplicationInfo mApplicationInfo;
@Mock @Mock
private ComponentName mComponentName; private ComponentName mComponentName;
@Mock @Mock
private PackageManager mPackageManager; private PackageManager mPackageManager;
@Mock
private PackageManagerWrapper mPackageManagerWrapper;
private DefaultAppInfo mInfo; private DefaultAppInfo mInfo;
@Before @Before
public void setUp() { public void setUp() {
MockitoAnnotations.initMocks(this); MockitoAnnotations.initMocks(this);
when(mPackageManagerWrapper.getPackageManager()).thenReturn(mPackageManager);
} }
@Test @Test
public void initInfoWithActivityInfo_shouldLoadInfo() { public void initInfoWithActivityInfo_shouldLoadInfo() {
mActivityInfo.packageName = "test"; mPackageItemInfo.packageName = "test";
mInfo = new DefaultAppInfo(mActivityInfo); mInfo = new DefaultAppInfo(mPackageManagerWrapper, mPackageItemInfo);
mInfo.loadLabel(mPackageManager); mInfo.loadLabel();
mInfo.loadIcon(mPackageManager); mInfo.loadIcon();
assertThat(mInfo.getKey()).isEqualTo(mActivityInfo.packageName); assertThat(mInfo.getKey()).isEqualTo(mPackageItemInfo.packageName);
verify(mActivityInfo).loadLabel(mPackageManager); verify(mPackageItemInfo).loadLabel(mPackageManager);
verify(mActivityInfo).loadIcon(mPackageManager); verify(mPackageItemInfo).loadIcon(mPackageManager);
}
@Test
public void initInfoWithApplicationInfo_shouldLoadInfo() {
mApplicationInfo.packageName = "test";
mInfo = new DefaultAppInfo(mApplicationInfo);
mInfo.loadLabel(mPackageManager);
mInfo.loadIcon(mPackageManager);
assertThat(mInfo.getKey()).isEqualTo(mApplicationInfo.packageName);
verify(mApplicationInfo).loadLabel(mPackageManager);
verify(mApplicationInfo).loadIcon(mPackageManager);
} }
@Test @Test
public void initInfoWithComponent_shouldLoadInfo() { public void initInfoWithComponent_shouldLoadInfo() {
when(mComponentName.getPackageName()).thenReturn("com.android.settings"); when(mComponentName.getPackageName()).thenReturn("com.android.settings");
mInfo = new DefaultAppInfo(0 /* uid */, mComponentName); mInfo = new DefaultAppInfo(mPackageManagerWrapper, 0 /* uid */, mComponentName);
mInfo.getKey(); mInfo.getKey();
verify(mComponentName).flattenToString(); verify(mComponentName).flattenToString();

View File

@@ -17,11 +17,15 @@
package com.android.settings.applications.defaultapps; package com.android.settings.applications.defaultapps;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;
import android.app.Activity; import android.app.Activity;
import android.content.Context; import android.content.Context;
import android.os.Bundle;
import android.os.UserManager; import android.os.UserManager;
import android.support.v4.app.FragmentManager;
import android.support.v7.preference.PreferenceScreen; import android.support.v7.preference.PreferenceScreen;
import com.android.settings.SettingsRobolectricTestRunner; import com.android.settings.SettingsRobolectricTestRunner;
@@ -40,13 +44,6 @@ import org.robolectric.annotation.Config;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@RunWith(SettingsRobolectricTestRunner.class) @RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
public class DefaultAppPickerFragmentTest { public class DefaultAppPickerFragmentTest {
@@ -57,8 +54,6 @@ public class DefaultAppPickerFragmentTest {
private PreferenceScreen mScreen; private PreferenceScreen mScreen;
@Mock @Mock
private UserManager mUserManager; private UserManager mUserManager;
@Mock
private FragmentManager mFragmentManager;
private TestFragment mFragment; private TestFragment mFragment;
@@ -66,9 +61,6 @@ public class DefaultAppPickerFragmentTest {
public void setUp() { public void setUp() {
MockitoAnnotations.initMocks(this); MockitoAnnotations.initMocks(this);
mFragment = spy(new TestFragment()); mFragment = spy(new TestFragment());
final Bundle bundle = new Bundle();
bundle.putBoolean(DefaultAppPickerFragment.EXTRA_FOR_WORK, false);
mFragment.setArguments(bundle);
when(mActivity.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager); when(mActivity.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager);
doReturn(mActivity).when(mFragment).getContext(); doReturn(mActivity).when(mFragment).getContext();
@@ -76,26 +68,7 @@ public class DefaultAppPickerFragmentTest {
} }
@Test @Test
public void onAttach_userIsInitialized() { public void clickPreference_hasConfirmation_shouldShowConfirmation() {
mFragment.onAttach((Context) mActivity);
verify(mActivity).getPackageManager();
verify(mActivity).getSystemService(Context.USER_SERVICE);
}
@Test
public void clickPreference_noCofirmation_shouldDirectlyConfirm() {
final RadioButtonPreference pref =
new RadioButtonPreference(RuntimeEnvironment.application);
pref.setKey("TEST");
mFragment.onRadioButtonClicked(pref);
assertThat(mFragment.setDefaultAppKeyCalled).isTrue();
}
@Test
public void clickPreference_hasCofirmation_shouldShowConfirmation() {
final RadioButtonPreference pref = final RadioButtonPreference pref =
new RadioButtonPreference(RuntimeEnvironment.application); new RadioButtonPreference(RuntimeEnvironment.application);
pref.setKey("TEST"); pref.setKey("TEST");
@@ -106,18 +79,6 @@ public class DefaultAppPickerFragmentTest {
mFragment.onRadioButtonClicked(pref); mFragment.onRadioButtonClicked(pref);
} }
@Test
public void displaySingleOption_shouldSelectRadioButton() {
final RadioButtonPreference pref =
new RadioButtonPreference(RuntimeEnvironment.application);
when(mScreen.getPreferenceCount()).thenReturn(1);
when(mScreen.getPreference(0)).thenReturn(pref);
mFragment.mayCheckOnlyRadioButton();
assertThat(pref.isChecked()).isTrue();
}
public static class TestFragment extends DefaultAppPickerFragment { public static class TestFragment extends DefaultAppPickerFragment {
boolean setDefaultAppKeyCalled; boolean setDefaultAppKeyCalled;
@@ -133,12 +94,12 @@ public class DefaultAppPickerFragmentTest {
} }
@Override @Override
protected String getDefaultAppKey() { protected String getDefaultKey() {
return null; return null;
} }
@Override @Override
protected boolean setDefaultAppKey(String key) { protected boolean setDefaultKey(String key) {
setDefaultAppKeyCalled = true; setDefaultAppKeyCalled = true;
return true; return true;
} }

View File

@@ -17,6 +17,10 @@
package com.android.settings.applications.defaultapps; package com.android.settings.applications.defaultapps;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import android.content.Context; import android.content.Context;
import android.os.UserManager; import android.os.UserManager;
import android.support.v7.preference.Preference; import android.support.v7.preference.Preference;
@@ -33,10 +37,6 @@ import org.mockito.Mock;
import org.mockito.MockitoAnnotations; import org.mockito.MockitoAnnotations;
import org.robolectric.annotation.Config; import org.robolectric.annotation.Config;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@RunWith(SettingsRobolectricTestRunner.class) @RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
public class DefaultAppPreferenceControllerTest { public class DefaultAppPreferenceControllerTest {
@@ -62,7 +62,7 @@ public class DefaultAppPreferenceControllerTest {
public void updateState_hasDefaultApp_shouldUpdateAppName() { public void updateState_hasDefaultApp_shouldUpdateAppName() {
mController = new TestPreferenceController(mContext); mController = new TestPreferenceController(mContext);
when(mController.mAppInfo.loadLabel(mContext.getPackageManager())) when(mController.mAppInfo.loadLabel())
.thenReturn(TEST_APP_NAME); .thenReturn(TEST_APP_NAME);
mController.updateState(mPreference); mController.updateState(mPreference);

View File

@@ -16,9 +16,14 @@
package com.android.settings.applications.defaultapps; package com.android.settings.applications.defaultapps;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;
import android.app.Activity; import android.app.Activity;
import android.content.Context; import android.content.Context;
import android.content.pm.PackageManager;
import android.os.UserManager; import android.os.UserManager;
import com.android.settings.SettingsRobolectricTestRunner; import com.android.settings.SettingsRobolectricTestRunner;
@@ -36,13 +41,6 @@ import org.robolectric.RuntimeEnvironment;
import org.robolectric.annotation.Config; import org.robolectric.annotation.Config;
import org.robolectric.util.ReflectionHelpers; import org.robolectric.util.ReflectionHelpers;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;
@RunWith(SettingsRobolectricTestRunner.class) @RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
@@ -73,14 +71,14 @@ public class DefaultAutofillPickerTest {
@Test @Test
public void setAndGetDefaultAppKey_shouldUpdateDefaultAutoFill() { public void setAndGetDefaultAppKey_shouldUpdateDefaultAutoFill() {
assertThat(mPicker.setDefaultAppKey(TEST_APP_KEY)).isTrue(); assertThat(mPicker.setDefaultKey(TEST_APP_KEY)).isTrue();
assertThat(mPicker.getDefaultAppKey()).isEqualTo(TEST_APP_KEY); assertThat(mPicker.getDefaultKey()).isEqualTo(TEST_APP_KEY);
} }
@Test @Test
public void getConfirmationMessage_shouldNotBeNull() { public void getConfirmationMessage_shouldNotBeNull() {
final DefaultAppInfo info = mock(DefaultAppInfo.class); final DefaultAppInfo info = mock(DefaultAppInfo.class);
when(info.loadLabel(any(PackageManager.class))).thenReturn("test_app_name"); when(info.loadLabel()).thenReturn("test_app_name");
assertThat(mPicker.getConfirmationMessage(info)).isNotNull(); assertThat(mPicker.getConfirmationMessage(info)).isNotNull();
} }

View File

@@ -67,14 +67,14 @@ public class DefaultBrowserPickerTest {
@Test @Test
public void setDefaultAppKey_shouldUpdateDefaultBrowser() { public void setDefaultAppKey_shouldUpdateDefaultBrowser() {
mPicker.setDefaultAppKey(TEST_APP_KEY); mPicker.setDefaultKey(TEST_APP_KEY);
verify(mPackageManager) verify(mPackageManager)
.setDefaultBrowserPackageNameAsUser(eq(TEST_APP_KEY), anyInt()); .setDefaultBrowserPackageNameAsUser(eq(TEST_APP_KEY), anyInt());
} }
@Test @Test
public void getDefaultAppKey_shouldReturnDefaultBrowser() { public void getDefaultAppKey_shouldReturnDefaultBrowser() {
mPicker.getDefaultAppKey(); mPicker.getDefaultKey();
verify(mPackageManager) verify(mPackageManager)
.getDefaultBrowserPackageNameAsUser(anyInt()); .getDefaultBrowserPackageNameAsUser(anyInt());
} }

View File

@@ -70,8 +70,8 @@ public class DefaultEmergencyPickerTest {
@Test @Test
public void setDefaultAppKey_shouldUpdateDefault() { public void setDefaultAppKey_shouldUpdateDefault() {
assertThat(mPicker.setDefaultAppKey(TEST_APP_KEY)).isTrue(); assertThat(mPicker.setDefaultKey(TEST_APP_KEY)).isTrue();
assertThat(mPicker.getDefaultAppKey()).isEqualTo(TEST_APP_KEY); assertThat(mPicker.getDefaultKey()).isEqualTo(TEST_APP_KEY);
} }
@Test @Test
@@ -80,6 +80,6 @@ public class DefaultEmergencyPickerTest {
Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION, Settings.Secure.EMERGENCY_ASSISTANCE_APPLICATION,
TEST_APP_KEY); TEST_APP_KEY);
assertThat(mPicker.getDefaultAppKey()).isEqualTo(TEST_APP_KEY); assertThat(mPicker.getDefaultKey()).isEqualTo(TEST_APP_KEY);
} }
} }

View File

@@ -72,7 +72,7 @@ public class DefaultHomePickerTest {
@Test @Test
public void setDefaultAppKey_shouldUpdateDefault() { public void setDefaultAppKey_shouldUpdateDefault() {
assertThat(mPicker.setDefaultAppKey(TEST_APP_KEY)).isTrue(); assertThat(mPicker.setDefaultKey(TEST_APP_KEY)).isTrue();
verify(mPackageManager).replacePreferredActivity(any(IntentFilter.class), verify(mPackageManager).replacePreferredActivity(any(IntentFilter.class),
anyInt(), any(ComponentName[].class), any(ComponentName.class)); anyInt(), any(ComponentName[].class), any(ComponentName.class));
@@ -83,7 +83,7 @@ public class DefaultHomePickerTest {
final ComponentName cn = mock(ComponentName.class); final ComponentName cn = mock(ComponentName.class);
when(mPackageManager.getHomeActivities(anyList())) when(mPackageManager.getHomeActivities(anyList()))
.thenReturn(cn); .thenReturn(cn);
mPicker.getDefaultAppKey(); mPicker.getDefaultKey();
verify(cn).flattenToString(); verify(cn).flattenToString();
} }

View File

@@ -70,9 +70,9 @@ public class DefaultNotificationAssistantPickerTest {
@Test @Test
public void setDefaultAppKey_shouldUpdateDefault() { public void setDefaultAppKey_shouldUpdateDefault() {
mPicker.setDefaultAppKey(TEST_APP_KEY); mPicker.setDefaultKey(TEST_APP_KEY);
assertThat(mPicker.getDefaultAppKey()).isEqualTo(TEST_APP_KEY); assertThat(mPicker.getDefaultKey()).isEqualTo(TEST_APP_KEY);
} }
@Test @Test
@@ -81,6 +81,6 @@ public class DefaultNotificationAssistantPickerTest {
Settings.Secure.ENABLED_NOTIFICATION_ASSISTANT, Settings.Secure.ENABLED_NOTIFICATION_ASSISTANT,
TEST_APP_KEY); TEST_APP_KEY);
assertThat(mPicker.getDefaultAppKey()).isEqualTo(TEST_APP_KEY); assertThat(mPicker.getDefaultKey()).isEqualTo(TEST_APP_KEY);
} }
} }

View File

@@ -75,14 +75,14 @@ public class DefaultPhonePickerTest {
@Test @Test
public void getSystemDefaultPackage_shouldAskDefaultKeyUpdater() { public void getSystemDefaultPackage_shouldAskDefaultKeyUpdater() {
mPicker.getSystemDefaultAppKey(); mPicker.getSystemDefaultKey();
verify(mDefaultKeyUpdater).getSystemDialerPackage(); verify(mDefaultKeyUpdater).getSystemDialerPackage();
} }
@Test @Test
public void setDefaultAppKey_shouldUpdateDefault() { public void setDefaultAppKey_shouldUpdateDefault() {
mPicker.setDefaultAppKey(TEST_APP_KEY); mPicker.setDefaultKey(TEST_APP_KEY);
verify(mDefaultKeyUpdater).setDefaultDialerApplication( verify(mDefaultKeyUpdater).setDefaultDialerApplication(
any(Context.class), eq(TEST_APP_KEY), anyInt()); any(Context.class), eq(TEST_APP_KEY), anyInt());
@@ -90,7 +90,7 @@ public class DefaultPhonePickerTest {
@Test @Test
public void getDefaultAppKey_shouldReturnDefault() { public void getDefaultAppKey_shouldReturnDefault() {
mPicker.getDefaultAppKey(); mPicker.getDefaultKey();
verify(mDefaultKeyUpdater).getDefaultDialerApplication(any(Context.class), anyInt()); verify(mDefaultKeyUpdater).getDefaultDialerApplication(any(Context.class), anyInt());
} }
} }

View File

@@ -73,14 +73,14 @@ public class DefaultSmsPickerTest {
@Test @Test
public void setDefaultAppKey_shouldUpdateDefault() { public void setDefaultAppKey_shouldUpdateDefault() {
mPicker.setDefaultAppKey(TEST_APP_KEY); mPicker.setDefaultKey(TEST_APP_KEY);
verify(mDefaultKeyUpdater).setDefaultApplication(any(Context.class), eq(TEST_APP_KEY)); verify(mDefaultKeyUpdater).setDefaultApplication(any(Context.class), eq(TEST_APP_KEY));
} }
@Test @Test
public void getDefaultAppKey_shouldReturnDefault() { public void getDefaultAppKey_shouldReturnDefault() {
mPicker.getDefaultAppKey(); mPicker.getDefaultKey();
verify(mDefaultKeyUpdater).getDefaultApplication(any(Context.class)); verify(mDefaultKeyUpdater).getDefaultApplication(any(Context.class));
} }

View File

@@ -46,8 +46,6 @@ import com.android.settings.applications.PackageManagerWrapper;
import com.android.settings.applications.defaultapps.DefaultAppInfo; import com.android.settings.applications.defaultapps.DefaultAppInfo;
import com.android.settings.widget.RadioButtonPreference; import com.android.settings.widget.RadioButtonPreference;
import java.util.Arrays;
import org.junit.Before; import org.junit.Before;
import org.junit.Test; import org.junit.Test;
import org.junit.runner.RunWith; import org.junit.runner.RunWith;
@@ -58,6 +56,8 @@ import org.robolectric.RuntimeEnvironment;
import org.robolectric.annotation.Config; import org.robolectric.annotation.Config;
import org.robolectric.util.ReflectionHelpers; import org.robolectric.util.ReflectionHelpers;
import java.util.Arrays;
@RunWith(SettingsRobolectricTestRunner.class) @RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
public class WebViewAppPickerTest { public class WebViewAppPickerTest {
@@ -162,13 +162,14 @@ public class WebViewAppPickerTest {
@Test @Test
public void testDisabledPackageShownAsDisabled() { public void testDisabledPackageShownAsDisabled() {
String disabledReason = "disabled"; String disabledReason = "disabled";
DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo( DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo(mPackageManager,
createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason); createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason);
RadioButtonPreference mockPreference = mock(RadioButtonPreference.class); RadioButtonPreference mockPreference = mock(RadioButtonPreference.class);
mPicker.configurePreferenceFromAppInfo(mockPreference, mPicker.bindPreference(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null);
mPicker.bindPreferenceExtra(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null); DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null);
verify(mockPreference, times(1)).setEnabled(eq(false)); verify(mockPreference, times(1)).setEnabled(eq(false));
verify(mockPreference, never()).setEnabled(eq(true)); verify(mockPreference, never()).setEnabled(eq(true));
} }
@@ -176,13 +177,14 @@ public class WebViewAppPickerTest {
@Test @Test
public void testEnabledPackageShownAsEnabled() { public void testEnabledPackageShownAsEnabled() {
String disabledReason = ""; String disabledReason = "";
DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo( DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo(mPackageManager,
createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason); createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason);
RadioButtonPreference mockPreference = mock(RadioButtonPreference.class); RadioButtonPreference mockPreference = mock(RadioButtonPreference.class);
mPicker.configurePreferenceFromAppInfo(mockPreference, mPicker.bindPreference(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null);
mPicker.bindPreferenceExtra(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null); DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null);
verify(mockPreference, times(1)).setEnabled(eq(true)); verify(mockPreference, times(1)).setEnabled(eq(true));
verify(mockPreference, never()).setEnabled(eq(false)); verify(mockPreference, never()).setEnabled(eq(false));
} }
@@ -190,13 +192,14 @@ public class WebViewAppPickerTest {
@Test @Test
public void testDisabledPackageShowsDisabledReasonSummary() { public void testDisabledPackageShowsDisabledReasonSummary() {
String disabledReason = "disabled"; String disabledReason = "disabled";
DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo( DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo(mPackageManager,
createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason); createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason);
RadioButtonPreference mockPreference = mock(RadioButtonPreference.class); RadioButtonPreference mockPreference = mock(RadioButtonPreference.class);
mPicker.configurePreferenceFromAppInfo(mockPreference, mPicker.bindPreference(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null);
mPicker.bindPreferenceExtra(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null); DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null);
verify(mockPreference, times(1)).setSummary(eq(disabledReason)); verify(mockPreference, times(1)).setSummary(eq(disabledReason));
// Ensure we haven't called setSummary several times. // Ensure we haven't called setSummary several times.
verify(mockPreference, times(1)).setSummary(any()); verify(mockPreference, times(1)).setSummary(any());
@@ -205,13 +208,14 @@ public class WebViewAppPickerTest {
@Test @Test
public void testEnabledPackageShowsEmptySummary() { public void testEnabledPackageShowsEmptySummary() {
String disabledReason = null; String disabledReason = null;
DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo( DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo(mPackageManager,
createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason); createApplicationInfo(DEFAULT_PACKAGE_NAME), disabledReason);
RadioButtonPreference mockPreference = mock(RadioButtonPreference.class); RadioButtonPreference mockPreference = mock(RadioButtonPreference.class);
mPicker.configurePreferenceFromAppInfo(mockPreference, mPicker.bindPreference(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null);
mPicker.bindPreferenceExtra(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null); DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null);
verify(mockPreference, never()).setSummary(any()); verify(mockPreference, never()).setSummary(any());
} }
@@ -242,7 +246,7 @@ public class WebViewAppPickerTest {
WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class); WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class);
when(wvusWrapper.getPackageInfosAllUsers( when(wvusWrapper.getPackageInfosAllUsers(
any(), eq(DEFAULT_PACKAGE_NAME))).thenReturn( any(), eq(DEFAULT_PACKAGE_NAME))).thenReturn(
Arrays.asList(packageForFirstUser, packageForSecondUser)); Arrays.asList(packageForFirstUser, packageForSecondUser));
assertThat(mPicker.getDisabledReason(wvusWrapper, mContext, DEFAULT_PACKAGE_NAME)).isNull(); assertThat(mPicker.getDisabledReason(wvusWrapper, mContext, DEFAULT_PACKAGE_NAME)).isNull();
} }
@@ -255,8 +259,8 @@ public class WebViewAppPickerTest {
when(packageForFirstUser.getUserInfo()).thenReturn(FIRST_USER); when(packageForFirstUser.getUserInfo()).thenReturn(FIRST_USER);
WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class); WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class);
when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME) when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME)))
)).thenReturn(Arrays.asList(packageForFirstUser)); .thenReturn(Arrays.asList(packageForFirstUser));
final String EXPECTED_DISABLED_REASON = String.format( final String EXPECTED_DISABLED_REASON = String.format(
"(disabled for user %s)", FIRST_USER.name); "(disabled for user %s)", FIRST_USER.name);
@@ -272,8 +276,8 @@ public class WebViewAppPickerTest {
when(packageForFirstUser.getUserInfo()).thenReturn(FIRST_USER); when(packageForFirstUser.getUserInfo()).thenReturn(FIRST_USER);
WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class); WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class);
when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME) when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME)))
)).thenReturn(Arrays.asList(packageForFirstUser)); .thenReturn(Arrays.asList(packageForFirstUser));
final String EXPECTED_DISABLED_REASON = String.format( final String EXPECTED_DISABLED_REASON = String.format(
"(uninstalled for user %s)", FIRST_USER.name); "(uninstalled for user %s)", FIRST_USER.name);
@@ -294,13 +298,13 @@ public class WebViewAppPickerTest {
when(packageForSecondUser.getUserInfo()).thenReturn(SECOND_USER); when(packageForSecondUser.getUserInfo()).thenReturn(SECOND_USER);
WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class); WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class);
when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME) when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME)))
)).thenReturn(Arrays.asList(packageForFirstUser, packageForSecondUser)); .thenReturn(Arrays.asList(packageForFirstUser, packageForSecondUser));
final String EXPECTED_DISABLED_REASON = String.format( final String EXPECTED_DISABLED_REASON = String.format(
"(disabled for user %s)", FIRST_USER.name); "(disabled for user %s)", FIRST_USER.name);
assertThat(mPicker.getDisabledReason( assertThat(mPicker.getDisabledReason(
wvusWrapper, mContext,DEFAULT_PACKAGE_NAME)).isEqualTo(EXPECTED_DISABLED_REASON); wvusWrapper, mContext, DEFAULT_PACKAGE_NAME)).isEqualTo(EXPECTED_DISABLED_REASON);
} }
/** /**
@@ -320,8 +324,8 @@ public class WebViewAppPickerTest {
when(packageForSecondUser.getUserInfo()).thenReturn(SECOND_USER); when(packageForSecondUser.getUserInfo()).thenReturn(SECOND_USER);
WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class); WebViewUpdateServiceWrapper wvusWrapper = mock(WebViewUpdateServiceWrapper.class);
when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME) when(wvusWrapper.getPackageInfosAllUsers(any(), eq(DEFAULT_PACKAGE_NAME)))
)).thenReturn(Arrays.asList(packageForFirstUser, packageForSecondUser)); .thenReturn(Arrays.asList(packageForFirstUser, packageForSecondUser));
final String EXPECTED_DISABLED_REASON = String.format( final String EXPECTED_DISABLED_REASON = String.format(
"(uninstalled for user %s)", FIRST_USER.name); "(uninstalled for user %s)", FIRST_USER.name);
@@ -338,7 +342,7 @@ public class WebViewAppPickerTest {
PackageItemInfo mockPackageItemInfo = mock(PackageItemInfo.class); PackageItemInfo mockPackageItemInfo = mock(PackageItemInfo.class);
mockPackageItemInfo.packageName = DEFAULT_PACKAGE_NAME; mockPackageItemInfo.packageName = DEFAULT_PACKAGE_NAME;
when(mockPackageItemInfo.loadLabel(any())).thenReturn("myPackage"); when(mockPackageItemInfo.loadLabel(any())).thenReturn("myPackage");
DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo( DefaultAppInfo webviewAppInfo = mPicker.createDefaultAppInfo(mPackageManager,
mockPackageItemInfo, "" /* disabledReason */); mockPackageItemInfo, "" /* disabledReason */);
PackageInfo packageInfo = new PackageInfo(); PackageInfo packageInfo = new PackageInfo();
@@ -348,9 +352,10 @@ public class WebViewAppPickerTest {
when(mPackageManager.getPackageManager()).thenReturn(pm); when(mPackageManager.getPackageManager()).thenReturn(pm);
RadioButtonPreference mockPreference = mock(RadioButtonPreference.class); RadioButtonPreference mockPreference = mock(RadioButtonPreference.class);
mPicker.configurePreferenceFromAppInfo(mockPreference, mPicker.bindPreference(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null);
mPicker.bindPreferenceExtra(mockPreference,
DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null); DEFAULT_PACKAGE_NAME, webviewAppInfo, null, null);
verify(mockPreference, times(1)).setTitle(eq("myPackage myVersionName")); verify(mockPreference, times(1)).setTitle(eq("myPackage myVersionName"));
verify(mockPreference, times(1)).setTitle(any()); verify(mockPreference, times(1)).setTitle(any());
} }

View File

@@ -0,0 +1,132 @@
/*
* Copyright (C) 2017 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.settings.widget;
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import android.app.Activity;
import android.content.Context;
import android.os.UserManager;
import android.support.v7.preference.PreferenceScreen;
import com.android.settings.SettingsRobolectricTestRunner;
import com.android.settings.TestConfig;
import com.android.settings.applications.defaultapps.DefaultAppInfo;
import com.android.settings.applications.defaultapps.DefaultAppPickerFragment;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Answers;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.robolectric.RuntimeEnvironment;
import org.robolectric.annotation.Config;
import java.util.ArrayList;
import java.util.List;
@RunWith(SettingsRobolectricTestRunner.class)
@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION)
public class RadioButtonPickerFragmentTest {
@Mock(answer = Answers.RETURNS_DEEP_STUBS)
private Activity mActivity;
@Mock
private PreferenceScreen mScreen;
@Mock
private UserManager mUserManager;
private TestFragment mFragment;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
mFragment = spy(new TestFragment());
when(mActivity.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager);
doReturn(mActivity).when(mFragment).getContext();
doReturn(mScreen).when(mFragment).getPreferenceScreen();
}
@Test
public void onAttach_userIsInitialized() {
mFragment.onAttach((Context) mActivity);
verify(mActivity).getPackageManager();
verify(mActivity).getSystemService(Context.USER_SERVICE);
}
@Test
public void displaySingleOption_shouldSelectRadioButton() {
final RadioButtonPreference pref =
new RadioButtonPreference(RuntimeEnvironment.application);
when(mScreen.getPreferenceCount()).thenReturn(1);
when(mScreen.getPreference(0)).thenReturn(pref);
mFragment.mayCheckOnlyRadioButton();
assertThat(pref.isChecked()).isTrue();
}
@Test
public void clickPreference_shouldConfirm() {
final RadioButtonPreference pref =
new RadioButtonPreference(RuntimeEnvironment.application);
pref.setKey("TEST");
mFragment.onRadioButtonClicked(pref);
assertThat(mFragment.setDefaultKeyCalled).isTrue();
}
public static class TestFragment extends DefaultAppPickerFragment {
boolean setDefaultKeyCalled;
@Override
public int getMetricsCategory() {
return 0;
}
@Override
protected List<DefaultAppInfo> getCandidates() {
return new ArrayList<>();
}
@Override
protected String getDefaultKey() {
return null;
}
@Override
protected boolean setDefaultKey(String key) {
setDefaultKeyCalled = true;
return true;
}
@Override
public Context getContext() {
return RuntimeEnvironment.application;
}
}
}