首先要给大家分享一个网址:https://code.google.com/p/seek-for-android/
1、Tag的三种相应模式
当NFC读写设备扫描到一个tag时,会根据intent过滤器来选择最合适的activity处理。在android2.3中仅定义了android.nfc.action.NDEF_DISCOVERED一种相应类型,tag必须是智能海报、纯文本等类型的NFC标签,也就是可以传输NDEF(NFC电子数据交换格式)的tag,NFC读写设备才能处理。我的理解是:一般的公交卡、市民卡等都不属于包含文本类容的NFC标签,此时的NFC读写设备无法处理(注:此处理解有误,以上应该都属于nfc的tag)。
在android2.3.3中,又增加了android.nfc.action.TECH_DISCOVERED和android.nfc.action.TAG_DISCOVERED响应类型,其中TECH_DISCOVERED是指检测出来被扫描tag支持的技术类型,也就是说扫描出来的tag必须符合intent过滤器期望的NFC规范,比如符合ISO14443-4,或者ISO14443-3B等规范,扫描器才会做出相应;TAG_DISCOVERED是指只要tag能被扫描出来即可响应。
2、三种相应模式的优先级
假设在nexus s手机上装了3种NFC相应程序(每种应用程序的启动页就是一个activity),分别对应三种过滤器,那么当一个tag靠近时,nexus s究竟选择哪种应用程序来处理呢?按照以下的规则,该规则成为intent发布系统规则:
activity A中对intent过滤器设置了android.nfc.action.NDEF_DISCOVERED的判断规则;
<intent-filter>
<action android:name = "android.nfc.action.NDEF_DISCOVERED" />
<data android:mimeType = "text/plain" />
intent-filter>
activity B中对intent过滤器设置了android.nfc.action.TECH_DISCOVERED的判断规则;
android:resource="@xml/filter_nfc" />
activity C中对intent过滤器设置了android.nfc.action.TAG_DISCOVERED的判断规则;
1)、按照优先级(android.nfc.action.NDEF_DISCOVERED优先级最高),会先去判断请求是否满足activity A(因为A用的是NDEF_DISCOVERED)中的intent过滤器规则,先判断请求是否是NDEF_DISCOVERED格式的数据(action name),另外再判断NDEF_DISCOVERED数据的类型(action type),是纯文本还是智能海报,只有与过滤器中两个条件都要求的一致,才会选择activity A来处理。
2)、当activity A不满足,则判断activity B来判断,也就是NDEF_DISCOVERED处理不了的则开始找TECH_DISCOVERED。Activity B的intent过滤器中选择了根据TECH_DISCOVERED来过滤,也就是请求tag的NFC规范必须满足TECH_DISCOVERED设置的ISO14443-4、ISO14443-3A,或者ISO14443-3B种的一种或几种。TECH_DISCOVERED过滤必须要定义一个xml文件来筛选所要支持的tech的模式,根据
android:resource="@xml/filter_nfc" /> 来关联对应的tech过滤器filter_nfc文件。在filter_nfc.xml中,只有符合了
3)、当请求intent对于NDEF_DISCOVERED和TECH_DISCOVERED规则都不满足的时候,则intent才开始找intent过滤规则为android.nfc.action.TAG_DISCOVERED的activity,也就是activity C。TAG_DISCOVERED的过滤规则是最不严格的,只要符合NFC规范中的任一种则都会响应,所以在android中,它的优先级是最低的,否则一开始就选择TAG_DISCOVERED来相应,activity无法获得tag更详细的一些信息,比如tag满足的NFC规范或者NDEF类型等。
3、假设有多个activity可响应tag请求
以上说的都是完美的情况,也就是手机上只安装了3个支持NFC的应用程序,假设手机上安装了10种NFC程序,每当一个tag标签被扫描时,对应着多个(假设是4个)activity的intent过滤器都满足相应规则的话,那么程序会怎么处理呢?
系统会优先询问当前正在运行的activity(nexus s当前显示的应用程序)能否处理,如果能处理,则由当前的activity来相应,且无论当前的activity选用的是NDEF_DISCOVERED、TECH_DISCOVERED或者TAG_DISCOVERED,这个规则成为前台发布系统,前台发布系统的判断优先级高于intent发布系统。
如果前台发布系统无法处理,那么系统则会启用intent发布系统规则,去AndroidManifest.xml中查找各种activity的intent过滤器规则:
假设我们的前台应用程序是activity A,按照规则无法响应TECH_DISCOVERED请求,则启动intent发布规则,假设找到了3个activity可响应TECH_DISCOVERED,系统会弹出一个提示框,出现三种应用程序让用户选择。(此时activity C不会启动出来,因为按照优先级已经有其他的TECH_DISCOVERED应用程序可处理了,比如activity B)
除了上面说的之外,还有一种情况:假设activity D,同时设置了三个intent过滤器,即把NDEF_DISCOVERED、TECH_DISCOVERED和TAG_DISCOVERED这三种都包括了,按照原则,请求只要满足D的任一种过滤规则,则D会响应。比如:
1、 当一个TECH_DISCOVERED的标签靠近时,activity D和activityB都会响应;
2、 当一个TAG_DISCOVERED的标签靠近时,activity D和activityC都会响应;
3、 当一个标签同时具备TECH_DISCOVERED和TAG_DISCOVERED的属性时,则activity D和activityB会响应,activityC不会响应,因为TECH_DISCOVERED优先,已经检测到activity相应了,则不会继续判断TAG_DISCOVERED。
例子:杭州市民卡同时满足TECH_DISCOVERED中的
如果activity C为前台发布程序(正在前台运行的),则系统默认会让activity c来处理,如果activity C正常处理,则activity E不被唤起(前台发布系统的优先级规则大于intent系统发布规则);如果activity C处理失败,非正常跳出,则系统会弹出其他可响应的activity(比如activity E)供用户选择。
4、TECH_DISCOVERED的tech筛选规则 前面讲到了在activity的intent过滤器中,如果选用了TECH_DISCOVERED作为action的过滤模式,则必须要定义一个xml文件来筛选所能支持的NFC标准,步骤如下: