Question

How would you open your application directly using an intent filter when using the NFC service with a Mifare card? I know that you can use an intent filter using a specific mimeType directly for a P2P Connection like

<data android:mimeType="application/com.sticknotes.android"/>

I'm just not sure how I'd set up the sectors of a Mifare1K to do the same thing. Anybody have any ideas on how to do this? Or am I just limited to having the application chooser pop-up?

I suppose I could create a completely separate activity to handle passive tags versus active devices but is there any way to handle this all in one activity??

Was it helpful?

Solution

If your app already has an intent filter for the MIME type "application/com.sticknotes.android" that works with Android Beam (P2P connection), then it will also work with tags that contain and NDEF message with the same MIME type. Android Beam and tag discovery both generate an ACTION_NDEF_DISCOVERED intent in the receiving/reading device.

To write such an NDEF message to a MIFARE Classic 1K tag, you can create a simple app that does that for you. In this app's manifest file put:

<activity>
...
<intent-filter>
  <action android:name="android.nfc.action.TECH_DISCOVERED"/>
</intent-filter>

<meta-data android:name="android.nfc.action.TECH_DISCOVERED"
  android:resource="@xml/nfc_tech_filter" />
...
</activity>

And in project's res/xml folder put a file nfc_tech_filter.xml with the following contents:

<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
  <tech-list>
    <tech>android.nfc.tech.MifareClassic</tech>
  </tech-list>
</resources>

In the app's Activity put:

onCreate(Bundle savedInstanceState) {
  // put code here to set up your app
  ...

  // create NDEF message
  String mime = "application/com.sticknotes.android";
  byte[] payload = ... ; // put your payload here
  NdefRecord record = new NdefRecord(NdefRecord.TNF_MIME_MEDIA, mime.toBytes(), null, payload);
  NdefMessage ndef = new NdefMessage(new NdefRecord[] {ndef});

  // write NDEF message
  Intent intent = getIntent();
  if (NfcAdapter.ACTION_TECH_DISCOVERED.equals(intent.getAction()) {
    Tag tag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
    NdefFormatable nf = NdefFormatable.get(tag);
    if (nf != null) {
      // tag not yet formatted with NDEF
      try {
        nf.connect();
        nf.format(ndef);
        nf.close();
      } catch (IOException e) {
        // tag communication error occurred
      }
    } else {
      Ndef n = Ndef.get(tag);
      if (n != null && n.isWritable() ) {
        // can write NDEF
        try {
          n.connect();
          n.writeNdefMessage(ndef);
          n.close();
        } catch (IOException e) {
          // tag communication error occurred
        }
      }
    }
  }
}

This formats and writes an NDEF message to unformatted (blank) MIFARE Classic tags or overwrites tags that are already formatted with NDEF. If you want to write other tag types besides MIFARE Classic ones, adjust nfc_tech_filter.xml accordingly.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top