USB免驱NFC读写器 Android系统中NFC读写范例
由于Android具有良好的開(kāi)源優(yōu)勢(shì),可進(jìn)行深度定制開(kāi)發(fā)。?安卓系統(tǒng)市場(chǎng)應(yīng)用比windows晚,雖然支持的應(yīng)用不如windows系統(tǒng)多,但由于系統(tǒng)的免費(fèi)開(kāi)放性,眾多軟件廠商經(jīng)過(guò)近幾年的開(kāi)發(fā),已經(jīng)有越來(lái)越多的應(yīng)用加入進(jìn)來(lái),目前支持辦公、教學(xué)、娛樂(lè)已經(jīng)完全沒(méi)有問(wèn)題。因此,越來(lái)越多的行業(yè)接受并認(rèn)可基于Android操作系統(tǒng)的設(shè)備。
目前市面上大多數(shù)工業(yè)控制設(shè)備開(kāi)始采用Android系統(tǒng)了,然而這部分設(shè)備并沒(méi)有搭載原生的NFC功能。隨著近年來(lái),NFC功能需求的興起,很多行業(yè)需要一直可以支持Android系統(tǒng)的可接入Android設(shè)備并進(jìn)行二次開(kāi)發(fā)的 NFC讀寫器。因此,?L3-U這款NFC讀寫器 應(yīng)運(yùn)而生。作為一款采用USB免驅(qū)?的NFC讀寫器,支持在windows、Android、linux等操作系統(tǒng),免費(fèi)提供基于上述各種系統(tǒng)的SDK,方便客戶進(jìn)行功能擴(kuò)展和二次開(kāi)發(fā)。
L3-U這款USB免驅(qū)動(dòng)NFC讀寫器已經(jīng)設(shè)計(jì)好了USB 驅(qū)動(dòng),用戶在基于Android系統(tǒng)的設(shè)備上只有能獲取USB HOST權(quán)限或者采用OTG傳輸就可以使用,無(wú)需安裝額外驅(qū)動(dòng)。如果你其它非標(biāo)準(zhǔn)的Android設(shè)備,需要提供設(shè)備我們進(jìn)行編譯驅(qū)動(dòng)。以下為標(biāo)準(zhǔn)的具有USB HOST權(quán)限的設(shè)備接入NFC讀寫器的過(guò)程。供大家在進(jìn)行NFC讀寫器二次開(kāi)發(fā)過(guò)程中參考!
1、在項(xiàng)目中對(duì)AndroidManifest.xml文件進(jìn)行配置,獲取相關(guān)權(quán)限。
<uses-permission android:name="android.permission.NFC" /><uses-featureandroid:name="android.hardware.nfc"android:required="true" /> <uses-sdkandroid:minSdkVersion="12"android:targetSdkVersion="17" /><intent-filter><action android:name="android.nfc.action.NDEF_DISCOVERED" /><category android:name="android.intent.category.DEFAULT" /><data android:mimeType="text/*" /></intent-filter> <intent-filter><action android:name="android.nfc.action.TECH_DISCOVERED" /></intent-filter><meta-dataandroid:name="android.nfc.action.TECH_DISCOVERED"android:resource="@xml/nfc_tech_filter" />?
<uses-permission android:name="android.permission.NFC" /><uses-featureandroid:name="android.hardware.nfc"android:required="true" />? 添加了這句代碼,會(huì)使得在應(yīng)用商店下載應(yīng)用是過(guò)濾掉不支持NFC功能的設(shè)備。這里聲明了三種intent篩選條件,分別是action為
android.nfc.action.NDEF_DISCOVERED,
android.nfc.action.TECH_DISCOVERED,
android.nfc.action.TAG_DISCOVERED。
這一步可以幫助android系統(tǒng)內(nèi)的NFC模塊在掃描到一個(gè)NFC目標(biāo)的時(shí)候?qū)ふ业轿覀兊腶ctivity來(lái)進(jìn)行交互。
android系統(tǒng)內(nèi)的NFC模塊在掃描到一個(gè)NFC目標(biāo)后會(huì)通過(guò)以下幾步來(lái)尋找到合適的處理NFC消息的activity。在這之前先介紹兩個(gè)概念,1、Tag代表一個(gè)NFC目標(biāo),當(dāng)android設(shè)備掃描到一個(gè)NFC目標(biāo)的時(shí)候會(huì)將相關(guān)數(shù)據(jù)封裝成一個(gè)Tag實(shí)例,通過(guò)Intent傳遞給合適的activity去做處理。2、TagTechnology表示NFC標(biāo)簽支持的技術(shù),可以通過(guò)Tag的getTechList()獲取。
Tag的分發(fā)步驟:
a、先看Tag中是否包含了系統(tǒng)支持的NDEF數(shù)據(jù),如果包含則分發(fā)給注冊(cè)了action為ACTION_NEDF_DISCOVERED的activity。
b、如果Tag中不包含系統(tǒng)支持的NDEF數(shù)據(jù)或者沒(méi)有找到注冊(cè)了action為ACTION_NDEF_DISCOVERED的activity,則NFC系統(tǒng)模塊嘗試分發(fā)給一個(gè)action為ACTION_TECH_DISCOVERED的activity。NFC系統(tǒng)模塊在分發(fā)是首先分析NFC Tag支持的Tag Technology,然后尋找支持這類Tag Technology的activity,然后封裝了Tag數(shù)據(jù)的Intent分發(fā)給對(duì)應(yīng)的activity。
c、如果上面兩種都不滿足,則發(fā)送action為ACTION_TAG_DISCOVERED的intent
2、建立一個(gè)Activity頁(yè)面,用于實(shí)現(xiàn)NFC讀寫的功能。NFC讀寫功能實(shí)現(xiàn)的代碼如下:
package cc.lotusnfc;import java.io.IOException; import java.nio.charset.Charset; import java.sql.Date; import java.text.SimpleDateFormat; import java.util.Arrays;import cc.lotusnfc.R;import android.nfc.FormatException; import android.nfc.NdefMessage; import android.nfc.NdefRecord; import android.nfc.NfcAdapter; import android.nfc.NfcManager; import android.nfc.Tag; import android.nfc.tech.MifareClassic; import android.nfc.tech.Ndef; import android.nfc.tech.NfcA; import android.os.Bundle; import android.os.Parcelable; import android.annotation.SuppressLint; import android.app.Activity; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.content.IntentFilter; import android.view.Menu; import android.view.View; import android.widget.Button; import android.widget.EditText; import android.widget.TextView; import android.widget.Toast;public class MainActivity extends Activity {private TextView resultText;private PendingIntent pendingIntent;private IntentFilter[] mFilters;private String[][] mTechLists;private Button mJumpTagBtn;private boolean isFirst = true;private NfcAdapter m_NfcAdpater;private EditText m_edtLog;private Intent m_NfcIntent = null;@Overrideprotected void onCreate(Bundle savedInstanceState) {// 獲取nfc適配器,判斷設(shè)備是否支持NFC功能m_NfcAdpater = NfcAdapter.getDefaultAdapter(this);if (m_NfcAdpater == null) {Toast.makeText(this, "Not Found NfcAdapter!", Toast.LENGTH_SHORT).show();//finish();//return;} else if (!m_NfcAdpater.isEnabled()) {Toast.makeText(this, "Please Enabled NfcAdapter",Toast.LENGTH_SHORT).show();//finish();//return;}super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);m_edtLog = (EditText) findViewById(R.id.edtLog);m_edtLog.setText("");pendingIntent = PendingIntent.getActivity(this, 0, new Intent(this,getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);IntentFilter ndef = new IntentFilter(NfcAdapter.ACTION_TECH_DISCOVERED);ndef.addCategory("*/*");mFilters = new IntentFilter[] { ndef };// 過(guò)濾器mTechLists = new String[][] {new String[] { MifareClassic.class.getName() },new String[] { NfcA.class.getName() } };// 允許掃描的標(biāo)簽類型}@Overridepublic boolean onCreateOptionsMenu(Menu menu) {// Inflate the menu; this adds items to the action bar if it is present.getMenuInflater().inflate(R.menu.main, menu);return true;}@SuppressLint("NewApi")@Overrideprotected void onResume() {// TODO Auto-generated method stubsuper.onResume();m_NfcAdpater.enableForegroundDispatch(this, pendingIntent, mFilters,mTechLists);}private NdefMessage createMessage(String text) {NdefRecord[] record = new NdefRecord[1];String lang = "en";byte[] langBytes = lang.getBytes(Charset.forName("US-ASCII"));byte[] textBytes = text.getBytes(Charset.forName("UTF-8"));char status = (char) (langBytes.length);byte[] data = new byte[1 + langBytes.length + textBytes.length];data[0] = (byte) status;System.arraycopy(langBytes, 0, data, 1, langBytes.length);System.arraycopy(textBytes, 0, data, 1 + langBytes.length,textBytes.length);record[0] = new NdefRecord(NdefRecord.TNF_WELL_KNOWN,NdefRecord.RTD_TEXT, new byte[0], data);return new NdefMessage(record);}@Overrideprotected void onNewIntent(Intent intent) {// TODO Auto-generated method stubsuper.onNewIntent(intent);m_NfcIntent = intent;String strWriteText = "春眠不覺(jué)曉";if (NfcAdapter.ACTION_TECH_DISCOVERED.equals(intent.getAction())) {Tag tagFromIntent = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);Ndef ndef = Ndef.get(tagFromIntent);if (ndef != null) {NdefMessage ndefMessage = createMessage(strWriteText);try {ndef.connect();// READNdefMessage msg = ndef.getNdefMessage();if(null == msg) return;NdefRecord[] records = msg.getRecords();// NdefMessage nmsg = (NdefMessage) msgs[0];NdefRecord record = records[0];String resultStr = "";if (record.getTnf() == NdefRecord.TNF_WELL_KNOWN) {if (Arrays.equals(record.getType(), NdefRecord.RTD_TEXT)) {byte[] payload = record.getPayload();if (payload == null)return;try {String textEString = ((payload[0] & 0x80) == 0) ? "UTF-8": "UTF-16";int languageCodeLength = payload[0] & 0x3f;resultStr = new String(payload,languageCodeLength + 1, payload.length- languageCodeLength - 1,textEString);AddLog("Read:" + resultStr);} catch (Exception e) {e.printStackTrace();}}}// WRITEndef.writeNdefMessage(ndefMessage);AddLog("WRITE:" + strWriteText);ndef.close();} catch (IOException e) {// TODO Auto-generated catch blocke.printStackTrace();AddLog("IOException" );} catch (FormatException e) {// TODO Auto-generated catch blocke.printStackTrace();AddLog("FormatException" );}}}}private void AddLog(String strLog) {SimpleDateFormat formatter = new SimpleDateFormat("HH:mm:ss");Date curDate = new Date(System.currentTimeMillis());// 獲取當(dāng)前時(shí)間String strDate = formatter.format(curDate);if (null == m_edtLog)return;String strLogs = m_edtLog.getText().toString().trim();if (strLogs.equals("")) {strLogs = strDate + " " + strLog;} else {strLogs += "\r\n" + strDate + " " + strLog;}m_edtLog.setText(strLogs);}public void OnClearLogListener(View arg0) {if (null == m_edtLog)return;m_edtLog.setText("");}public void OnSetNfcListener(View arg0) {startActivityForResult(new Intent(android.provider.Settings.ACTION_WIRELESS_SETTINGS), 0); }public void OnTestListener(View arg0) {String strWriteText = "春眠不覺(jué)曉";if(null == m_NfcIntent) return;if (NfcAdapter.ACTION_TECH_DISCOVERED.equals(m_NfcIntent.getAction())) {Tag tagFromIntent = m_NfcIntent.getParcelableExtra(NfcAdapter.EXTRA_TAG);Ndef ndef = Ndef.get(tagFromIntent);if (ndef != null) {NdefMessage ndefMessage = createMessage(strWriteText);try {ndef.connect();// READNdefMessage msg = ndef.getNdefMessage();NdefRecord[] records = msg.getRecords();// NdefMessage nmsg = (NdefMessage) msgs[0];NdefRecord record = records[0];String resultStr = "";if (record.getTnf() == NdefRecord.TNF_WELL_KNOWN) {if (Arrays.equals(record.getType(), NdefRecord.RTD_TEXT)) {byte[] payload = record.getPayload();if (payload == null)return;try {String textEString = ((payload[0] & 0x80) == 0) ? "UTF-8": "UTF-16";int languageCodeLength = payload[0] & 0x3f;resultStr = new String(payload,languageCodeLength + 1, payload.length- languageCodeLength - 1,textEString);AddLog("Read:" + resultStr);} catch (Exception e) {e.printStackTrace();}}}// WRITEndef.writeNdefMessage(ndefMessage);AddLog("WRITE:" + strWriteText);ndef.close();} catch (IOException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (FormatException e) {// TODO Auto-generated catch blocke.printStackTrace();}}}} }?
總結(jié)
以上是生活随笔為你收集整理的USB免驱NFC读写器 Android系统中NFC读写范例的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 手把手教你安装华为网络模拟器及设备注册
- 下一篇: Android设备读写NFC标签