All the examples below have the host configure and parse the JSON data from UnitV/StickV, not switch the UnitV/StickV functions. To switch functions, please use M5Burner to burn the corresponding functional firmware to UnitV/StickV.
The firmware page is shown below:
The motion target detection function can be configured with two detection modes: static detection mode (COMPUTE_MODE_STATIC
) and dynamic detection mode (COMPUTE_MODE_DYNAMIC
). The default in M5Burner firmware is dynamic detection mode.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
int motion_cnt = 0;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
//Setting JSON
JSONVar obj;
obj["MOTION DETECT"] = 1.0; // Not optional
obj["mode"] = "COMPUTE_MODE_DYNAMIC"; // "COMPUTE_MODE_STATIC" or "COMPUTE_MODE_DYNAMIC"
obj["thr_w"] = 20; // optional
obj["thr_h"] = 20; // optional
obj["stepx"] = 1; // optional
obj["stepy"] = 2; // optional
obj["delta"] = 20; // optional
obj["merge"] = 10; // optional
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') {// clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar motion_detect_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(motion_detect_obj) == "undefined")){
display.fillRect(0, 35, 320, 205, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Motion Detect V-Func example");
if (motion_detect_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) motion_detect_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) motion_detect_obj["FUNC"]);
}
if (motion_detect_obj.hasOwnProperty("DIFF TOTAL")) {
Serial.print("Diff TOTAL = ");
Serial.println((int)motion_detect_obj["DIFF TOTAL"]);
display.printf(" Diff TOTAL: %d\n", (int)motion_detect_obj["DIFF TOTAL"]);
}
if (motion_detect_obj.hasOwnProperty("DIFF MAX")) {
Serial.print("Diff MAX = ");
Serial.println((int)motion_detect_obj["DIFF MAX"]);
display.printf(" Diff MAX: %d\n", (int)motion_detect_obj["DIFF MAX"]);
}
if (motion_detect_obj.hasOwnProperty("TOTAL")) {
motion_cnt = (int)motion_detect_obj["TOTAL"];
Serial.printf("Motion number = %d\n", motion_cnt);
display.printf(" Motion number: %d\n", motion_cnt);
}
for (int i = 0; i < motion_cnt; i++) {
display.setCursor(0, 120);
display.fillRect(0, 120, 320, 130, TFT_WHITE);
Serial.print("Motion ");
Serial.print(i);
display.printf("Motion %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) motion_detect_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int) motion_detect_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) motion_detect_obj[String(i)]["y"]);
display.printf("\r\n\t Y: %d", (int) motion_detect_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) motion_detect_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int) motion_detect_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) motion_detect_obj[String(i)]["h"]);
display.printf("\r\n\t Height: %d", (int) motion_detect_obj[String(i)]["h"]);
Serial.print("\tArea:");
Serial.println((int) motion_detect_obj[String(i)]["area"]);
display.printf("\r\n\t Area: %d", (int) motion_detect_obj[String(i)]["area"]);
delay(500);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
} else {
return;
}
}
}
The above example uses dynamic detection mode. When StickV/UnitV detects object motion, it will provide real-time feedback on the object's position and other data. The detection result is as shown below.
The object tracking function requires capturing the target object's information in the current camera frame after UnitV/StickV powers on to function properly. The capture start point and width/height parameter configuration code is shown below. To customize the capture position, please modify here.
obj["x"] = 80; //start point x-coordinate
obj["y"] = 0; //start point y-coordinate
obj["w"] = 100; //width
obj["h"] = 100; //height
The example below sends parameter data once after the host powers on. At that time, the StickV screen appears as shown below. Make sure the tracking target is within the yellow capture box.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
//Setting JSON
JSONVar obj;
obj["TARGET TRACKER"] = " V1.0";
obj["x"] = 80;
obj["y"] = 0;
obj["w"] = 100;
obj["h"] = 100;
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar object = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(object) == "undefined")){
display.fillRect(0, 35, 320, 205, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Target Tracker V-Func example");
if (object.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) object["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) object["FUNC"]);
}
if (object.hasOwnProperty("x")) {
Serial.print("X: ");
Serial.println((int) object["x"]);
display.printf(" X: %d\n", (int) object["x"]);
}
if (object.hasOwnProperty("y")) {
Serial.print("Y: ");
Serial.println((int) object["y"]);
display.printf(" Y: %d\n", (int) object["y"]);
}
if (object.hasOwnProperty("w")) {
Serial.print("Width: ");
Serial.println((int) object["w"]);
display.printf(" Width: %d\n", (int) object["w"]);
}
if (object.hasOwnProperty("h")) {
Serial.print("Height: ");
Serial.println((int) object["h"]);
display.printf(" Height: %d\n", (int) object["h"]);
}
display.waitDisplay();
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
} else {
return;
}
}
}
After successfully capturing the target object data, the host will display and print the object's position and other data in real time. The detection result is as shown below.
The color tracking function requires setting the target color parameters after UnitV/StickV powers on in order to operate correctly. The color parameters can be obtained using the LAB Color Picker Tool.
Steps for obtaining and configuring the color parameters:
open
at the lower part of the interface to open the sample image (this example's sample image), then click the specific area in the image to sample. Determine the final color parameters according to the white area below (i.e., the specific sampling position).LAB color
from the image above into the code below in order from left to right (from top to bottom). obj["Lmin"] = 0;
obj["Lmax"] = 100;
obj["Amin"] = 51;
obj["Amax"] = 61;
obj["Bmin"] = 34;
obj["Bmax"] = 44;
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 2, 2);
display.drawLine(0, 20, 320, 20, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
//Setting JSON
JSONVar obj;
obj["COLOR TRACKER"] = 1.0;
obj["thr_w"] = 20;
obj["thr_h"] = 20;
obj["stepx"] = 2;
obj["stepy"] = 2;
obj["merge"] = 10;
//Please fill in the below six parameters with the values extracted from the LAB color selection tool.
obj["Lmin"] = 0;
obj["Lmax"] = 100;
obj["Amin"] = 51;
obj["Amax"] = 61;
obj["Bmin"] = 34;
obj["Bmax"] = 44;
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar color_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(color_obj) == "undefined")) {
display.fillRect(0, 35, 320, 205, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Color Tracker V-Func example");
if (color_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) color_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) color_obj["FUNC"]);
}
int box_cnt = 0;
if (color_obj.hasOwnProperty("TOTAL")) {
box_cnt = (int)color_obj["TOTAL"];
Serial.printf("Box number = %d\n", box_cnt);
display.printf(" Box number: %d\n", box_cnt);
}
for (int i = 0; i < box_cnt; i++) {
Serial.print("Box ");
Serial.print(i);
display.printf("Box %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) color_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int) color_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) color_obj[String(i)]["y"]);
display.printf("\r\n\t Y: %d", (int) color_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) color_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int) color_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) color_obj[String(i)]["h"]);
display.printf("\r\n\t Height: %d", (int) color_obj[String(i)]["h"]);
Serial.print("\tArea:");
Serial.println((int) color_obj[String(i)]["area"]);
display.printf("\r\n\t Area: %d\r\n\t", (int) color_obj[String(i)]["area"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
}
delay(50);
}
}
When the program runs successfully, the host will display and print the tracked color block's position, size, quantity, and other data in real time. (In the case of multiple tracked color blocks, it is recommended to view the feedback data via serial monitor.) Detection result is as shown below.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
int face_cnt;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar face_detect_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(face_detect_obj) == "undefined")) {
display.fillRect(0, 35, 320, 205, TFT_WHITE);
// display.drawString("Parsing Json succeed!", 5, 30);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Face Detect V-Func example");
if (face_detect_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*)face_detect_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*)face_detect_obj["FUNC"]);
}
if (face_detect_obj.hasOwnProperty("count")) {
face_cnt = (int)face_detect_obj["count"];
Serial.printf("Face number = %d\n", face_cnt);
display.printf(" Face number: %d\n", face_cnt);
}
for (int i = 0; i < face_cnt; i++) {
Serial.print("Face ");
Serial.print(i + 1);
display.printf("Face %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int)face_detect_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int)face_detect_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int)face_detect_obj[String(i)]["y"]);
display.printf("\r\n\t Y: %d", (int)face_detect_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int)face_detect_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int)face_detect_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int)face_detect_obj[String(i)]["h"]);
display.printf("\r\n\t Height: %d", (int)face_detect_obj[String(i)]["h"]);
Serial.print("\tConfidence:");
Serial.println(face_detect_obj[String(i)]["value"]);
display.printf("\r\n\t Confidence:");
display.println(face_detect_obj[String(i)]["value"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
} else {
return;
}
}
}
Scan the face on the left side below, and the detection result is as shown on the right.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
//Setting JSON
JSONVar obj;
obj["FIND CODE"] = 1.0;
obj["mode"] = "QRCODE"; // Recognition mode, optional: QRCODE, APRILTAG, DATAMATRIX, BARCODE
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar code_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(code_obj) == "undefined")){
display.fillRect(0, 35, 320, 205, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack QRCode Detect V-Func example");
if (code_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) code_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) code_obj["FUNC"]);
}
int qrcode_cnt = 0;
if (code_obj.hasOwnProperty("count")) {
qrcode_cnt = (int)code_obj["count"];
Serial.printf("QR Code number = %d\n", qrcode_cnt);
display.printf(" QR Code number: %d\n", qrcode_cnt);
}
for (int i = 0; i < qrcode_cnt; i++) {
Serial.print("QRCode ");
Serial.print(i);
display.printf("QRCode %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) code_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int) code_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) code_obj[String(i)]["y"]);
display.printf(" Y: %d", (int) code_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) code_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int) code_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) code_obj[String(i)]["h"]);
display.printf(" Height: %d", (int) code_obj[String(i)]["h"]);
Serial.print("\tPayload:");
Serial.println((const char*) code_obj[String(i)]["payload"]);
display.printf("\r\n\t Payload: %s", (const char*) code_obj[String(i)]["payload"]);
Serial.print("\tVersion:");
Serial.println((int) code_obj[String(i)]["version"]);
display.printf("\r\n\t Version: %d", (int) code_obj[String(i)]["version"]);
Serial.print("\tECC Level:");
Serial.println((int) code_obj[String(i)]["ecc_level"]);
display.printf("\r\n\t ECC Level: %d", (int) code_obj[String(i)]["ecc_level"]);
Serial.print("\tMask:");
Serial.println((int) code_obj[String(i)]["mask"]);
display.printf("\r\n\t Mask: %d", (int) code_obj[String(i)]["mask"]);
Serial.print("\tData Type:");
Serial.println((int) code_obj[String(i)]["data_type"]);
display.printf("\r\n\t Data Type: %d", (int) code_obj[String(i)]["data_type"]);
Serial.print("\tECI:");
Serial.println((int) code_obj[String(i)]["eci"]);
display.printf("\r\n\t ECI: %d", (int) code_obj[String(i)]["eci"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
}
delay(50);
}
}
Scan the QR code on the left side below, and the detection result is as shown on the right.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
JSONVar obj;
obj["FIND CODE"] = 1.0;
obj["mode"] = "BARCODE"; // Recognition mode, optional: QRCODE, APRILTAG, DATAMATRIX, BARCODE
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar code_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(code_obj) == "undefined")){
display.fillRect(0, 35, 320, 205, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Barcode Detect V-Func example");
if (code_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) code_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) code_obj["FUNC"]);
}
int barcode_cnt = 0;
if (code_obj.hasOwnProperty("count")) {
barcode_cnt = (int)code_obj["count"];
Serial.printf("Barcode number = %d\n", barcode_cnt);
display.printf(" Barcode number: %d\n", barcode_cnt);
}
for (int i = 0; i < barcode_cnt; i++) {
Serial.print("Barcode ");
Serial.print(i);
display.printf("Barcode %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) code_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int) code_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) code_obj[String(i)]["y"]);
display.printf("\r\n\t Y: %d", (int) code_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) code_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int) code_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) code_obj[String(i)]["h"]);
display.printf("\r\n\t Height: %d", (int) code_obj[String(i)]["h"]);
Serial.print("\tPayload:");
Serial.println((const char*) code_obj[String(i)]["payload"]);
display.printf("\r\n\t Payload: %s", (const char*) code_obj[String(i)]["payload"]);
Serial.print("\tType:");
Serial.println((int) code_obj[String(i)]["type"]);
display.printf("\r\n\t Type: %d", (int) code_obj[String(i)]["type"]);
Serial.print("\tRotation:");
Serial.println((double) code_obj[String(i)]["rotation"]);
display.printf("\r\n\t Rotation: %f", (double) code_obj[String(i)]["rotation"]);
Serial.print("\tQuality:");
Serial.println((int) code_obj[String(i)]["quality"]);
display.printf("\r\n\t Quality: %d", (int) code_obj[String(i)]["quality"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
}
delay(50);
}
}
Scan the barcode below, and the detection result is as shown.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
JSONVar obj;
obj["FIND CODE"] = 1.0;
obj["mode"] = "DATAMATRIX"; // Recognition mode, optional: QRCODE, APRILTAG, DATAMATRIX, BARCODE
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar code_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(code_obj) == "undefined")){
display.fillRect(0, 40, 320, 200, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack DataMatrix Detect V-Func example");
if (code_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) code_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) code_obj["FUNC"]);
}
int dm_cnt = 0;
if (code_obj.hasOwnProperty("count")) {
dm_cnt = (int)code_obj["count"];
Serial.printf("DataMatrix number = %d\n", dm_cnt);
display.printf(" DataMatrix number: %d\n", dm_cnt);
}
for (int i = 0; i < dm_cnt; i++) {
Serial.print("DataMatrix ");
Serial.print(i);
display.printf("DataMatrix %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) code_obj[String(i)]["x"]);
display.printf("\r\n\t X: %d", (int) code_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) code_obj[String(i)]["y"]);
display.printf(" Y: %d", (int) code_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) code_obj[String(i)]["w"]);
display.printf("\r\n\t Width: %d", (int) code_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) code_obj[String(i)]["h"]);
display.printf(" Height: %d", (int) code_obj[String(i)]["h"]);
Serial.print("\tPayload:");
Serial.println((const char*) code_obj[String(i)]["payload"]);
display.printf("\r\n\t Payload: %s", (const char*) code_obj[String(i)]["payload"]);
Serial.print("\tRotation:");
Serial.println((double) code_obj[String(i)]["rotation"]);
display.printf("\r\n\t Rotation: %f", (double) code_obj[String(i)]["rotation"]);
Serial.print("\tRows:");
Serial.println((int) code_obj[String(i)]["rows"]);
display.printf("\r\n\t Rows: %d", (int) code_obj[String(i)]["rows"]);
Serial.print("\tColumns:");
Serial.println((int) code_obj[String(i)]["columns"]);
display.printf(" Columns: %d", (int) code_obj[String(i)]["columns"]);
Serial.print("\tCapacity:");
Serial.println((int) code_obj[String(i)]["capacity"]);
display.printf("\r\n\t Capacity: %d", (int) code_obj[String(i)]["capacity"]);
Serial.print("\tPadding:");
Serial.println((int) code_obj[String(i)]["padding"]);
display.printf("\r\n\t Padding: %d", (int) code_obj[String(i)]["padding"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
}
delay(50);
}
}
Scan the Datamatrix code on the left side below, and the detection result is as shown on the right.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::Font2);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 2, 2);
display.drawLine(0, 20, 320, 20, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
JSONVar obj;
obj["FIND CODE"] = 1.0;
obj["mode"] = "APRILTAG"; // Recognition mode, optional: QRCODE, APRILTAG, DATAMATRIX, BARCODE
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar code_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(code_obj) == "undefined")){
display.fillRect(0, 25, 320, 215, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack AprilTag Detect V-Func example");
if (code_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) code_obj["FUNC"]);
display.setCursor(0, 25);
display.printf(" V-Fun: %s\n", (const char*) code_obj["FUNC"]);
}
int april_cnt = 0;
if (code_obj.hasOwnProperty("count")) {
april_cnt = (int)code_obj["count"];
Serial.printf("AprilTag number = %d\n", april_cnt);
display.printf(" AprilTag number: %d\n", april_cnt);
}
for (int i = 0; i < april_cnt; i++) {
Serial.print("AprilTag ");
Serial.print(i);
display.printf("AprilTag %d:", i);
Serial.print(":\r\n\tX:");
Serial.println((int) code_obj[String(i)]["x"]);
display.printf(" X: %d", (int) code_obj[String(i)]["x"]);
Serial.print("\tY:");
Serial.println((int) code_obj[String(i)]["y"]);
display.printf(" Y: %d", (int) code_obj[String(i)]["y"]);
Serial.print("\tWidth:");
Serial.println((int) code_obj[String(i)]["w"]);
display.printf(" Width: %d", (int) code_obj[String(i)]["w"]);
Serial.print("\tHeight:");
Serial.println((int) code_obj[String(i)]["h"]);
display.printf(" Height: %d", (int) code_obj[String(i)]["h"]);
Serial.print("\tID:");
Serial.println((int) code_obj[String(i)]["id"]);
display.printf("\r\n\t ID: %d", (int) code_obj[String(i)]["id"]);
Serial.print("\tFamily:");
Serial.println((int) code_obj[String(i)]["family"]);
display.printf(" Family: %d", (int) code_obj[String(i)]["family"]);
Serial.print("\tCX:");
Serial.println((int) code_obj[String(i)]["cx"]);
display.printf(" CX: %d", (int) code_obj[String(i)]["cx"]);
Serial.print("\tCY:");
Serial.println((int) code_obj[String(i)]["cy"]);
display.printf(" CY: %d", (int) code_obj[String(i)]["cy"]);
Serial.print("\tRotation:");
Serial.println((double) code_obj[String(i)]["rotation"]);
display.printf("\r\n\t Rotation: %f", (double) code_obj[String(i)]["rotation"]);
Serial.print("\tDecision margin:");
Serial.println((double) code_obj[String(i)]["decision_margin"]);
display.printf("\r\n\t Decision margin: %f", (double) code_obj[String(i)]["decision_margin"]);
Serial.print("\tHamming:");
Serial.println((int) code_obj[String(i)]["hamming"]);
display.printf(" Hamming: %d", (int) code_obj[String(i)]["hamming"]);
Serial.print("\tGoodness:");
Serial.println((double) code_obj[String(i)]["goodness"]);
display.printf("\r\n\t Goodness: %f", (double) code_obj[String(i)]["goodness"]);
Serial.print("\tX translation:");
Serial.println((double) code_obj[String(i)]["x_translation"]);
display.printf("\r\n\t X translation: %f", (double) code_obj[String(i)]["x_translation"]);
Serial.print("\tY translation:");
Serial.println((double) code_obj[String(i)]["y_translation"]);
display.printf("\r\n\t Y translation: %f", (double) code_obj[String(i)]["y_translation"]);
Serial.print("\tZ translation:");
Serial.println((double) code_obj[String(i)]["z_translation"]);
display.printf("\r\n\t Z translation: %f", (double) code_obj[String(i)]["z_translation"]);
Serial.print("\tX rotation:");
Serial.println((double) code_obj[String(i)]["x_rotation"]);
display.printf("\r\n\t X rotation: %f", (double) code_obj[String(i)]["x_rotation"]);
Serial.print("\tY rotation:");
Serial.println((double) code_obj[String(i)]["y_rotation"]);
display.printf("\r\n\t Y rotation: %f", (double) code_obj[String(i)]["y_rotation"]);
Serial.print("\tZ rotation:");
Serial.println((double) code_obj[String(i)]["z_rotation"]);
display.printf("\r\n\t Z rotation: %f", (double) code_obj[String(i)]["z_rotation"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
}
delay(50);
}
}
Scan the Apriltag on the left side below, and the detection result is as shown on the right.
The line tracking function requires setting the line color parameters after UnitV/StickV powers on to operate correctly. These color parameters can be obtained using the LAB Color Picker Tool.
The process for obtaining and configuring the color parameters is the same as in Color Tracking. The example image of the weight sampling area is shown below. Please set the proportion values according to your own needs.
#include <M5Unified.h>
#include <M5GFX.h>
#include <Arduino_JSON.h>
M5GFX display;
void setup() {
display.begin();
display.setRotation(1);
display.clear(TFT_WHITE);
display.setFont(&fonts::FreeMonoBold9pt7b);
display.setTextColor(TFT_BLACK);
delay(100);
display.drawString("UnitV Json Example", 5, 5);
display.drawLine(0, 25, 320, 25, TFT_BLACK);
Serial.begin(115200);
Serial2.begin(115200, SERIAL_8N1, 13, 14);//PORT.C
//Setting JSON
JSONVar obj;
obj["LINE TRACKER"] = 1.0;
obj["thr_w"] = 20;
obj["thr_h"] = 20;
obj["stepx"] = 2;
obj["stepy"] = 2;
obj["merge"] = 10;
//Please fill in the below six parameters with the values extracted from the LAB color selection tool.
obj["Lmin"] = 0;
obj["Lmax"] = 100;
obj["Amin"] = 51;
obj["Amax"] = 61;
obj["Bmin"] = 34;
obj["Bmax"] = 44;
obj["weight_0"] = 0.1;
obj["weight_1"] = 0.3;
obj["weight_2"] = 0.6;
String jsonString = JSON.stringify(obj);
Serial2.println(jsonString);
Serial2.flush();
}
void loop() {
if (Serial2.available() > 0) {
String line = Serial2.readStringUntil('\r');
while (line.length() && line[0] != '{') { // clear '\0'
line.remove(0, 1);
}
Serial2.flush();
JSONVar line_obj = JSON.parse(line);
// JSON.typeof(jsonVar) can be used to get the type of the var
if (!(JSON.typeof(line_obj) == "undefined")){
display.fillRect(0, 40, 320, 200, TFT_WHITE);
Serial.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
Serial.println("M5Stack Line Tracker V-Func example");
if (line_obj.hasOwnProperty("FUNC")) {
Serial.print("V-Function = ");
Serial.println((const char*) line_obj["FUNC"]);
display.setCursor(0, 35);
display.printf(" V-Fun: %s\n", (const char*) line_obj["FUNC"]);
}
if (line_obj.hasOwnProperty("angle")) {
Serial.print("Angle: ");
Serial.println((double) line_obj["angle"]);
display.printf(" Angle: %f\n", (double) line_obj["angle"]);
}
Serial.println("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
} else {
return;
}
}
}
When the program runs successfully, the host will display and print the turn angle in real time.