M24LR64E-R ISO15693标签特定存储区多NDEF记录读写实现问询
我之前刚好折腾过M24LR64E-R这个标签的项目,对你遇到的这个问题太有共鸣了——普通NFC-V标签的多文本NDEF读写没问题,但要指定存储位置就懵了对吧?别慌,给你一步步梳理清楚:
先搞懂M24LR64E-R的存储逻辑
这个标签是64Kbit(也就是8KB)的容量,按4字节为一个块划分,总共有2048个块,地址从0x0000到0x07FF(十六进制)。前几个块(一般是0x0000到0x000F左右)是系统块,存标签配置、权限这些核心信息,绝对不能碰,建议从0x0010之后的块开始自定义存储NDEF消息。
步骤1:把多文本NDEF写入指定位置
核心思路是:先把你的多文本NDEF消息转成字节数组,然后分块写入到你指定的起始块地址。这里以Android平台为例(iOS用CoreNFC逻辑类似):
- 先确定你要用到的起始块,比如我习惯用
0x0010作为自定义存储的起始点; - 把已经编好的多文本NDEF消息转换成字节数组(假设叫
ndefBytes); - 用NFC-V的写块命令(命令码
0x21)分块写入,每个块写4字节:
int startBlock = 0x0010; // 自定义起始块地址 NfcV nfcV = NfcV.get(tag); nfcV.connect(); try { for (int i = 0; i < ndefBytes.length; i += 4) { int currentBlock = startBlock + (i / 4); byte[] blockData = new byte[4]; // 把NDEF字节数组的对应部分拷贝到块数据里,最后一个块不够4字节的话补0也没关系 System.arraycopy(ndefBytes, i, blockData, 0, Math.min(4, ndefBytes.length - i)); // 构造写块命令:0x21 + 块地址(2字节大端) + 4字节块数据 byte[] command = new byte[]{ (byte)0x21, (byte)((currentBlock >> 8) & 0xFF), (byte)(currentBlock & 0xFF), blockData[0], blockData[1], blockData[2], blockData[3] }; nfcV.transceive(command); } } catch (IOException e) { // 处理写入失败的情况,比如标签断开、权限不足 } finally { try { nfcV.close(); } catch (IOException ignored) {} }
⚠️ 注意:如果你的标签设置了读写密码,必须先发送密码验证命令(命令码0x2C),验证通过后才能执行写操作。
步骤2:从指定位置读取并展示多文本记录
读取的时候要和写入的起始块对应,然后把读取到的块数据拼接成完整的NDEF字节数组,再解析出文本记录:
int startBlock = 0x0010; int blockCount = 8; // 根据你的NDEF消息长度调整,比如8个块就是32字节 NfcV nfcV = NfcV.get(tag); nfcV.connect(); try { // 构造读块命令:0x20 + 起始块地址(2字节) + 块数(1字节) byte[] command = new byte[]{ (byte)0x20, (byte)((startBlock >> 8) & 0xFF), (byte)(startBlock & 0xFF), (byte)blockCount }; byte[] response = nfcV.transceive(command); // 响应的前2字节是状态码,0x0000表示成功,后面的是块数据 if (response[0] == 0x00 && response[1] == 0x00) { byte[] ndefBytes = new byte[blockCount * 4]; System.arraycopy(response, 2, ndefBytes, 0, ndefBytes.length); // 解析NDEF消息 NdefMessage ndefMessage = NdefMessage.parse(ndefBytes); // 遍历每个文本记录并展示 for (NdefRecord record : ndefMessage.getRecords()) { // 判断是不是标准文本记录 if (record.getTnf() == NdefRecord.TNF_WELL_KNOWN && Arrays.equals(record.getType(), NdefRecord.RTD_TEXT)) { // 文本记录的payload前2字节是语言编码,从第3字节开始是内容 String textContent = new String( record.getPayload(), 2, record.getPayload().length - 2, Charset.forName("UTF-8") ); // 这里把textContent展示到你的应用UI上,比如TextView.setText(textContent) } } } } catch (IOException e) { // 处理读取失败的情况 } finally { try { nfcV.close(); } catch (IOException ignored) {} }
几个关键提醒
- 地址别乱选:一定要避开系统块,不然可能导致标签变砖或者无法正常识别;
- NDEF完整性:写入和读取时要确保字节数组没有截断,比如NDEF消息长度是10字节的话,需要写3个块(12字节),读取的时候也要读3个块;
- 权限问题:如果标签被锁了,先解锁再操作,密码验证命令的格式可以查M24LR64E-R的 datasheet;
- 跨平台适配:iOS上用CoreNFC的
NFCISO15693Tag类,发送的命令格式和Android完全一样,只是API调用方式不同。
内容的提问来源于stack exchange,提问作者DaGuy
相关产品推荐
相关产品推荐

