/*
NEXTION → ARDUINO DIAGNOSTIC RECEIVER
- In ra Serial Monitor (115200) khi nhận:
1) Khung nhị phân: A5 A5 A5 [page][type][index][d0][d1]
-> Log: [BIN] page,type,index,d0,d1,value
2) CSV: "CT1,<n0>,<n1>,<n2>."
-> Log: [CSV] n0,n1,n2
Chọn cổng Nextion:
- Với Mega/ESP32/STM32: #define USE_HW_SERIAL1
- Với UNO/Nano: comment dòng USE_HW_SERIAL1, dùng SoftwareSerial(10,11)
*/
// ====== CHỌN CỔNG NEXTION ======
#define USE_HW_SERIAL1 // <- Bỏ comment nếu bạn có Serial1 (Mega/ESP32/STM32)
#ifdef USE_HW_SERIAL1
#define NX Serial1
#else
#include <SoftwareSerial.h>
SoftwareSerial NX(10, 11); // RX, TX cho UNO/Nano
#endif
#define PC Serial // Serial Monitor
// ====== HỖ TRỢ IN HEX GỌN ======
static void printHex2(uint8_t b) {
if (b < 16) PC.print('0');
PC.print(b, HEX);
}
// ====== BỘ NHẬN KHUNG NHỊ PHÂN A5 A5 A5 + 5 BYTE ======
struct Frame5 { uint8_t page, type, index, d0, d1; };
static uint8_t a5count = 0; // đếm A5
static uint8_t pay_i = 0; // chỉ số byte payload
static Frame5 paybuf; // buffer 5 byte
void processBinaryByte(uint8_t b) {
// Đồng bộ 3 byte A5
if (a5count < 3) {
if (b == 0xA5) {
if (++a5count == 3) pay_i = 0; // chuẩn bị nhận 5 byte
} else {
a5count = 0; // mất sync
}
return;
}
// Nhận 5 byte payload
reinterpret_cast<uint8_t*>(&paybuf)[pay_i++] = b;
if (pay_i >= 5) {
// Hoàn tất 1 khung: log ra Serial
uint16_t value = (uint16_t)paybuf.d0 | ((uint16_t)paybuf.d1 << 8);
PC.print(F("[BIN] page=0x")); printHex2(paybuf.page);
PC.print(F(" type=0x")); printHex2(paybuf.type);
PC.print(F(" index=0x")); printHex2(paybuf.index);
PC.print(F(" d0=0x")); printHex2(paybuf.d0);
PC.print(F(" d1=0x")); printHex2(paybuf.d1);
PC.print(F(" value=")); PC.println(value);
// Reset chờ khung mới
a5count = 0;
pay_i = 0;
}
}
// ====== BỘ NHẬN CSV: "CT1,<n0>,<n1>,<n2>." ======
// Trạng thái đơn giản để tránh nhầm với nhị phân
enum CSVState { CSV_IDLE, CSV_C, CSV_CT, CSV_CT1, CSV_COLLECT };
static CSVState csv_state = CSV_IDLE;
static char csv_buf[64];
static uint8_t csv_len = 0;
void resetCSV() {
csv_state = CSV_IDLE;
csv_len = 0;
}
void processCSVByte(uint8_t b) {
char c = (char)b;
switch (csv_state) {
case CSV_IDLE: csv_state = (c=='C') ? CSV_C : CSV_IDLE; break;
case CSV_C: csv_state = (c=='T') ? CSV_CT : CSV_IDLE; break;
case CSV_CT: csv_state = (c=='1') ? CSV_CT1 : CSV_IDLE; break;
case CSV_CT1: csv_state = (c==',') ? CSV_COLLECT : CSV_IDLE;
if (csv_state == CSV_COLLECT) { csv_len = 0; csv_buf[csv_len++]='C'; csv_buf[csv_len++]='T'; csv_buf[csv_len++]='1'; csv_buf[csv_len++]=','; }
break;
case CSV_COLLECT:
if (csv_len < sizeof(csv_buf)-1) csv_buf[csv_len++] = c;
if (c == '.') {
csv_buf[csv_len] = '\0';
// csv_buf bây giờ có dạng "CT1,<n0>,<n1>,<n2>."
// Parse nhanh:
// Bỏ '.' cuối
if (csv_len && csv_buf[csv_len-1]=='.') csv_buf[csv_len-1] = '\0';
// Bỏ prefix "CT1,"
char *p = csv_buf + 4;
char *t0 = strtok(p, ",");
char *t1 = strtok(NULL, ",");
char *t2 = strtok(NULL, ",");
if (t0 && t1 && t2) {
int n0 = atoi(t0);
int n1 = atoi(t1);
int n2 = atoi(t2);
PC.print(F("[CSV] n0=")); PC.print(n0);
PC.print(F(" n1=")); PC.print(n1);
PC.print(F(" n2=")); PC.println(n2);
} else {
PC.println(F("[CSV] Parse error"));
}
resetCSV();
}
break;
}
}
// ====== BƠM DỮ LIỆU TỪ NEXTION SANG 2 BỘ NHẬN ======
void pumpNextion() {
while (NX.available()) {
uint8_t b = NX.read();
// Luồng nhị phân (A5 A5 A5 ...):
processBinaryByte(b);
// Luồng CSV (chỉ hoạt động nếu thấy 'CT1,'):
processCSVByte(b);
}
}
// ====== SETUP/LOOP ======
void setup() {
PC.begin(115200);
#ifdef USE_HW_SERIAL1
NX.begin(9600);
#else
NX.begin(9600);
#endif
PC.println(F("Ready. Press START on Nextion."));
PC.println(F("Expect either:"));
PC.println(F(" [BIN] page,type,index,d0,d1,value (for printh A5 A5 A5 ...)"));
PC.println(F(" [CSV] n0,n1,n2 (for prints \"CT1,... .\")"));
}
void loop() {
pumpNextion();
// làm việc khác nếu cần...
}
I want to send data n0n1n2=111 to arduino but serial is not read correctly, can someone help me, thank you very much!!!


