I use Ad8242 ECG sensor and ESP32. In my project im sending the data to database and next with php code i get data from database and show the chart in website. The problem is that i must use the frequency 50Hz, but i cand send so many httprequests to database. I'm thinking about is there an option to save the data temporary to data packets and next to send this data to database. I was trying to save the data by simple array but when i sent data i was reciving only 0 or id of data.
the probability of 50Hz to a database working is doubtful unless it is on a local network
rather than attempting to transmit 50 times/second try reducing traffic by transmitting 5 samples every tenth of a second
your chart should still update in near real time
we had a similar application recently collecting data from a sensor every 20mSec (using timer interrupts) which was saved into a ring buffer, formed into a frame and transmitted over BLE to a smart phone every second
the example mentioned in post #1 was was a commercial product implemented on a PIC24 processor
however, if you do aa web search for arduino ring buffer you will get plenty of links
* if (httpResponseCode>0) {* * Serial.print("HTTP Response code: ");* * Serial.println(httpResponseCode);* * }* * else {* * Serial.print("Error code: ");* * Serial.println(httpResponseCode);* * }* * // Free resources* * http.end();* * }* * else {* * Serial.println("WiFi Disconnected");* * }* * delay(1000);* } bool takeAnalogReadings(uint16_t* p_numReadings, uint16_t** p_analogVals) { * static const uint16_t NUM_READINGS = 20;
static uint16_t i = 0; // index* * static uint16_t analogVals[NUM_READINGS];
const uint32_t SAMPLE_PD = 50; // ms; sample period (how often to take a new sample)
static uint32_t tStart = millis(); // ms; start time* * bool bufferIsFull = false; // set to true each time NUM_READINGS have been taken* * // Only take a reading once per SAMPLE_PD* * uint32_t tNow = millis(); // ms; time now* * if (tNow - tStart >= SAMPLE_PD)
_ {_
_//Serial.print("taking sample num "); Serial.println(i + 1);_
tStart += SAMPLE_PD; // reset start time to take next sample at exactly the correct pd* _ analogVals = analogRead(A0);
* i++;_ if (i >= NUM_READINGS) _ { bufferIsFull = true; i = 0; // reset to beginning of array, so you don't try to save readings outside of the bounds of the array*
* } } // Assign the user-passed-in pointers so that the user can retrieve the data if they so desire to do it this way* * if (p_numReadings != nullptr)*
* { *p_numReadings = NUM_READINGS; }_ if (p_analogVals != nullptr) _ { *p_analogVals = analogVals; } return bufferIsFull; }*_
mkul:
Could you please send me your code for your project with ring buffer
this is an example where a timer interrupt service routine saves a record into a ring buffer every 20mSec
the main loop() then extracts the records and checks for sequence errors
// 20mSec timer interrupt - write record into ring buffer
// adapted from https://www.instructables.com/id/Arduino-Timer-Interrupts/
//timer1 will interrupt at every 20msec 50times/second // pin 13
// test structure
struct TESTrecord {
unsigned short int seq;
short int temperature;
}
testRecord;
// ring buffer and indexes
volatile byte data[sizeof(testRecord)*100+100]; // dual buffer for MEMS data
volatile int inData=0, outData=0, inDataCount=0; // index into buffers
//timer1 interrupt called every 20mSec
ISR(TIMER1_COMPA_vect){
// increment sequence number and add structure to ring buffer
testRecord.seq++;
memcpy((byte*) &data[inData], (byte*)&testRecord, sizeof(testRecord));;
// increment index to ring buffer and if at end reset to start
if((inData+=sizeof(testRecord))>=sizeof(testRecord)*100) inData=0;
// increment count of records in buffer
inDataCount++;
}
unsigned long int time=millis();
void loop(){
// check if records in ring buffer - if so read next record
while(inDataCount) {
// used to check sequence numbers of records in buffer and error count
static unsigned short int seqCheck=0, errors=0;
// if ring buffer overflow display message and reset
if(inDataCount>100) {
Serial.println("ring buffer overflow");
inData=0, outData=0, inDataCount=0, seqCheck=0, testRecord.seq=0;
errors++;
break;
}
// read a record from buffer
struct TESTrecord record;
memcpy((byte*)&record, (byte*) &data[outData], sizeof(testRecord));;
// if at end of buffer reset to start and display some data
if((outData+=sizeof(testRecord))>=sizeof(testRecord)*100) {
outData=0; Serial.print(" time "); Serial.print(millis()-time);
Serial.print(" seqcheck ");Serial.print(seqCheck);
Serial.print(" errors ");Serial.println(errors);
}
inDataCount--; // decrement count of records in buffer
// check record sequence number - if in error reset and display !
if(record.seq != ++seqCheck) {
seqCheck=record.seq; // reset
Serial.print('!');
errors++;
}
else Serial.print('*'); // sequence number OK
}
}
void setup(){
Serial.begin(115200);
pinMode(13, OUTPUT);
Serial.println("20mSec timer interrupt - write record into ring buffer");
cli();//stop interrupts
//set timer1 interrupt every 20mSec
TCCR1A = 0;// set entire TCCR1A register to 0
TCCR1B = 0;// same for TCCR1B
TCNT1 = 0;//initialize counter value to 0
// set compare match register for 1hz increments
OCR1A = 311;// = (16*10^6) / (50*1024) - 1 (must be <65536)
// turn on CTC mode
TCCR1B |= (1 << WGM12);
// Set CS12 and CS10 bits for 1024 prescaler
TCCR1B |= (1 << CS12) | (1 << CS10);
// enable timer compare interrupt
TIMSK1 |= (1 << OCIE1A);
sei();//allow interrupts
// delay(3000); // uncomment to force ring buffer overflow
}
a run gives
20mSec timer interrupt - write record into ring buffer
*************************************************************************************************** time 1996 seqcheck 99 errors 0
**************************************************************************************************** time 3993 seqcheck 199 errors 0
**************************************************************************************************** time 5990 seqcheck 299 errors 0
**************************************************************************************************** time 7987 seqcheck 399 errors 0
**************************************************************************************************** time 9984 seqcheck 499 errors 0
**************************************************************************************************** time 11980 seqcheck 599 errors 0
...
**************************************************************************************************** time 537139 seqcheck 26899 errors 0
**************************************************************************************************** time 539136 seqcheck 26999 errors 0
**************************************************************************************************** time 541132 seqcheck 27099 errors 0