NFC(近场通信)在两个小环形天线之间使用磁感应,常用于各种智能卡的读写。项目采用Arduino Uno开发板读取PN532 NFC模块卡,显示器采用0.96″I2C OLED小屏幕。 使用的物料清单如下: Arduino Nano开发板 Adafruit PN532 RFID/NFC模块 SSD1306 0.96″OLED显示器 跳线 面包板 Arduino IDE(集成开发环境) Adafruit PN532 NFC近场通讯模块兼容Arduino设备,运用UART串口进行通讯。可用USB to UART转换器,通过电脑进行测试。用户也可根据自己需要,利用管脚改变数据传输方式,如IIC、SPI等。 该PN532 NFC近场通讯模块基于NXP PN532芯片,包含80C51微控制器内核,集成了13.56MHz下的各种主动/被动式非接触通信方法和协议,支持6种不同的工作模式: 读写器模式,支持ISO/IEC 14443A / MIFARE机制 读写器模式,支持 FeliCa机制 读写器模式,支持ISO/IEC 14443B机制 卡操作模式,支持ISO 14443A / MIFARE机制 卡操作模式,FeliCa机制 ISO/IEC18092,ECM340点对点 首先,我们按照电路图将PN532模块和OLED显示器连接到Arduino开发板: GND (Ground) GND VCC (Power supply) 5V SDA (Data) A4 SCL (Clock) A5 为读卡器更先进,我们采用Adafruit PN532 library,这个数据库兼容Arduino UNO/Nano板,支持I2C or SPI通信模式。下载Adafruit PN532库、Adafruit GFX库和SSD1306 OLED库,将如下代码上传到Arduino Nano开发板: #include #include #include #include #include #define PN532_IRQ (2) #define PN532_RESET (3) // Not connected by default on the NFC Shield #define SCREEN_WIDTH 128 // OLED display width, in pixels #define SCREEN_HEIGHT 64 // OLED display height, in pixels #define OLED_RESET 4 // Reset pin # (or -1 if sharing Arduino reset pin) #define SCREEN_ADDRESS 0x3C ///< See datasheet for Address; 0x3D for 128x64, 0x3C for 128x32; Adafruit_PN532 nfc(PN532_IRQ, PN532_RESET); Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET); void setup(void) { Serial.begin(115200); while (!Serial) delay(10); // for Leonardo/Micro/Zero Serial.println("Hello!"); nfc.begin(); if (!display.begin(SSD1306_SWITCHCAPVCC, SCREEN_ADDRESS)) { Serial.println(F("SSD1306 allocation failed")); for (;;); // Don't proceed, loop forever } uint32_t versiondata = nfc.getFirmwareVersion(); if (! versiondata) { Serial.print("Didn't find PN53x board"); while (1); // halt } // Got ok data, print it out! Serial.print("Found chip PN5"); 24) & 0xFF, HEX); Serial.print("Firmware ver. "); 16) & 0xFF, DEC); 8) & 0xFF, DEC); display.clearDisplay(); display.setCursor(0, 0); //oled display display.setTextSize(1); display.setTextColor(WHITE); display.print("Found chip PN5"); 24) & 0xFF, HEX); display.setCursor(0, 20); //oled display display.setTextSize(1); display.setTextColor(WHITE); display.print("Firmware ver. "); 16) & 0xFF, DEC); display.print("."); 8) & 0xFF, DEC); nfc.setPassiveActivationRetries(0xFF); // configure board to read RFID tags nfc.SAMConfig(); Serial.println("Waiting for an ISO14443A card"); display.setCursor(0, 40); //oled display display.setTextSize(1); display.setTextColor(WHITE); display.print("Waiting for NFC Card"); display.display(); } void loop(void) { boolean success; uint8_t uid , &uidLength); if (success) { Serial.println("Found a card!"); Serial.print("UID Length: "); Serial.print(uidLength, DEC); Serial.println(" bytes"); Serial.print("UID Value: "); display.clearDisplay(); display.setCursor(10, 0); //oled display display.setTextSize(1); display.setTextColor(WHITE); display.print("UID Length:"); display.print(uidLength, DEC); display.print(" bytes"); display.setCursor(35, 20); //oled display display.setTextSize(1); display.setTextColor(WHITE); display.println("UID Value: "); display.setCursor(5, 35); //oled display for (uint8_t i=0; i < uidLength; i++) { Serial.print(" 0x"); Serial.print(uid , HEX); display.print(" 0x"); display.print(uid , HEX); display.display(); } Serial.println(""); // Wait 1 second before continuing delay(1000); } else { // PN532 probably timed out waiting for a card Serial.println("Timed out waiting for a card"); } } 上传成功后就可以开始测试了。OLED显示器将显示固件版本1.6,并询问是否扫描卡片。 将银行卡、旅行卡、公交卡等NFC卡靠近PN532 NFC模块板,PN532将读取字节长度和UID值,并显示在OLED屏幕上。 字节长度有时是4位,有时是7位,这取决于卡的发卡机构的设定。如果不喜欢这个OLED显示器,也可以改用串口监视工具Serial Monitor来显示UID值和字节长度。