LAUNCH BY DEFAULT
You've chosen to launch this app by default for some actions.
packages\apps\Provision\src\com\android\provision\DefaultActivity.java
/*
* Copyright (C) 2008 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.provision;
import android.app.Activity;
import android.content.ComponentName;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.os.Bundle;
import android.os.SystemProperties;
import android.provider.Settings;
import android.util.Log;
import java.util.List;
/**
* Application that sets the provisioned bit, like SetupWizard does.
*/
public class DefaultActivity extends Activity {
private static final String TAG = "DefaultActivity";
@Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
// Add a persistent setting to allow other apps to know the device has been provisioned.
Settings.Global.putInt(getContentResolver(), Settings.Global.DEVICE_PROVISIONED, 1);
// remove this activity from the package manager.
PackageManager pm = getPackageManager();
Intent intent = new Intent(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_HOME);
List<ResolveInfo> resolveInfoList = pm.queryIntentActivities(intent, 0);
if(resolveInfoList != null) {
int size = resolveInfoList.size();
for(int j=0; j<size; j++) {
final ResolveInfo r = resolveInfoList.get(j);
if(r.activityInfo.packageName.equals(this.getPackageName())) {
resolveInfoList.remove(j);
size -= 1;
break;
}
}
ComponentName[] set = new ComponentName[size];
String defaultLauncherPackage = SystemProperties.get("ro.defaultlauncher.package", "com.android.launcher2");
String defaultLauncherClass = SystemProperties.get("ro.defaultlauncher.class", "com.android.launcher2.Launcher");
ComponentName defaultLauncher = new ComponentName(defaultLauncherPackage, defaultLauncherClass);
int defaultMach = 0;
for(int i=0; i<size; i++) {
final ResolveInfo resolveInfo = resolveInfoList.get(i);
Log.d(TAG, resolveInfo.toString());
set[i] = new ComponentName(resolveInfo.activityInfo.packageName, resolveInfo.activityInfo.name);
if(defaultLauncher.getClassName().equals(resolveInfo.activityInfo.name)) {
defaultMach = resolveInfo.match;
}
}
Log.d(TAG, "defaultMatch="+Integer.toHexString(defaultMach));
IntentFilter filter = new IntentFilter();
filter.addAction(Intent.ACTION_MAIN);
filter.addCategory(Intent.CATEGORY_HOME);
filter.addCategory(Intent.CATEGORY_DEFAULT);
pm.clearPackagePreferredActivities(defaultLauncher.getPackageName());
pm.addPreferredActivity(filter, defaultMach, set, defaultLauncher);
} else {
Log.d(TAG, "****resolveInfoList is null.");
}
ComponentName name = new ComponentName(this, DefaultActivity.class);
pm.setComponentEnabledSetting(name, PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
// terminate the activity.
finish();
}
}
另外参考frameworks\base\services\java\com\android\server\pm\PackageManagerService.java
ResolveInfo findPreferredActivity(Intent intent, String resolvedType,
int flags, List<ResolveInfo> query, int priority, int userId) {
if (!sUserManager.exists(userId)) return null;
// writer
synchronized (mPackages) {
if (intent.getSelector() != null) {
intent = intent.getSelector();
}
if (DEBUG_PREFERRED) intent.addFlags(Intent.FLAG_DEBUG_LOG_RESOLUTION);
PreferredIntentResolver pir = mSettings.mPreferredActivities.get(userId);
List<PreferredActivity> prefs = pir != null
? pir.queryIntent(intent, resolvedType,
(flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, userId)
: null;
if (prefs != null && prefs.size() > 0) {
// First figure out how good the original match set is.
// We will only allow preferred activities that came
// from the same match quality.
int match = 0;
if (DEBUG_PREFERRED) {
Log.v(TAG, "Figuring out best match...");
}
final int N = query.size();
for (int j=0; j<N; j++) {
final ResolveInfo ri = query.get(j);
if (DEBUG_PREFERRED) {
Log.v(TAG, "Match for " + ri.activityInfo + ": 0x"
+ Integer.toHexString(match));
}
if (ri.match > match) {
match = ri.match;
}
}
if (DEBUG_PREFERRED) {
Log.v(TAG, "Best match: 0x" + Integer.toHexString(match));
}
match &= IntentFilter.MATCH_CATEGORY_MASK;
final int M = prefs.size();
for (int i=0; i<M; i++) {
final PreferredActivity pa = prefs.get(i);
if (pa.mPref.mMatch != match) {
continue;
}
final ActivityInfo ai = getActivityInfo(pa.mPref.mComponent,
flags | PackageManager.GET_DISABLED_COMPONENTS, userId);
if (DEBUG_PREFERRED) {
Log.v(TAG, "Got preferred activity:");
if (ai != null) {
ai.dump(new LogPrinter(Log.VERBOSE, TAG), " ");
} else {
Log.v(TAG, " null");
}
}
if (ai == null) {
// This previously registered preferred activity
// component is no longer known. Most likely an update
// to the app was installed and in the new version this
// component no longer exists. Clean it up by removing
// it from the preferred activities list, and skip it.
Slog.w(TAG, "Removing dangling preferred activity: "
+ pa.mPref.mComponent);
pir.removeFilter(pa);
continue;
}
for (int j=0; j<N; j++) {
final ResolveInfo ri = query.get(j);
if (!ri.activityInfo.applicationInfo.packageName
.equals(ai.applicationInfo.packageName)) {
continue;
}
if (!ri.activityInfo.name.equals(ai.name)) {
continue;
}
// Okay we found a previously set preferred app.
// If the result set is different from when this
// was created, we need to clear it and re-ask the
// user their preference.
if (!pa.mPref.sameSet(query, priority)) {
Slog.i(TAG, "Result set changed, dropping preferred activity for "
+ intent + " type " + resolvedType);
pir.removeFilter(pa);
return null;
}
// Yay!
return ri;
}
}
}
}
return null;
}