Intent filters

==================================================

Intent的分类

==================================================

Intent大体上可以分成两类

*.  显式Intent,它通过组件名来指定要运行的目标组件(通过它的setComponent()方法),

    因为指定了组件名,所以它要运行的组件是确定的;其它程序开发者并不知道某个程序

    组件的名字,所以显式Intent通常用于程序内的组件调用,比如启动同一程序的其他

    服务或Activity。

*.  隐式Intent, 它不通过组件名来启动目标组件, 系统必须通过其他的手段找到合适的

    目标组件, 隐式Intent一般用于启动其他程序的组件.


===================================================

Intent filters

===================================================

如上所说, 对于隐式Intent不指定目标组件名,  Android必须用其他方法来找到目标组件,

这需要Intent和组件提供必要的信息.

对于组件来说, 它可以包含多个Intent filter, 这些Intent filter告知系统它可以处理

哪些Intent. 隐式Intent必须通过组件的Intent fitler测试才能启动该组件.

组件可以在AndroidManifest.xml指定它的Intent filter, 它包含action, data, category

三种Filter, 与Intent的这三种属性对应, 如:

    <activity . . .>

        <intent-filter . . . >

            <action android:name="com.example.project.SHOW_CURRENT" />

            <action android:name="com.example.project.SHOW_RECENT" />

            <action android:name="com.example.project.SHOW_PENDING" />

            <category android:name="android.intent.category.DEFAULT" />

            <category android:name="android.intent.category.BROWSABLE" />

            <data android:mimeType="video/mpeg" android:scheme="http" . . . /> 

            <data android:mimeType="audio/mpeg" android:scheme="http" . . . />

            . . . 

        </intent-filter>

    </activity>

一个Intent必须通过三种Filter的测试才能调用该组件, 但上面可以看到每种Filter可以

有多项, 对于每种Filter, 只要通过其中一项就算通过了.

下面分别描述:


*.  Action测试

    <intent-filter . . . >

        <action android:name="com.example.project.SHOW_CURRENT" />

        <action android:name="com.example.project.SHOW_RECENT" />

        <action android:name="com.example.project.SHOW_PENDING" />

        . . .

    </intent-filter>

    一个Intent的Action必须匹配Filter的Action列表中的一项, 才能通过, 如果Intent或

    组件的Filter没有指定Action, 会导致下两个结果:

    *.  如果组件的Intent Filter没有指定任何Action, 那么所有Intent都将不通过测试.

    *.  但另一方面,  如果Intent没有指定Action, 则它将通过测试, 即使组件的Intent

        Filter没有指定任何Action.


*.  Category测试

    <intent-filter . . . >

        <category android:name="android.intent.category.DEFAULT" />

        <category android:name="android.intent.category.BROWSABLE" />

        . . .

    </intent-filter>

    一个Intent如果要通过测试, 则它包含的所有category都必须通过Filter的category列表

    中的一项. 因此, 如果一个Intent没有category, 它就总是可以通过测试. 但有一个

    例外的情况: 对于传递给Activity(调用startActivity())的隐式Intent, 系统默认它

    带有一个 android.intent.category.DEFAULT 的category, 所以Activity的Intent Filter

    必须包含一项 android.intent.category.DEFAULT, 才能使这个Intent通过测试. 

    不过如果Activity的Intent Filter带有 android.intent.action.MAIN 和

    android.intent.category.LAUNCHER , 就不再需要包含android.intent.category.DEFAULT 了.


*.  Data测试

    <intent-filter . . . >

        <data android:mimeType="video/mpeg" android:scheme="http" . . . /> 

        <data android:mimeType="audio/mpeg" android:scheme="http" . . . />

        . . .

    </intent-filter>

    Data测试主要是测URI和数据类型(mimeType), URI的形式大概如下:

        scheme://host:port/path

    比如:

        http://www.douban.com:8080/people

    data filter将URI分成多个属性, 如下:

        <data android:host="string"

            android:mimeType="string"

            android:path="string"

            android:pathPattern="string"

            android:pathPrefix="string"

            android:port="string"

            android:scheme="string" />

    系统只比较出现的URI属性, 比如Data Filter只指定android:scheme, 那么所有包含

    这个scheme的URI都可以匹配这个Filter.


    Data的测试规则如下:

    *.  如果一个Intent没有包含URI和数据类型, 那么只当Data Filter也没有包含任何URI

        和数据类型时才能通过.

    *.  如果一个Intent包含URI但没有包含数据类型(并且数据类型不能从URI推断出来), 

        那么只当Intent的URI与Filter的URI匹配, 并且Filter也没有数据类型时才能通过.

    *.  如果一个Intent包含数据类型但没有包含URI, 那么只当Filter包含同样的数据

   amp;nbsp;    类型并且没有包含URI时才能通过.

    *.  如果一个Intent即包含URI也包含数据类型(或可以从URI推断出数据类型), 那么

        当它匹配Filter的数据类型时通过数据类型部分的测试, 当它匹配Filter的URI时

        通过URI部分的测试; 

        如果Intent的URI是content: 或 file: , 并且Filter没有指定URI时通过URI测试,

        换名话说, 一个Filter只列出数据类型, 则假定支持content: 或 file: 类型的URI.

你可能感兴趣的:(Intent filters)