nfcを使って書くコードの取り敢えずのゴールを「Felicaカードのデータを読み出して人間が読める形式にする」という所に置こうと思う。※これは私が普段からPASMOを使用しており、一番身近でよく利用しているデバイスだからである。ほぼ毎日使用しているので、使用履歴も豊富だ。
Nexus Sのnfc機能は基本的にはnfcリーダでありFelicaフォーマットで書きこまれた非接触型のICカードデバイスからデータを読みだすことができるはずである。
- カードを翳されたことを検知する
常駐しているサービス"NfcService"がFelicaカードが翳されたことを検知して、インテント"android.nfc.action.TAG_DISCOVERED"をブロードキャストで投じるので、それに呼応するActivityを作成しておけばシステムが勝手に起動してくれる。(このAndroidプラットホームを利用した機構こそが素晴らしい)
SDKに添付されている"NFCDemo"では上記の通り、マニフェストにインテントフィルタを記述してTagViewerというActivityを起動している。
-
- Manifest.xml
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.android.nfc"
>
<uses-permission android:name="android.permission.NFC" />
<uses-permission android:name="android.permission.CALL_PHONE" />
〜 略
<activity android:name="TagViewer"
android:theme="@android:style/Theme.NoTitleBar">
<intent-filter>
<action android:name="android.nfc.action.TAG_DISCOVERED"/>
<category android:name="android.intent.category.DEFAULT"/>
</intent-filter>
</activity>
<uses-feature android:name="android.hardware.nfc" android:required="true" />
</manifest>
-
- TagViewer.java
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.tag_viewer);
mTagContent = (LinearLayout) findViewById(R.id.list);
mTitle = (TextView) findViewById(R.id.title);
resolveIntent(getIntent());
}
void resolveIntent(Intent intent) {
// Parse the intent
String action = intent.getAction();
if (NfcAdapter.ACTION_TAG_DISCOVERED.equals(action)) {
〜 NFCServiceからのインテントを処理する
}
ここまでは何も問題は無い。
この後、用意されたクラスとメソッドでデータがすんなり読み出せればそれで終了なのだが、そうは問屋がおろさない。
今もいろいろやっているが未だに上手くデータを読み出せない。というのもAndroid 2.3で公開されている数少ないクラスとメソッドではFelicaのデータは読み出せないのである。
同じくTagViewer.java中のコードからの抜粋だと、デバイス側からデータを読み出すには以下のコードで良いはずである。
Parcelable rawMsgs = intent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES); NdefMessage msgs = new NdefMessage[rawMsgs.length]; Listrecords = NdefMessageParser.parse(msgs[0]);
ところが実際にやってみると最初のNfcAdapter.EXTRA_NDEF_MESSAGESから取得できるはずのParcelableの配列がいきなりnullで戻る。 この段階では何もデータは取得できないのである。
さて困ったぞ。
※既に実現してる開発者がおりAndroidマーケットにアプリケーションが公開されているのは知っている。しかし、ソースコードが公開されていない以上、自分で納得のいくまでやってみたいのだ。