如何将NDEF记录写入NFC标签? [英] How to write NDEF records to NFC tag?
问题描述
如何将NDEF消息写入NFC标签?我是否需要更改清单文件?到目前为止,我已经生成了NDEF消息的代码:
How do I write NDEF message to NFC tag? Do I have to change manifest file? So far I have code to generate NDEF message:
public NdefRecord createTextRecord(String payload, Locale locale, boolean encodeInUtf8) {
byte[] langBytes = locale.getLanguage().getBytes(Charset.forName("US-ASCII"));
Charset utfEncoding = encodeInUtf8 ? Charset.forName("UTF-8") : Charset.forName("UTF-16");
byte[] textBytes = payload.getBytes(utfEncoding);
int utfBit = encodeInUtf8 ? 0 : (1 << 7);
char status = (char) (utfBit + 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);
NdefRecord record = new NdefRecord(NdefRecord.TNF_WELL_KNOWN,
NdefRecord.RTD_TEXT, new byte[0], data);
return record;
}
我如何发现TAG?有人可以帮我吗?
How do I discover the TAG? Can someone help me with that?
推荐答案
我会忽略Google文档在 https://developer.android.com/guide/topics/connectivity/nfc/advanced-nfc#read-write ,因为这会给用户写标签带来非常糟糕的用户体验,并且由于用户行为而导致很多失败的写操作.
I would ignore what the Google documentation says for reading at https://developer.android.com/guide/topics/connectivity/nfc/nfc and for read/write at https://developer.android.com/guide/topics/connectivity/nfc/advanced-nfc#read-write as this provides a very poor user experience for writing to Tags and leads to a lot of failed writes because of user behaviour.
要使用Android可靠地编写NFC,您应该使用更新更好的 enableReaderMode
API
To get reliable writing to NFC with Android you should use the newer and much better enableReaderMode
API https://developer.android.com/reference/android/nfc/NfcAdapter
使用此更新的API,可减少写入失败和卡损坏的几率,因为您可以控制通知声音的发生时间.使用基于旧版 Intent
的系统,系统App会暂停您的应用程序,然后读取卡并发出通知声音,然后用户在恢复您的App之前采用卡的方式,并有机会处理该卡数据并写入卡.
Using this newer API leads to a lot less failed writes and corrupted cards because you can control when the notification sound happens. With the old Intent
based system the system App pauses your app and then reads the card and makes a notification sound, the user then takes the card way before your App is resumed and has a chance to handle the card data and write to the card.
使用更新的 enableReaderMode
API,您可以关闭系统通知声音,并且您的应用程序永不暂停读取NFC卡,然后您就可以对卡进行读写了,然后就可以成功写入了卡上,您可以自己发出通知.
With the newer enableReaderMode
API you turn off the system notification sound and your App is never paused to read the NFC card, you can then read and write to the card and then when you have successfully written to the card you can make the notification sound yourself.
由于所有错误均被忽略,因此用户将继续尝试出示卡,直到成功通知为止.不需要额外的逻辑,以免在每次出示单张卡或出示不同的卡时都向同一条消息写入相同的消息.
Because any errors are silent, the user will keep trying to present the card until the success Notification. Additional logic is needed not to write the same message to every time a single card is presented or when different cards are presented.
一些示例代码(从我的应用程序改编了NFC低级读写功能(不是Ndef Tag技术)
Some example code (adapted from my app the does NFC low level reading and writing (not Ndef Tag technology))
public class NFCActivity extends AppCompatActivity implements NfcAdapter.ReaderCallback{
private NfcAdapter mNfcAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_nfc);
mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
// Rest of Activity setup
}
@Override
protected void onResume() {
super.onResume();
if(mNfcAdapter!= null) {
Bundle options = new Bundle();
// Work around for some broken Nfc firmware implementations that poll the card too fast
options.putInt(NfcAdapter.EXTRA_READER_PRESENCE_CHECK_DELAY, 250);
// Enable ReaderMode for all types of card and disable platform sounds
mNfcAdapter.enableReaderMode(this,
this,
NfcAdapter.FLAG_READER_NFC_A |
NfcAdapter.FLAG_READER_NFC_B |
NfcAdapter.FLAG_READER_NFC_F |
NfcAdapter.FLAG_READER_NFC_V |
NfcAdapter.FLAG_READER_NFC_BARCODE |
NfcAdapter.FLAG_READER_NO_PLATFORM_SOUNDS,
options);
}
}
@Override
protected void onPause() {
super.onPause();
if(mNfcAdapter!= null)
mNfcAdapter.disableReaderMode(this);
}
// This method is run in another thread when a card is discovered
// !!!! This method cannot cannot direct interact with the UI Thread
// Use `runOnUiThread` method to change the UI from this method
public void onTagDiscovered(Tag tag) {
// Read and or write to Tag here to the appropriate Tag Technology type class
// in this example the card should be an Ndef Technology Type
Ndef mNdef = Ndef.get(tag);
// Check that it is an Ndef capable card
if (mNdef!= null) {
// If we want to read
// As we did not turn on the NfcAdapter.FLAG_READER_SKIP_NDEF_CHECK
// We can get the cached Ndef message the system read for us.
NdefMessage mNdefMessage = mNdef.getCachedNdefMessage();
// Or if we want to write a Ndef message
// Create a Ndef Record
NdefRecord mRecord = NdefRecord.createTextRecord("en","English String");
// Add to a NdefMessage
NdefMessage mMsg = new NdefMessage(mRecord);
// Catch errors
try {
mNdef.connect();
mNdef.writeNdefMessage(mMsg);
// Success if got to here
runOnUiThread(() -> {
Toast.makeText(getApplicationContext(),
"Write to NFC Success",
Toast.LENGTH_SHORT).show();
});
// Make a Sound
try {
Uri notification = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
Ringtone r = RingtoneManager.getRingtone(getApplicationContext(),
notification);
r.play();
} catch (Exception e) {
// Some error playing sound
}
} catch (FormatException e) {
// if the NDEF Message to write is malformed
} catch (TagLostException e) {
// Tag went out of range before operations were complete
} catch (IOException e){
// if there is an I/O failure, or the operation is cancelled
} finally {
// Be nice and try and close the tag to
// Disable I/O operations to the tag from this TagTechnology object, and release resources.
try {
mNdef.close();
} catch (IOException e) {
// if there is an I/O failure, or the operation is cancelled
}
}
}
}
这篇关于如何将NDEF记录写入NFC标签?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!