android - 当应用程序接收到 NFC 数据时,它会打开 "New Tag collected"

标签 android nfc intentfilter ndef nfc-p2p

我正在创建一个应用程序,其中两个设备通过 NFC 进行通信,然后一个传输到服务器。

我正在尝试为 Lollipop 前和 Lollipop 后开发此功能。问题是我在一个应用程序中创建我的 NDEF 消息,然后在另一个应用程序中接收它。但是,当我尝试在其他应用程序中接收时,会打开 NFC“收集新标签”屏幕而不是我的应用程序。这对我来说是一个真正的问题,我只是发送一个需要发送到 Web 服务的字符串。

下面是接收应用程序的 list :

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.devcompany.paymentcustomer" >
    <uses-permission android:name="android.permission.NFC" />
    <uses-permission android:name="android.permission.INTERNET"/>

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <activity
            android:name=".activities.HomeActivity"
            android:launchMode="singleTop"
            android:label="@string/app_name"
            android:screenOrientation="portrait">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <action android:name="android.nfc.action.NDEF_DISCOVERED" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

这是我的发送代码:

   mNfcAdapter = NfcAdapter.getDefaultAdapter(getActivity());


        //If device is running lollipop remove the touch to beam action
        if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
            Handler handler = new Handler();
            handler.postDelayed(new Runnable() {
                @Override
                public void run() {

                    mNfcAdapter.setNdefPushMessageCallback(nDefCallback, getActivity());
                    mNfcAdapter.invokeBeam(getActivity());
                }

            }, 2000);
        }else{
            //leave touch to beam action
            mNfcAdapter.setNdefPushMessageCallback(new NfcAdapter.CreateNdefMessageCallback() {
                @Override
                public NdefMessage createNdefMessage(NfcEvent event) {
                    NdefMessage message = new NdefMessage((new NdefRecord[]{createMime("application/com.devcompany.paymentvendor.fragments", mToBeam.getBytes()) }));

                    return message;
                }
            }, getActivity());

            mNfcAdapter.setOnNdefPushCompleteCallback(
                    new NfcAdapter.OnNdefPushCompleteCallback() {

                        @Override
                        public void onNdefPushComplete(NfcEvent event) {

                        }
                    }, getActivity());
        }

这是我的接收代码:

public class HomeActivity extends ActionBarActivity {

    private NfcAdapter mAdapter;
    private TextView textView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_home_layout);

        mAdapter = NfcAdapter.getDefaultAdapter(this);
        textView = (TextView)findViewById(R.id.fortressLabel);

    }

    @Override
    public void onResume(){
        super.onResume();
        if(NfcAdapter.ACTION_NDEF_DISCOVERED.equals(getIntent().getAction())){
            processIntent(getIntent());
        }
    }

    @Override
    public void onNewIntent(Intent intent) {
        // onResume gets called after this to handle the intent
        setIntent(intent);
    }

    private void processIntent(Intent intent){

        //textView.setText(intent.getDataString());
        Parcelable[] rawMsgs = intent.getParcelableArrayExtra(
                NfcAdapter.EXTRA_NDEF_MESSAGES);
        // only one message sent during the beam
        NdefMessage msg = (NdefMessage) rawMsgs[0];

        Log.i(this.getLocalClassName(), intent.getDataString());
    }
}

我已经调试了我的接收代码并单步执行,当我将手机放在一起时,代码甚至没有进入 onResume 方法。标签 Intent 首先启动。我不明白为什么会这样。谁能帮我解决这个问题?

最佳答案

您正在发送“application/com.devcompany.paymentvendor.fragments”类型的 MIME 类型记录:

NdefMessage message = new NdefMessage(new NdefRecord[] {
    NdefRecord.createMime("application/com.devcompany.paymentvendor.fragments",
                  mToBeam.getBytes())
});

因此,您还需要指示您的接收 Activity 实际接收该 MIME 类型记录。您可以通过为您的 Activity 添加 NDEF_DISCOVERED intent 过滤器来注册您的应用程序以在检测到 NFC 事件中的 MIME 类型时打开(和接收):

<activity android:name=".activities.HomeActivity" ...>
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />
        <category android:name="android.intent.category.LAUNCHER" />
    </intent-filter>
    <intent-filter>
        <action android:name="android.nfc.action.NDEF_DISCOVERED"/>
        <category android:name="android.intent.category.DEFAULT"/>
        <data android:mimeType="application/com.devcompany.paymentvendor.fragments" />
    </intent-filter>
</activity>

关于android - 当应用程序接收到 NFC 数据时,它会打开 "New Tag collected",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30849901/

相关文章:

android - Webview android目标='_blank'

android - 如何获取webView的url

android - 无法在 Android 中使用正确的 key 验证 Mifare 卡中的扇区

android - 在 android 中单击 gmail 通知时,在 Intent 选择器对话框中隐藏我的应用程序

java - Android Nougat 上的错误通知 : Couldn't expand RemoteViews for: StatusBarNotification.

java - Android 在 "<"上编辑文本时按键监听器?

android - 为什么Android和IOS11无法通过NFC通信

android - 无法使用 nfc_initiator_transceive_bytes() 通过 libnfc 发​​送大型 APDU 命令

javascript - Android Chrome 和 Intent 检测

android - 如何修复未 protected SMS BroadcastReceiver lint 警告