Skip to content

Commit

Permalink
feat: add uri record method
Browse files Browse the repository at this point in the history
  • Loading branch information
DeimosHall committed Dec 14, 2023
1 parent 7c1138c commit 8a29c4f
Show file tree
Hide file tree
Showing 6 changed files with 229 additions and 48 deletions.
16 changes: 11 additions & 5 deletions examples/NDEFSendMessage/NDEFSendMessage.ino
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
/**
* Example to send NDEF messages
*
* Note: If you know how to create custom NDEF messages, you can use the NDEFSendRawMessage example, otherwise, use this example.
*
* Authors:
* Salvador Mendoza - @Netxing - salmg.net
* Francisco Torres - Electronic Cats - electroniccats.com
*
* August 2023
* December 2023
*
* This code is beerware; if you see me (or any other collaborator
* member) at the local, and you've found our code helpful,
Expand All @@ -30,10 +33,13 @@ void setup() {
;
Serial.println("Send NDEF Message with PN7150");

message.addTextRecord("Hello"); // English by default
message.addTextRecord("world", "en"); // English explicitly, the library only supports two letter language codes (ISO 639-1) by now
message.addTextRecord("Hola mundo!", "es"); // Spanish explicitly, check a language code table at https://www.science.co.il/language/Locale-codes.php
message.addTextRecord("Bonjour le monde!", "fr"); // French explicitly
message.addTextRecord("Hello"); // English by default
message.addTextRecord("world", "en"); // English explicitly, the library only supports two letter language codes (ISO 639-1) by now
message.addTextRecord("Hola mundo!", "es"); // Spanish explicitly, check a language code table at https://www.science.co.il/language/Locale-codes.php
message.addTextRecord("Bonjour le monde!", "fr"); // French explicitly
message.addUriRecord("google.com"); // No prefix explicitly
message.addUriRecord("https://www.electroniccats.com"); // https://www. prefix explicitly, the library can handle all the prefixes listed at TODO: add link to prefixes table
message.addUriRecord("rtsp://test");
nfc.setSendMsgCallback(messageSentCallback);

Serial.println("Initializing...");
Expand Down
56 changes: 32 additions & 24 deletions examples/NDEFSendRawMessage/NDEFSendRawMessage.ino
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
/**
* Example to create a custom NDEF message and send it using the PN7150.
*
* Note: If you know how to create custom NDEF messages, you can use this example, otherwise, use the NDEFSend example.
*
*
* Note: If you know how to create custom NDEF messages, you can use this example, otherwise, use the NDEFSendMessage example.
*
* Authors:
* Salvador Mendoza - @Netxing - salmg.net
* Francisco Torres - Electronic Cats - electroniccats.com
*
* August 2023
* December 2023
*
* This code is beerware; if you see me (or any other collaborator
* member) at the local, and you've found our code helpful,
Expand All @@ -28,26 +28,34 @@ Electroniccats_PN7150 nfc(PN7150_IRQ, PN7150_VEN, PN7150_ADDR); // Creates a gl
NdefMessage message;

// Three records, "Hello", "world" and Uri "https://www.electroniccats.com"
const char ndefMessage[] = {0x91, // MB/ME/CF/1/IL/TNF
0x01, // Type length (1 byte)
0x08, // Payload length
'T', // Type -> 'T' for text, 'U' for URI
0x02, // Status
'e', 'n', // Language
'H', 'e', 'l', 'l', 'o', // Message Payload
0x11, // MB/ME/CF/1/IL/TNF
0x01, // Type length (1 byte)
0x08, // Payload length
'T', // Type -> 'T' for text, 'U' for URI
0x02, // Status
'e', 'n', // Language
'w', 'o', 'r', 'l', 'd', // Message Payload
0x51, // MB/ME/CF/1/IL/TNF
0x01, // Type length (1 byte)
0x13, // Payload length
'U', // Type -> 'T' for text, 'U' for URI
0x02, // Status
'e', 'l', 'e', 'c', 't', 'r', 'o', 'n', 'i', 'c', 'c', 'a', 't', 's', '.', 'c', 'o', 'm'}; // Message Payload
// const char ndefMessage[] = {0x91, // MB/ME/CF/1/IL/TNF
// 0x01, // Type length (1 byte)
// 0x08, // Payload length
// 'T', // Type -> 'T' for text, 'U' for URI
// 0x02, // Status
// 'e', 'n', // Language
// 'H', 'e', 'l', 'l', 'o', // Message Payload
// 0x11, // MB/ME/CF/1/IL/TNF
// 0x01, // Type length (1 byte)
// 0x08, // Payload length
// 'T', // Type -> 'T' for text, 'U' for URI
// 0x02, // Status
// 'e', 'n', // Language
// 'w', 'o', 'r', 'l', 'd', // Message Payload
// 0x51, // MB/ME/CF/1/IL/TNF
// 0x01, // Type length (1 byte)
// 0x13, // Payload length
// 'U', // Type -> 'T' for text, 'U' for URI
// 0x02, // Status
// 'e', 'l', 'e', 'c', 't', 'r', 'o', 'n', 'i', 'c', 'c', 'a', 't', 's', '.', 'c', 'o', 'm'}; // Message Payload

// One uri record "https://www.electroniccats.com"
const char ndefMessage[] = {0xD1,
0x01,
0x13,
'U',
0x02,
'e', 'l', 'e', 'c', 't', 'r', 'o', 'n', 'i', 'c', 'c', 'a', 't', 's', '.', 'c', 'o', 'm'};

void setup() {
Serial.begin(9600);
Expand Down
127 changes: 121 additions & 6 deletions src/NdefMessage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
* Authors:
* Francisco Torres - Electronic Cats - electroniccats.com
*
* August 2023
* December 2023
*
* This code is beerware; if you see me (or any other collaborator
* member) at the local, and you've found our code helpful,
Expand Down Expand Up @@ -160,14 +160,129 @@ void NdefMessage::addTextRecord(String text, String languageCode) {
record.setLanguageCode(languageCode);
record.setPayload(text);

#ifdef DEBUG3
Serial.println("Payload size: " + String(record.getPayloadSize()));
Serial.println("Payload: " + String((char *)record.getPayload()));
#endif

addRecord(record);
}

void NdefMessage::addTextRecord(String text) {
addTextRecord(text, NDEF_DEFAULT_LANGUAGE_CODE);
}

void NdefMessage::addUriRecord(String uri) {
NdefRecord record;
record.setHeaderFlags(NDEF_HEADER_FLAGS_SINGLE_RECORD);
record.setTypeLength(NDEF_TYPE_LENGTH);
record.setPayloadSize(uri.length() + 3);
record.setRecordType(NDEF_URI_RECORD_TYPE);

if (uri.startsWith("http://www.")) {
record.setStatus(NDEF_URI_HTTP_WWWDOT);
record.setPayload(uri.substring(11).c_str());
} else if (uri.startsWith("https://www.")) {
record.setStatus(NDEF_URI_HTTPS_WWWDOT);
record.setPayload(uri.substring(12).c_str());
} else if (uri.startsWith("http://")) {
record.setStatus(NDEF_URI_HTTP);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("https://")) {
record.setStatus(NDEF_URI_HTTPS);
record.setPayload(uri.substring(8).c_str());
} else if (uri.startsWith("tel:")) {
record.setStatus(NDEF_URI_TEL);
record.setPayload(uri.substring(4).c_str());
} else if (uri.startsWith("mailto:")) {
record.setStatus(NDEF_URI_MAILTO);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("ftp://anonymous:anonymous@")) {
record.setStatus(NDEF_URI_FTP_ANONIMOUS);
record.setPayload(uri.substring(26).c_str());
} else if (uri.startsWith("ftp://ftp.")) {
record.setStatus(NDEF_URI_FTP_FTPDOT);
record.setPayload(uri.substring(9).c_str());
} else if (uri.startsWith("ftps://")) {
record.setStatus(NDEF_URI_FTPS);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("sftp://")) {
record.setStatus(NDEF_URI_SFTP);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("smb://")) {
record.setStatus(NDEF_URI_SMB);
record.setPayload(uri.substring(6).c_str());
} else if (uri.startsWith("nfs://")) {
record.setStatus(NDEF_URI_NFS);
record.setPayload(uri.substring(6).c_str());
} else if (uri.startsWith("ftp://")) {
record.setStatus(NDEF_URI_FTP);
record.setPayload(uri.substring(6).c_str());
} else if (uri.startsWith("dav://")) {
record.setStatus(NDEF_URI_DAV);
record.setPayload(uri.substring(6).c_str());
} else if (uri.startsWith("news:")) {
record.setStatus(NDEF_URI_NEWS);
record.setPayload(uri.substring(5).c_str());
} else if (uri.startsWith("telnet://")) {
record.setStatus(NDEF_URI_TELNET);
record.setPayload(uri.substring(9).c_str());
} else if (uri.startsWith("imap:")) {
record.setStatus(NDEF_URI_IMAP);
record.setPayload(uri.substring(5).c_str());
} else if (uri.startsWith("rtsp://")) {
record.setStatus(NDEF_URI_RTSP);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("urn:")) {
record.setStatus(NDEF_URI_URN);
record.setPayload(uri.substring(4).c_str());
} else if (uri.startsWith("pop:")) {
record.setStatus(NDEF_URI_POP);
record.setPayload(uri.substring(4).c_str());
} else if (uri.startsWith("sip:")) {
record.setStatus(NDEF_URI_SIP);
record.setPayload(uri.substring(4).c_str());
} else if (uri.startsWith("sips:")) {
record.setStatus(NDEF_URI_SIPS);
record.setPayload(uri.substring(5).c_str());
} else if (uri.startsWith("tftp:")) {
record.setStatus(NDEF_URI_TFTP);
record.setPayload(uri.substring(5).c_str());
} else if (uri.startsWith("btspp://")) {
record.setStatus(NDEF_URI_BTSPP);
record.setPayload(uri.substring(8).c_str());
} else if (uri.startsWith("btl2cap://")) {
record.setStatus(NDEF_URI_BTL2CAP);
record.setPayload(uri.substring(10).c_str());
} else if (uri.startsWith("btgoep://")) {
record.setStatus(NDEF_URI_BTGOEP);
record.setPayload(uri.substring(9).c_str());
} else if (uri.startsWith("tcpobex://")) {
record.setStatus(NDEF_URI_TCPOBEX);
record.setPayload(uri.substring(10).c_str());
} else if (uri.startsWith("irdaobex://")) {
record.setStatus(NDEF_URI_IRDAOBEX);
record.setPayload(uri.substring(11).c_str());
} else if (uri.startsWith("file://")) {
record.setStatus(NDEF_URI_FILE);
record.setPayload(uri.substring(7).c_str());
} else if (uri.startsWith("urn:epc:id:")) {
record.setStatus(NDEF_URI_URN_EPC_ID);
record.setPayload(uri.substring(11).c_str());
} else if (uri.startsWith("urn:epc:tag:")) {
record.setStatus(NDEF_URI_URN_EPC_TAG);
record.setPayload(uri.substring(12).c_str());
} else if (uri.startsWith("urn:epc:pat:")) {
record.setStatus(NDEF_URI_URN_EPC_PAT);
record.setPayload(uri.substring(12).c_str());
} else if (uri.startsWith("urn:epc:raw:")) {
record.setStatus(NDEF_URI_URN_EPC_RAW);
record.setPayload(uri.substring(12).c_str());
} else if (uri.startsWith("urn:epc:")) {
record.setStatus(NDEF_URI_URN_EPC);
record.setPayload(uri.substring(8).c_str());
} else if (uri.startsWith("urn:nfc:")) {
record.setStatus(NDEF_URI_URN_NFC);
record.setPayload(uri.substring(8).c_str());
} else {
record.setStatus(NDEF_URI_NO_PREFIX);
record.setPayload(uri);
}

addRecord(record);
}
44 changes: 39 additions & 5 deletions src/NdefMessage.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
* Authors:
* Francisco Torres - Electronic Cats - electroniccats.com
*
* August 2023
* December 2023
*
* This code is beerware; if you see me (or any other collaborator
* member) at the local, and you've found our code helpful,
Expand All @@ -21,7 +21,6 @@
#include "T4T_NDEF_emu.h"
#include "ndef_helper.h"

#define MAX_NDEF_RECORDS 4
#define NDEF_HEADER_FLAGS_SINGLE_RECORD 0xD1
#define NDEF_HEADER_FLAGS_FIRST_RECORD 0x91
#define NDEF_HEADER_FLAGS_NEXT_RECORD 0x11
Expand All @@ -32,9 +31,45 @@
#define NDEF_STATUS 0x02
#define NDEF_DEFAULT_LANGUAGE_CODE "en"

class NdefMessage : NdefRecord {
#define NDEF_URI_NO_PREFIX 0x00
#define NDEF_URI_HTTP_WWWDOT 0x01
#define NDEF_URI_HTTPS_WWWDOT 0x02
#define NDEF_URI_HTTP 0x03
#define NDEF_URI_HTTPS 0x04
#define NDEF_URI_TEL 0x05
#define NDEF_URI_MAILTO 0x06
#define NDEF_URI_FTP_ANONIMOUS 0x07
#define NDEF_URI_FTP_FTPDOT 0x08
#define NDEF_URI_FTPS 0x09
#define NDEF_URI_SFTP 0x0A
#define NDEF_URI_SMB 0x0B
#define NDEF_URI_NFS 0x0C
#define NDEF_URI_FTP 0x0D
#define NDEF_URI_DAV 0x0E
#define NDEF_URI_NEWS 0x0F
#define NDEF_URI_TELNET 0x10
#define NDEF_URI_IMAP 0x11
#define NDEF_URI_RTSP 0x12
#define NDEF_URI_URN 0x13
#define NDEF_URI_POP 0x14
#define NDEF_URI_SIP 0x15
#define NDEF_URI_SIPS 0x16
#define NDEF_URI_TFTP 0x17
#define NDEF_URI_BTSPP 0x18
#define NDEF_URI_BTL2CAP 0x19
#define NDEF_URI_BTGOEP 0x1A
#define NDEF_URI_TCPOBEX 0x1B
#define NDEF_URI_IRDAOBEX 0x1C
#define NDEF_URI_FILE 0x1D
#define NDEF_URI_URN_EPC_ID 0x1E
#define NDEF_URI_URN_EPC_TAG 0x1F
#define NDEF_URI_URN_EPC_PAT 0x20
#define NDEF_URI_URN_EPC_RAW 0x21
#define NDEF_URI_URN_EPC 0x22
#define NDEF_URI_URN_NFC 0x23

class NdefMessage {
private:
NdefRecord records[MAX_NDEF_RECORDS];
static uint8_t recordCounter;
static unsigned char *content;
static unsigned short contentSize;
Expand All @@ -44,7 +79,6 @@ class NdefMessage : NdefRecord {
void getNextRecord();
static String getHexRepresentation(const byte *data, const uint32_t dataSize);
static String newString;
static void addContent(const char *record, unsigned short recordSize);
void addRecord(NdefRecord record);
static void updateHeaderFlags();

Expand Down
28 changes: 22 additions & 6 deletions src/NdefRecord.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
* Authors:
* Francisco Torres - Electronic Cats - electroniccats.com
*
* August 2023
* December 2023
*
* This code is beerware; if you see me (or any other collaborator
* member) at the local, and you've found our code helpful,
Expand All @@ -23,6 +23,11 @@ NdefRecord::NdefRecord() {
this->status = 0;
this->languageCode = 0;
this->newString = "null";
this->textRecord = false;
}

bool NdefRecord::isTextRecord() {
return this->textRecord;
}

void NdefRecord::create(NdefRecord_t record) {
Expand Down Expand Up @@ -240,6 +245,9 @@ String NdefRecord::getUri() {
}

void NdefRecord::setPayload(String payload) {
#ifdef DEBUG3
Serial.println("Payload: " + payload);
#endif
this->payload = new unsigned char[payload.length()];
strcpy((char *)this->payload, payload.c_str());
}
Expand All @@ -261,6 +269,7 @@ void NdefRecord::setStatus(uint8_t status) {
}

void NdefRecord::setLanguageCode(String languageCode) {
this->textRecord = true;
this->languageCode = new unsigned char[languageCode.length()];
strcpy((char *)this->languageCode, languageCode.c_str());
}
Expand All @@ -277,16 +286,23 @@ const char *NdefRecord::getContent() {
recordContent[2] = payloadSize;
recordContent[3] = recordType;
recordContent[4] = status;
recordContent[5] = languageCode[0];
recordContent[6] = languageCode[1];

for (int i = 0; i < getPayloadSize(); i++) {
recordContent[i + 7] = payload[i];
if (isTextRecord()) {
recordContent[5] = languageCode[0];
recordContent[6] = languageCode[1];

for (int i = 0; i < getPayloadSize(); i++) {
recordContent[i + 7] = payload[i];
}
} else {
for (int i = 0; i < getPayloadSize(); i++) {
recordContent[i + 5] = payload[i];
}
}

return recordContent;
}

unsigned short NdefRecord::getContentSize() {
return getPayloadSize() + 4; // 4 bytes for header, type length, payload length and record type
return getPayloadSize() + 4; // 4 bytes for header, type length, payload length and record type
}
Loading

0 comments on commit 8a29c4f

Please sign in to comment.