android设置多个类似APP其中的一个为默认

05-09 17:01:13.547: I/ActivityManager(3003): START u0 {act=android.intent.action.VIEW cat=[android.intent.category.BROWSABLE] dat=https://www.baidu.com cmp=android/com.android.internal.app.ResolverActivity} from pid 5222
05-09 17:01:13.587: I/ActivityManager(3003): Start proc system:ui for activity android/com.android.internal.app.ResolverActivity: pid=15544 uid=1000 gids={41000, 3002, 3001, 3003, 1028, 1015, 1023, 1021, 3004, 3005, 1000, 3009, 1010}
05-09 17:01:14.557: I/ActivityManager(3003): Displayed android/com.android.internal.app.ResolverActivity: +975ms

从ActivityManger输出Log可以知道是ResolverActivity处理app选择。

android\frameworks\base\core\java\com\android\internal\app\ResolverActivity.java

protected void onCreate(Bundle savedInstanceState) {
        // Use a specialized prompt when we‘re handling the ‘Home‘ app startActivity()
        final int titleResource;
        final Intent intent = makeMyIntent();
        final Set<String> categories = intent.getCategories();
        if (Intent.ACTION_MAIN.equals(intent.getAction())
                && categories != null
                && categories.size() == 1
                && categories.contains(Intent.CATEGORY_HOME)) {
            titleResource = com.android.internal.R.string.whichHomeApplication;//选择主屏幕应用
        } else {
            titleResource = com.android.internal.R.string.whichApplication;//选择要使用的应用:
        }

        onCreate(savedInstanceState, intent, getResources().getText(titleResource),
                null, null, true);
    }
 protected void onCreate(Bundle savedInstanceState, Intent intent,
            CharSequence title, Intent[] initialIntents, List<ResolveInfo> rList,
            boolean alwaysUseOption) {
        setTheme(R.style.Theme_DeviceDefault_Light_Dialog_Alert);
        super.onCreate(savedInstanceState);
        try {
            mLaunchedFromUid = ActivityManagerNative.getDefault().getLaunchedFromUid(
                    getActivityToken());
        } catch (RemoteException e) {
            mLaunchedFromUid = -1;
        }
        mPm = getPackageManager();
        mAlwaysUseOption = alwaysUseOption;
        mMaxColumns = getResources().getInteger(R.integer.config_maxResolverActivityColumns);

        AlertController.AlertParams ap = mAlertParams;

        ap.mTitle = title;

        mPackageMonitor.register(this, getMainLooper(), false);
        mRegistered = true;

        final ActivityManager am = (ActivityManager) getSystemService(ACTIVITY_SERVICE);
        mIconDpi = am.getLauncherLargeIconDensity();
        mIconSize = am.getLauncherLargeIconSize();

        mAdapter = new ResolveListAdapter(this, intent, initialIntents, rList, mLaunchedFromUid);//获取APP列表
        int count = mAdapter.getCount();
        if (mLaunchedFromUid < 0 || UserHandle.isIsolated(mLaunchedFromUid)) {
            // Gulp!
            finish();
            return;
        } else if (count > 1) {
            ap.mView = getLayoutInflater().inflate(R.layout.resolver_list, null);
            mListView = (ListView) ap.mView.findViewById(R.id.resolver_list);
            mListView.setAdapter(mAdapter);
            mListView.setOnItemClickListener(this);
            mListView.setOnItemLongClickListener(new ItemLongClickListener());

            if (alwaysUseOption) {
                mListView.setChoiceMode(ListView.CHOICE_MODE_SINGLE);
            }
        } else if (count == 1) {
            startActivity(mAdapter.intentForPosition(0));
            mPackageMonitor.unregister();
            mRegistered = false;
            finish();
            return;
        } else {
            ap.mMessage = getResources().getText(R.string.noApplications);
        }

        setupAlert();

        if (alwaysUseOption) {
            final ViewGroup buttonLayout = (ViewGroup) findViewById(R.id.button_bar);
            if (buttonLayout != null) {
                buttonLayout.setVisibility(View.VISIBLE);
                mAlwaysButton = (Button) buttonLayout.findViewById(R.id.button_always);
                mOnceButton = (Button) buttonLayout.findViewById(R.id.button_once);
            } else {
                mAlwaysUseOption = false;
            }
            // Set the initial highlight if there was a preferred or last used choice
            final int initialHighlight = mAdapter.getInitialHighlight();
            if (initialHighlight >= 0) {
                mListView.setItemChecked(initialHighlight, true);
                onItemClick(null, null, initialHighlight, 0); // Other entries are not used
            }
        }
    }

点击“始终”按钮,设置默认程序

public void onButtonClick(View v) {
        final int id = v.getId();
        startSelected(mListView.getCheckedItemPosition(), id == R.id.button_always);
        dismiss();
    }

    void startSelected(int which, boolean always) {
        if (isFinishing()) {
            return;
        }
        ResolveInfo ri = mAdapter.resolveInfoForPosition(which);
        Intent intent = mAdapter.intentForPosition(which);
        onIntentSelected(ri, intent, always);
        finish();
    }

    protected void onIntentSelected(ResolveInfo ri, Intent intent, boolean alwaysCheck) {
        if (mAlwaysUseOption && mAdapter.mOrigResolveList != null) {
            // Build a reasonable intent filter, based on what matched.
            IntentFilter filter = new IntentFilter();

            if (intent.getAction() != null) {
                filter.addAction(intent.getAction());
            }
            Set<String> categories = intent.getCategories();
            if (categories != null) {
                for (String cat : categories) {
                    filter.addCategory(cat);
                }
            }
            filter.addCategory(Intent.CATEGORY_DEFAULT);

            int cat = ri.match&IntentFilter.MATCH_CATEGORY_MASK;
            Uri data = intent.getData();
            if (cat == IntentFilter.MATCH_CATEGORY_TYPE) {
                String mimeType = intent.resolveType(this);
                if (mimeType != null) {
                    try {
                        filter.addDataType(mimeType);
                    } catch (IntentFilter.MalformedMimeTypeException e) {
                        Log.w("ResolverActivity", e);
                        filter = null;
                    }
                }
            }
            if (data != null && data.getScheme() != null) {
                // We need the data specification if there was no type,
                // OR if the scheme is not one of our magical "file:"
                // or "content:" schemes (see IntentFilter for the reason).
                if (cat != IntentFilter.MATCH_CATEGORY_TYPE
                        || (!"file".equals(data.getScheme())
                                && !"content".equals(data.getScheme()))) {//注意这里排除了"file://", "content://"
                    filter.addDataScheme(data.getScheme());

                    // Look through the resolved filter to determine which part
                    // of it matched the original Intent.
                    Iterator<PatternMatcher> pIt = ri.filter.schemeSpecificPartsIterator();
                    if (pIt != null) {
                        String ssp = data.getSchemeSpecificPart();
                        while (ssp != null && pIt.hasNext()) {
                            PatternMatcher p = pIt.next();
                            if (p.match(ssp)) {
                                filter.addDataSchemeSpecificPart(p.getPath(), p.getType());
                                break;
                            }
                        }
                    }
                    Iterator<IntentFilter.AuthorityEntry> aIt = ri.filter.authoritiesIterator();
                    if (aIt != null) {
                        while (aIt.hasNext()) {
                            IntentFilter.AuthorityEntry a = aIt.next();
                            if (a.match(data) >= 0) {
                                int port = a.getPort();
                                filter.addDataAuthority(a.getHost(), port >= 0 ? Integer.toString(port) : null);
                                break;
                            }
                        }
                    }
                    pIt = ri.filter.pathsIterator();
                    if (pIt != null) {
                        String path = data.getPath();
                        while (path != null && pIt.hasNext()) {
                            PatternMatcher p = pIt.next();
                            if (p.match(path)) {
                                filter.addDataPath(p.getPath(), p.getType());
                                break;
                            }
                        }
                    }
                }
            }

            if (filter != null) {
                final int N = mAdapter.mOrigResolveList.size();
                ComponentName[] set = new ComponentName[N];
                int bestMatch = 0;
                for (int i=0; i<N; i++) {
                    ResolveInfo r = mAdapter.mOrigResolveList.get(i);
                    set[i] = new ComponentName(r.activityInfo.packageName, r.activityInfo.name);
                    if (r.match > bestMatch) bestMatch = r.match;
                }
                if (alwaysCheck) {
                    getPackageManager().addPreferredActivity(filter, bestMatch, set, intent.getComponent());//设置默认
                } else {
                    try {
                        AppGlobals.getPackageManager().setLastChosenActivity(intent,
                                intent.resolveTypeIfNeeded(getContentResolver()),
                                PackageManager.MATCH_DEFAULT_ONLY,
                                filter, bestMatch, intent.getComponent());
                    } catch (RemoteException re) {
                        Log.d(TAG, "Error calling setLastChosenActivity\n" + re);
                    }
                }
            }
        }

        if (intent != null) {
            startActivity(intent);
        }
    }
时间: 2024-10-25 04:33:32

android设置多个类似APP其中的一个为默认的相关文章

Android Studio 1.0.2项目实战——从一个APP的开发过程认识Android Studio

Android Studio 1.0.1刚刚发布不久,谷歌紧接着发布了Android Studio 1.0.2版本,和1.0.0一样,是一个Bug修复版本.在上一篇Android Studio 1.0.1 + Genymotion安卓模拟器打造高效安卓开发环境,我们介绍了Android开发环境的搭建,今天先来说一下上一篇中大家问道比较多的问题,然后说一些Android Studio的使用技巧.  一.搭建开发环境中遇到的问题及解决办法 1.Genymotion模拟器网络错误 我们顺利的安装完了G

Android UI之自定义——类似iOS的Tabbar

Android UI之自定义--类似iOS的Tabbar Tabbar最早出现在iOS,iOS中的TabBarController实现了这个功能,开发起来相当简单.现在的APP,大多数都会使用Tabbar来作为应用的功能导航,界面简单清晰.那么Android常见的实现是通过RadioGroup来实现,今天将带来自定义实现,补充RadioGroup实现的不足. 先看看常见的软件中的使用: 这个是高铁管家APP,大家应该非常熟悉.这个APP的首页底部就是一个类似iOS的Tabbar.这里就不多举例子

Android 4.3实现类似iOS在音乐播放过程中如果有来电则音乐声音渐小铃声渐大的效果

目前Android的实现是:有来电时,音乐声音直接停止,铃声直接直接使用设置的铃声音量进行铃声播放. Android 4.3实现类似iOS在音乐播放过程中如果有来电则音乐声音渐小铃声渐大的效果. 如果要实现这个效果,首先要搞清楚两大问题: 1.来电时的代码主要实现流程. 2.主流音乐播放器在播放过程中,如果有来电,到底在收到了什么事件后将音乐暂停了? 一:来电时的代码主要实现流程 我不是第一研究来电代码的人,网上已经有高手对这个流程剖析过,不是不完全符合我的要求,我参考过的比较有价值的是如下两个

Android官方文档之App Resources(上)

想做出一款出色的App,仅仅编写Java代码还不够.在代码中调用资源(Resources ),如位图(bitmaps).布局资源( layout definitions).UI中需要展示的字符串资源(user interface strings).动画资源(animation instructions)等,可以让您的App更加出色. 本文将介绍Android中各种类型的资源.以及获取资源的方式,如需访问官方原文,您可以点击这个链接:<App Resources>. 可为App提供的资源(Pro

Android项目中使用类似菊花的Dialog

Android项目中使用类似菊花的Dialog 效果图一: 项目中使用的效果图二: 1.首先定义动画文件 <?xml version="1.0" encoding="utf-8"?> <animated-rotate xmlns:android="http://schemas.android.com/apk/res/android" android:drawable="@drawable/loading2"

【转】Android学习系列(1)--为App签名(为apk签名)

原文网址:http://www.cnblogs.com/qianxudetianxia/archive/2011/04/09/2010468.html Android学习系列(1)--为App签名(为apk签名) 写博客是一种快乐,前提是你有所写,与人分享,是另一种快乐,前提是你有舞台展示,博客园就是这样的舞台.这篇文章是android开发人员的必备知识,是我特别为大家整理和总结的,不求完美,但是有用. 1.签名的意义 为了保证每个应用程序开发商合法ID,防止部分开放商可能通过使用相同的Pack

Android 设置图片倒影效果

首先,贴出效果图: 1.布局文件main.xml <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_p

Android官方文档之App Components(Common Intents)

Intent的真正强大之处在于它的隐式Intent,隐式Intent需要配合Intent-filters使用,有关这方面的概念和知识,您可以参考我翻译的官方文档:<Android官方文档之App Components(Intents and Intent Filters)>. 隐式Intent足够强大,以至于系统提供了大量的Intent方便开发者启动系统应用程序,本文将介绍一些常用的隐式Intent.以及如何自定义intent-filters以匹配隐式intent. 如需阅读官方原文,您可以点

android API Guides 之 web app --------------Building Web Apps in WebView(WebView与页面的绑定)

如果你要在手机端实现一个web app或在app里加载一个web页面,那么你就要用到WebView控件.这WebView类是View类的扩展子类,它允许web页面作为应用布局的一部分来展示.它是不具备一个完整的浏览器的那些特性,例如WebView没有导航栏,地址栏等.WebView的默认功能就是去找事WebView. 当你在你的app里面加一些以后可能跟新的信息时(例如用户协议或用户指南),你是用WebView那是非常有帮助的.在你的应用里,你可以创建一个带有WebView的activity,然