I am reading the data from a "Torque Wrench" using "USB Host Shield2.0" and Arduino UNO. I am receiving correct data from my "Torque Wrench" Data is receiving in a array.
But when I started reading data after "for" loop inside Void loop() I am receiving incorrect data. I attached Both output pictures correct and incorrect data.
Basically I am read data from Torque Wrench and send to receiver using Nrf24l01. I am receiving incorrect data.
My question is :- Why I am reading Incorrect data outside "for" loop.
Correct Data inside "for" loop :- enter image description here
Incorrect Data outside "for" loop :- enter image description here
#include <SPI.h> // for SPI communication
#include <nRF24L01.h>
#include <RF24.h>
#include <cdcacm.h>
#include <usbhub.h>
//#include "pgmstrings.h"
// Satisfy the IDE, which needs to see the include statment in the ino too.
#ifdef dobogusinclude
#include <spi4teensy3.h>
#endif
#include <SPI.h>
RF24 radio(7, 8); // CE, CSN
const byte address[6] = {'R','x','A','A','A','B'}; // the address the the module
class ACMAsyncOper : public CDCAsyncOper
{
public:
uint8_t OnInit(ACM *pacm);
};
uint8_t ACMAsyncOper::OnInit(ACM *pacm)
{
uint8_t rcode;
// Set DTR = 1 RTS=1
rcode = pacm->SetControlLineState(3);
if (rcode)
{
ErrorMessage<uint8_t>(PSTR("SetControlLineState"), rcode);
return rcode;
}
LINE_CODING lc;
lc.dwDTERate = 9600;
lc.bCharFormat = 0;
lc.bParityType = 0;
lc.bDataBits = 8;
rcode = pacm->SetLineCoding(&lc);
if (rcode)
ErrorMessage<uint8_t>(PSTR("SetLineCoding"), rcode);
return rcode;
}
USB Usb;
//USBHub Hub(&Usb);
ACMAsyncOper AsyncOper;
ACM Acm(&Usb, &AsyncOper);
void setup() {
Serial.begin(9600);
radio.begin();
radio.openWritingPipe(address);
radio.setPALevel(RF24_PA_MAX);
radio.stopListening();
#if !defined(__MIPSEL__)
while (!Serial);
#endif
Serial.println("Start");
if (Usb.Init() == -1)
Serial.println("USB Not Connected");
delay( 200 );
}
void loop() {
Usb.Task();
if( Acm.isReady()) {
uint8_t rcode;
/* reading the keyboard */
if(Serial.available()) {
uint8_t data= Serial.read();
/* sending to the phone */
rcode = Acm.SndData(1, &data);
if (rcode)
ErrorMessage<uint8_t>(PSTR("SndData"), rcode);
}
delay(10);
uint8_t buf[64];
uint16_t rcvd = 64;
char text[64];
rcode = Acm.RcvData(&rcvd, buf);
if (rcode && rcode != hrNAK)
ErrorMessage<uint8_t>(PSTR("Ret"), rcode);
if ( rcvd ) {
for(uint16_t i=0; i < rcvd; i++ )
{
// Serial.print((char)buf[i]); // correct Data read from torque wrench
text[i] = (char)buf[i];
}
Serial.println(text); // reading wrong data here
//radio.write(&text, sizeof(text));
//Serial.println(text);
}
delay(10);
}
}
Character arrays must be null-terminated to count as C strings.
After the for loop, add text[rcvd] = '\0';
Also, your rcvd is fixed at 64. It needs to be one less than the array size for the null terminator to fit.
I have an issue while transferring the values of string from UART to buffer. I am using ESP8266 to receive strings on serial from STM32 device. I have total 600 string and i have CSV file that is being transmitted from the STM32 device. I have used proper filtering for every row on the NodeMCU side... I am having no clue why after 300 string the value transmitted to the buffer gets changed as well as the string read on UART also changes exactly after 300/305 string being transmitted. please let me know if there's any mistake in the code.
int i,j,k,l=0;
int httpCode=0;
String fields[24] = {"","month","year","hours","minutes","seconds","rimin","riavg","rimax","yimin","yiavg","yimax","bimin","biavg","bimax","nimin","niavg","nimax","eimin","eiavg","eimax","simin","siavg","simax"};
String element = "API_key=123&mac=0fa&day=";
String postApi1[300];
String postApi2[300];
String str= "";
String str_tx = "";
char char_array[128];
char* token;
char* rest = char_array;
WiFiClient client;
HTTPClient http;
void setup()
{
Serial.begin(230400);
s.begin(9600);
pinMode(13, INPUT);
pinMode(15, OUTPUT);
}
void loop()
{
if (s.available() >0)
{
for(j=0;j<300;j++)
{
i=0;
str = s.readStringUntil('\n');
Serial.println(str);
Serial.println("j");
postApi1[j]= str;
Serial.println(postApi1[j]);
str = "";
}
for(k=0;k<300;k++)
{
i=0;
str = s.readStringUntil('\n');
Serial.println(str);
Serial.println("k");
postApi2[k]= str;
Serial.println(postApi2[k]);
str = "";
}
}
}
Here is the code i am using and following is the Serial output of the code.
I think that the readStringUntil function waits for the terminator char. Is the '\n' sent also after 300th character? Also, try to avoid Serial.println in the read function, since the print function is quite slow, you might miss some characters. I would also avoid two for loops, instead, declare a variable, count number of received bytes and according to this save the "str" into "postApi1" or "postApi2".
Also, what is the purpose of "i" variable?
Hey #Andrej I tried your suggestion but it worked as follows
#include <Arduino.h>
#include <ESP8266WiFi.h>
#include <ESP8266WiFiMulti.h>
#include <SoftwareSerial.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClient.h>
#include <stdio.h>
#include <string.h>
using namespace std;
ESP8266WiFiMulti WiFiMulti;
SoftwareSerial s(13,15); //RX TX
double buff[24]; //Initialized variable to store recieved data
double val;
char c;
int i,j,k,l=0;
int httpCode=0;
String fields[24] = {"","month","year","hours","minutes","seconds","rimin","riavg","rimax","yimin","yiavg","yimax","bimin","biavg","bimax","nimin","niavg","nimax","eimin","eiavg","eimax","simin","siavg","simax"};
String element = "API_key=123&mac=0fa&day=";
String postApi[616];
String str= "";
String str_tx = "";
char char_array[128];
char* token;
char* rest = char_array;
WiFiClient client;
HTTPClient http;
void setup()
{
Serial.begin(230400);
s.begin(9600);
pinMode(13, INPUT);
pinMode(15, OUTPUT);
//Serial.setDebugOutput(true);
//ESP.wdtDisable();
//Serial.begin(115200);
// Serial.setDebugOutput(true);
Serial.println();
Serial.println();
Serial.println();
for (uint8_t t = 4; t > 0; t--) {
Serial.printf("[SETUP] WAIT %d...\n", t);
Serial.flush();
delay(1000);
}
WiFi.mode(WIFI_STA);
WiFiMulti.addAP("ECLP", "p##$w0rD");
if ((WiFiMulti.run() == WL_CONNECTED))
{
Serial.print("WIFI connected");
}
}
void loop()
{
if (s.available() >0)
{
for(j=0;j<616;j++)
{
i++;
str = s.readStringUntil('\n');
//Serial.println(str);
//Serial.println(j);
postApi[j]= str;
//Serial.println(postApi[j]);
str = "";
}
}
if(i == 616)
{
i=0;
for(k=0;k<616;k++)
{
Serial.println(k);
Serial.print(" : ");
Serial.print(postApi[k]);
}
}
}
And receive on the output the following thing
Just for the ref i printed "k" value with output to know at which string the data loss occurs in buffer
i read a few example and the value is string or number like this
json[] =
"{\"sensor\":\"gps\",\"time\":1351824120,\"data\":[48.756080,2.302038]}";
For example i have 2 values:
pack0.humidity = dht.readHumidity();
pack0.temperature = dht.readTemperature();
Can i read those temp and humid and add it to json in loop()
like this
json[] =
"{\"Temperature\": /*temp here*/,
\"Humidity\":/*humid here*/}";
Could anyone give me example for my project. thanks a lot.
My current code for rf24
struct package0
{
float temperature = 0;
float humidity = 0;
int soil = 0;
};
typedef struct package0 Package0;
Package0 pack0;
void loop()
{
delay(2000);
pack0.humidity = dht.readHumidity();
pack0.temperature = dht.readTemperature();
pack0.soil = map(analogRead(SOILPIN), 0, 4096, 100, 0);//convert to percentage
if (isnan(pack0.humidity) || isnan(pack0.temperature))
{
Serial.println(F("Failed to read from DHT sensor!"));
return;
}
RF24NetworkHeader header(master00);
bool ok = network.write(header, &pack0, sizeof(pack0));
Consider using ArduinoJson, which will do the JSON encoding for you. The advantage of this library is that it makes it easy to modify your data schema at a later time.
Or you can do it yourself by simply using snprintf:
const int BUFFER_SIZE = 48; // Choose a suitable number here
char json[BUFFER_SIZE];
snprintf(json, BUFFER_SIZE, "{\"Temperature\":%f,\"Humidity\":%f}", pack0.humidity, pack0.temperature);
json will then contain your JSON data. Using snprintf ensures that the write will not overflow.
I've got a problem with my arduino program. I'm using a RFID reader to scan cards (this part works flawlessly). I want the program to grant access to using some buttons (doesn't matter to be honest). The user who uses a verified card can use the functionalities until he scans a card again. I've deleted some unnecessary parts of the code.
#include <SPI.h>
#include <MFRC522.h>
String read_rfid;
String ok_rfid_1="a3f90f7"; //ID of the verified CARD
const int buzzer=8; //Buzzer
const int redLed=7;
const int greenLed=6;
const int yellowLed=5;
byte access=false; //
void setup() {
Serial.begin(9600); // Initialize serial communications with the PC
SPI.begin(); // Init SPI bus
mfrc522.PCD_Init(); // Init MFRC522 card
}
/*
* Helper routine to dump a byte array as hex values to Serial.
*/
void dump_byte_array(byte *buffer, byte bufferSize) {
read_rfid="";
for (byte i = 0; i < bufferSize; i++) {
read_rfid=read_rfid + String(buffer[i], HEX);
}
}
void granted() { } //it lights up the green led
void denied() { } //it lights up the red led
void login() {
if (read_rfid==ok_rfid_1) {
granted();
access=true;
} else {
denied();
}
delay(1000);
}
void logout() {
if (read_rfid==ok_rfid_1 && access==1) {
access=false;
Serial.println("Logout ");
}
}
void loop() {
// Look for new cards
if ( ! mfrc522.PICC_IsNewCardPresent())
return;
// Select one of the cards
if ( ! mfrc522.PICC_ReadCardSerial())
return;
dump_byte_array(mfrc522.uid.uidByte, mfrc522.uid.size);
Serial.println(read_rfid);
login();
while(access==true)
{logout();};
}
The logging in part works well, but it logs out automatically. As I observed the problem might be that if(read_rfid==ok_rfid_1 && access==1) is always true, because the read_rfid does not change. Do you have any ideas to solve my dillema?
Hi I'm trying to figure out how to split the following LCD display code for a scrolling LED effect. but when I try to use the Substring function I get the error "class string has no member named Substring"
void setup()
{
lcd.init();
}
void loop()
{
for(int i = 0; i < 20; i++) {
lcd.clear ();
lcd.backlight();
lcd.setCursor(i, 1);
String printy = "Hello World ";
String printy1 = printy.SubSting(0, 20-i);
String printy2 = printy.SubSting(20-i, 20);
lcd.print(printy1);
delay(500);
}
}
It helps if I spelled string correctly and put "substring" instead of "substing", sorry.