Mo Hany
Created July 16, 2020

SPIRErate

Low cost IoT powered Portable Ventilator Device.

IntermediateFull instructions provided33
SPIRErate

Things used in this project

Hardware components

pressure sensors
×3
OSEPP Max- Arduino
×1
DS3235 Servo motor
×1
ACV
×1
SIMV
×1

Software apps and online services

Abode xd

Hand tools and fabrication machines

3D Printer (generic)
3D Printer (generic)
Laser cutter (generic)
Laser cutter (generic)

Story

Read more

Code

acv_mode.ino

Arduino
#include <Guino.h>
#include <Servo.h>
Servo servoright;
int pos = 0;    

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 2;
int pinguage_mask = 5;
int pinguage_expiration = 4;
int pinguage_diff = 3;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;
uint32_t endTime;


// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int mode;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
//  attachInterrupt(0, pin_ISR, CHANGE);
}
 
void loop()
 
{
  // ========== Read all analog input & Detecting Mode Settings =============
  pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
  pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
  pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
  
  mode = digitalRead(inPin);

  IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);     // scale it to use it with the servo (value between 0 and 180)
  TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     // scale it to use it with the servo (value between 0 and 180)
  BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     // scale it to use it with the servo (value between 0 and 180)

  // ====== Copmute respiration separation time based on pot inputs ==========
  separation = 60/BPM - (1+IE_ratio);
  if (separation < 0)
  {
    IE_ratio = 60/BPM - 1;
    separation = 60/BPM - (1+IE_ratio);
  }

/*   if (mode == HIGH && previous == LOW && millis() - t_time > debounce) 
  {
      // ========= Servo a-Clockwise motion =============
      for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
      {                                  // in steps of 1 degree
        servoright.write(pos);
        delay(1000/TidVol);                       
        // ============ Update pressure values =========
        pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
        pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
        pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
        
        Serial.println(pressure_mask);
        //Serial.println(pressure_diff);
        //Serial.println(pressure_expiration);
      }
      delay(15);
      
      // ========= Servo Clockwise motion ============
      for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
      {                                
        servoright.write(pos);
        delay(1000*IE_ratio/TidVol);                       
        // ============ Update pressure values =========
        pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
        pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
        pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
        
        Serial.println(pressure_mask);
        //Serial.println(pressure_diff);
        //Serial.println(pressure_expiration);
      }  
      delay(separation*1000);
  }
  else 
  {  */
    endTime = millis();  
    while(digitalRead(inPin) == HIGH)
      {
        pressure_diff = analogRead(pinguage_diff);   
        
        acv_mode();  
      }
      
//  }
previous = mode;

}

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { 
        IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
      }
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = analogRead(pinguage_diff);       
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 

      

      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }


  }
  
  /* per_breath_time = 1/BPM*60;
  per_inspiration_time = 1/(1+1/IE_ratio)*per_breath_time;
  per_expiration_time = per_breath_time - per_inspiration_time;
  for(int i=0;i<5;i++){
  human_effort = analogRead(pinguage_mask);
  check_value = (map(analogRead(human_effort), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
  delay(5);
  }
  //human_effort = analogRead(pinguage_mask);
  if(check_value < -1){
    if( check_value < -0.5 && check_value > -1){
    TidVol = 0.8*TidVol;
    per_inspiration_time = 0.8*per_inspiration_time;
    delay(per_inspiration_time);
    IE_ratio = per_inspiration_time/per_expiration_time; 
    }
    else if (check_value < -1 && check_value  > -2){
    TidVol = 0.6*TidVol;
    per_inspiration_time = 0.6*per_inspiration_time;
    delay(per_inspiration_time);
    IE_ratio = per_inspiration_time/per_expiration_time;
    }
    else if (check_value  < -2 && check_value > -3){
    TidVol = 0.4*TidVol;
    per_inspiration_time = 0.4*per_inspiration_time;
    delay(per_inspiration_time);
    IE_ratio = per_inspiration_time/per_expiration_time;
    }
    else if (check_value < -4){
    TidVol = 0.2*TidVol;
    per_inspiration_time = 0.2*per_inspiration_time;
    delay(per_inspiration_time);
    IE_ratio = per_inspiration_time/per_expiration_time;
    }
  }
 */
}

// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = analogRead(pinguage_diff); 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    if (millis() - endTime > (uint32_t)100)
        {
          Serial.println(pressure_mask);
          endTime = millis();
        }
    //Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================
uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = analogRead(pinguage_diff);   
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    if (millis() - endTime > (uint32_t)100)
        {
          Serial.println(pressure_mask);
          endTime = millis();
        }
    //Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}



// =============================
// Copmute volume and flow rates
// =============================
void computeFlows(float area_1, float area2)
{
  float pressureDiff;
  float pressure_cmH2o;
  float pressure_pa;
  float rho = 1.225;
  float massFlow;
  float volFlow;
  
  pressure_cmH2o = (analogRead(pinguage_diff) - pressureDiffSensorOffset)*10.1972/92;
  pressure_pa = pressure_cmH2o*98.0665;
//  massFlow=1000*sqrt((abs(pressure_pa)*2*rho)/((1/(pow(area_2,2)))-(1/(pow(area_1,2))))); 
  volFlow = massFlow/rho; 
  
} 

arduino_acv_simv_code.ino

Arduino
#include <Guino.h>

#include <Servo.h>
#include<SoftwareSerial.h>

//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

Servo servoright;
int pos = 0;   

 

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 2;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int mode;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(115200); //enable SUART Port for communication with NODEMCU
//  attachInterrupt(0, pin_ISR, CHANGE);
}
 
void loop()
 
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
      }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
    SUART.print('<');                   //<(start mark)
    SUART.print((int)BPM,DEC);
      SUART.print(',');                   //,(data seperator)
      SUART.print((int)IE_ratio, DEC);
    SUART.print(',');                   //,(data seperator)
    SUART.print((int)TidVol, DEC);
    SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_mask, DEC);
      SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_diff, DEC);
    SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_expiration, DEC);
      SUART.print('>');                   //>(end mark)
    SUART.println();
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }


  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    SUART.print('<');                   //<(start mark)
    SUART.print((int)BPM,DEC);
      SUART.print(',');                   //,(data seperator)
      SUART.print((int)IE_ratio, DEC);
    SUART.print(',');                   //,(data seperator)
    SUART.print((int)TidVol, DEC);
    SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_mask, DEC);
      SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_diff, DEC);
    SUART.print(',');                   //,(data seperator)
      SUART.print((int)pressure_expiration, DEC);
      SUART.print('>');                   //>(end mark)
    SUART.println();
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
      }

  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}

nodemcu_serial_wifi.ino

Arduino
#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif



#include <Wire.h>

#include<SoftwareSerial.h>
SoftwareSerial SUART(4, 5); //SRX=Dpin-D2; STX-DPin-D1


//===================================
//  Variables for storing pressure data
//===================================

float BPM = 0.00;
float IE_ratio = 0.00;
float TidVol = 0.00;
float pressure_mask = 0.00;
float pressure_diff = 0.00;
float pressure_expiration = 0.00;
float list_values[5] ;

//=======================================
const byte numChars = 32;
char receivedChars[numChars];
char tempChars[numChars];        // temporary array for use when parsing

boolean newData = false;


// Replace with your network credentials
const char* ssid     = "NETGEAR43";
const char* password = "smilingnest196";  

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "http://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "San Diego";

void setup() {
  Serial.begin(115200); //enable Serial Monitor
  SUART.begin(115200); //enable SUART Port
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
  
}

void loop() {
  recvWithStartEndMarkers();
    if (newData == true) {
        strcpy(tempChars, receivedChars);
            // this temporary copy is necessary to protect the original data
            //   because strtok() used in parseData() replaces the commas with \0
        parseData();
        newData = false;
    }
  Serial.print(list_values[0]);
  send_data(list_values);
  
  }

//======================================

void recvWithStartEndMarkers() {
    static boolean recvInProgress = false;
    static byte ndx = 0;
    char startMarker = '<';
    char endMarker = '>';
    char rc;

    while (Serial.available() > 0 && newData == false) {
        rc = Serial.read();

        if (recvInProgress == true) {
            if (rc != endMarker) {
                receivedChars[ndx] = rc;
                ndx++;
                if (ndx >= numChars) {
                    ndx = numChars - 1;
                }
            }
            else {
                receivedChars[ndx] = '\0'; // terminate the string
                recvInProgress = false;
                ndx = 0;
                newData = true;
            }
        }

        else if (rc == startMarker) {
            recvInProgress = true;
        }
    }
}

//========================================

void parseData() {      // split the data into its parts

    char * strtokIndx; // this is used by strtok() as an index

    for (int i=0;i<5;i++)
  {
    if(i=0){
      strtokIndx = strtok(tempChars,",");
    }
    else
    {
      strtokIndx = strtok(NULL, ",");
    }
    list_values[i] = atof(strtokIndx);
  }
}

void send_data(float list_data[]) {
if(WiFi.status()== WL_CONNECTED){
    HTTPClient http;
    
    // Your Domain name with URL path or IP address with path
    http.begin(serverName);
    
    // Specify content-type header
    http.addHeader("Content-Type", "application/x-www-form-urlencoded");
    // Prepare your HTTP POST request data
    //sample1 = sample1 + 0.646;
    //sample2 = sample2 + 0.545;
    //sample3 = sample3 + 0.666;
    String httpRequestData = "api_key=" + apiKeyValue + "&sensor=" + sensorName
                          + "&location=" + sensorLocation + "&value1=" + String(list_data[0])
                          + "&value2=" + String(list_data[1]) + "&value3=" + String(list_data[2]) + "";
    Serial.print("httpRequestData: ");
    Serial.println(httpRequestData);
  
  int httpResponseCode = http.POST(httpRequestData);
  
  if (httpResponseCode>0) {
      Serial.print("HTTP Response code: ");
      Serial.println(httpResponseCode);
    }
    else {
      Serial.print("Error code: ");
      Serial.println(httpResponseCode);
    }
    // Free resources
    http.end();
}}

acv_simv.ino

Arduino
#include <Guino.h>

#include <Servo.h>
 
Servo servoright;
int pos = 0;    

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 2;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 3;

// ==== Analog Pins ====
int inPin = 2;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int mode;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
//  attachInterrupt(0, pin_ISR, CHANGE);
}
 
void loop()
 
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
      }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;

      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }


  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
        }
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 

      

      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
      }

  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_diff);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_diff);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}


// =======================
// Layer 0: Alarm Function
// =======================

void alarm();

nodemcu_simv_acv.ino

Arduino
#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif
#include <ArduinoJson.h>
#include <Wire.h>

#include<SoftwareSerial.h>
SoftwareSerial SUART(4, 5); //SRX=Dpin-D2; STX-DPin-D1


//===================================
//  Variables for storing pressure data
//===================================

float BPM = 0.00;
float IE_ratio = 0.00;
float TidVol = 0.00;
float pressure_mask = 0.00;
float pressure_diff = 0.00;
float pressure_expiration = 0.00;

//=======================================
unsigned long time_1;
bool test_2;
String last_char = "}";


// Replace with your network credentials
const char* ssid     = "1.21 Jiggawatts!";
const char* password = "itburnswhenIP";  

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "http://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "San Diego";

void setup() {
  Serial.begin(9600); //enable Serial Monitor
  SUART.begin(9600); //enable SUART Port
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
  
}

void loop() {
  String message = "";
  //String test = "";
  DynamicJsonDocument doc(1024);
  doc["type"] = "request";
  //serializeJson(doc, test);
  //Serial.println(test);
  serializeJson(doc,SUART);
  // Reading the response
  boolean messageReady = false;
  time_1 = millis();
  while(messageReady == false) { // blocking but that's ok
    if(SUART.available()) {
      message = SUART.readString();
      Serial.println(message);
      test_2 = message.endsWith(last_char);
      Serial.println(test_2);
      if (!(test_2)){
        return;
      }
      Serial.println("I am here");
      messageReady = true;
    }

  }
  send_data(message);
  delay(3000);
  }
  

//======================================


void send_data(String message) {
  DynamicJsonDocument doc(1024);
  DeserializationError error = deserializeJson(doc,message);
  if(error) {
    Serial.print(F("deserializeJson() failed: "));
    Serial.println(error.c_str());
    return;
  }
  if(WiFi.status()== WL_CONNECTED){
    HTTPClient http;
    
    // Your Domain name with URL path or IP address with path
    http.begin(serverName);
    
    // Specify content-type header
    http.addHeader("Content-Type", "application/x-www-form-urlencoded");
    String BPM = doc["BPM"];
    String IE_ratio = doc["IE_ratio"];
    String TidVol = doc["TidVol"];
    String httpRequestData = "api_key=" + apiKeyValue + "&sensor=" + sensorName
                          + "&location=" + sensorLocation + "&value1=" + BPM
                          + "&value2=" + IE_ratio + "&value3=" + TidVol + "";
    Serial.print("httpRequestData: ");
    Serial.println(httpRequestData);
  
  int httpResponseCode = http.POST(httpRequestData);
  
  if (httpResponseCode>0) {
      Serial.print("HTTP Response code: ");
      Serial.println(httpResponseCode);
    }
    else {
      Serial.print("Error code: ");
      Serial.println(httpResponseCode);
    }
    // Free resources
    http.end();
}}

uno_simv_acv-Queue.h

Arduino
/*
 * Queue.h
 * 
 * By Steven de Salas
 * 
 * Defines a templated (generic) class for a queue of things.
 * Used for Arduino projects, just #include "Queue.h" and add this file via the IDE.
 * 
 * Examples:
 * 
 * Queue<char> queue(10); // Max 10 chars in this queue
 * queue.push('H');
 * queue.push('e');
 * queue.count(); // 2
 * queue.push('l');
 * queue.push('l');
 * queue.count(); // 4
 * Serial.print(queue.pop()); // H
 * Serial.print(queue.pop()); // e
 * queue.count(); // 2
 * queue.push('o');
 * queue.count(); // 3
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // o
 * 
 * struct Point { int x; int y; }
 * Queue<Point> points(5);
 * points.push(Point{2,4});
 * points.push(Point{5,0});
 * points.count(); // 2
 * 
 */

#ifndef QUEUE_H
#define QUEUE_H

#include <Arduino.h>

template<class T>
class Queue {
  private:
    int _front, _back, _count;
    T *_data;
    int _maxitems;
  public:
    Queue(int maxitems = 256) { 
      _front = 0;
      _back = 0;
      _count = 0;
      _maxitems = maxitems;
      _data = new T[maxitems + 1];   
    }
    ~Queue() {
      delete[] _data;  
    }
    inline int count();
    inline int front();
    inline int back();
    void push(const T &item);
    T peek();
    T pop();
    void clear();
};

template<class T>
inline int Queue<T>::count() 
{
  return _count;
}

template<class T>
inline int Queue<T>::front() 
{
  return _front;
}

template<class T>
inline int Queue<T>::back() 
{
  return _back;
}

template<class T>
void Queue<T>::push(const T &item)
{
  if(_count < _maxitems) { // Drops out when full
    _data[_back++]=item;
    ++_count;
    // Check wrap around
    if (_back > _maxitems)
      _back -= (_maxitems + 1);
  }
}

template<class T>
T Queue<T>::pop() {
  if(_count <= 0) return T(); // Returns empty
  else {
    T result = _data[_front];
    _front++;
    --_count;
    // Check wrap around
    if (_front > _maxitems) 
      _front -= (_maxitems + 1);
    return result; 
  }
}

template<class T>
T Queue<T>::peek() {
  if(_count <= 0) return T(); // Returns empty
  else return _data[_front];
}

template<class T>
void Queue<T>::clear() 
{
  _front = _back;
  _count = 0;
}

#endif

uno_simv_acv/uno_simv_acv.ino

Arduino
// ========================
//          SETUP
// ========================
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <Nextion.h>
#include <SPI.h>
#include <SD.h>

//====== Serial Connection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

// setup servo
Servo servo;
int pos = 0;   

// ==== Analog Pins =====
int potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 2;
int pinMask = 4; 
int pinDiff = 3;
int ledState = LOW;


// ==== Digital Pins =====
const int buzzerPin = 5;
const int ledPin = 6;

// ==== Sensor Offset =====
float constPressureMask = 41;
float slopePressureMask = 92;
float constPressureDiff = 548;
float slopePressureDiff = 204.8;

// ===== Other vars ======
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float maskPressure;
float diffPressure;
float volFlow;
float diffPressureArr[90];
float maskPressureArr[90];
float area_1 = 0.0002835287370;
float area_2 = 0.00007853981634;
float rho = 1.225;
float totVolume;
float timeNow;
String acvLabel = "acv";
String simvLabel = "simv";

// ======= Mode changing vars =========
int state = HIGH;      
uint32_t lastPrint = millis();

// Declare your Nextion objects - Example (page id = 0, component id = 1, component name = "b0")
//====== LCD Variables ==============
int id_1 = 5;
int ch = 0;
int id_2 = 4;
int id_3 = 3;
String ad = "add ";
static char buffer[10] = {};
static char buffer_2[10] = {};
static char buffer_3[10] = {};
static char buffer_mode[10] = {};
String set_mode = "ACV";
NexText t_ie_ratio = NexText(0, 8, "t_ie_ratio");
NexText t_bpm = NexText(0, 9, "t_bpm");
NexText t_tidvol = NexText(0, 10, "t_tidvol");
NexText t_mode = NexText(0, 12, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");
NexTouch *nex_listen_list[] = {&b0, &b1, NULL};

/* NexText t_mode = NexText(0, 9, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");
NexButton b2 = NexButton(0, 4, "b2");
NexText t3 = NexText(1, 5, "t3");
NexText t4 = NexText(1, 6, "t4");
NexText t5 = NexText(1, 7, "t5");
NexText t_ie_ratio = NexText(0, 10, "t_ie_Ratio");
NexText t_bpm = NexText(0, 11, "t_bpm");
NexText t_tidvol = NexText(0, 12, "t_tidvol");
String set_mode;
NexTouch *nex_listen_list[] = {&b0,&b1,&b2,NULL}; */


void b0PopCallback(void *ptr) {
  set_mode = "ACV";
  t_mode.setText(set_mode.c_str());
}

void b1PopCallback(void *ptr) {
  set_mode = "SIMV";
  t_mode.setText(set_mode.c_str());
}

//======= SD Card File ===========
File myFile;

void setup()
{
  servo.attach(9);  
  Serial.begin(9600);
  SUART.begin(9600); 
  pinMode(ledPin,OUTPUT);
  pinMode(buzzerPin,OUTPUT);
  pinMode(10, OUTPUT);
  nexInit();
  b0.attachPop(b0PopCallback, &b0);
  b1.attachPop(b1PopCallback, &b1);

  if (!SD.begin(4)) {
   Serial.println("initialization failed!");
   return;
  }
  Serial.println("SD Card Initialization done.");
  /* myFile = SD.open("example.txt", FILE_WRITE);
  myFile.close(); */
}

//////////////////
////// Loop //////
//////////////////
// ===========================================
//              RUN RESPIRATOR
// =========================================== 
void loop()
{
  //acv_mode();
  /* fetchPotValues();
  Serial.println(IE_ratio);
  Serial.println(BPM);
  Serial.println(TidVol);
  delay(1000); */

  // Run ventilator
  acv_mode();
  /*   send_to_screen_values();
    if (set_mode == "ACV") {
    //myFile = SD.open("example.txt", FILE_WRITE);
    acv_mode();
    //myFile.close();
  }
  else if (set_mode == "SIMV") {
    //myFile = SD.open("example.txt", FILE_WRITE);
    simv_mode();
    //myFile.close();
  } */
  //while(set_mode == simvLabel) simv_mode();
//  get b0.val;
  //while(set_mode == acvLabel) acv_mode();

//maskPressure = pressureFromAnalog(pinMask,1000);
//diffPressure = pressureFromAnalog(pinDiff,1000); 
//fetchPotValues();

//nexLoop(nex_listen_list);
}
// ***************** END RUN RESPIRATOR  *******************

// ============ LAYER 1 FUNCTIONS ===============
// =================================================
//                 ACV MODE Function
// =================================================
void acv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;
  
  while(true)
  {   
      // Fetch all potentiometer values
      fetchPotValues();
      
      // Initiate first run
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }
      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation || maskPressure < -1)
      {
        myFile = SD.open("example.txt", FILE_WRITE);
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        myFile.close(); 
      }
      sanityCheckBuzzer();
      
      // ============ Update pressure values =========
      maskPressure = pressureFromAnalog(pinMask,1000);
      diffPressure = pressureFromAnalog(pinDiff,1000); 
      send_to_screen_values();
      send_to_screen_graph();
      nexLoop(nex_listen_list); 
      
      //Serial.println(maskPressure);
      //print_to_screen();
      //nexLoop(nex_listen_list);
      //computePrintVolFlow();
  }
  return;
}



// ===========================================
//            SIMV MODE Function
// ===========================================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(set_mode = simvLabel)
  {
      // Fetch all potentiometer values
      fetchPotValues();

      // ==== Initiate the cycle =====
      if(firstRun)
      {
        maskPressure = average_maskPressure();
        cycleEndTime = simv_logic(maskPressure, TidVol, IE_ratio);
        firstRun = false;
      }
      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation || average_maskPressure() < -1)
      {
        maskPressure = average_maskPressure();
        cycleEndTime = simv_logic(maskPressure, TidVol, IE_ratio);
      }
      send_to_screen_values();
      
      //send_to_screen_graph();
  }
  return;
}

// ============ LAYER 2 FUNCTIONS ================

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float maskPressure, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    maskPressure = int(floor(maskPressure));
    switch(int(maskPressure)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// Average Pressure Function
// =======================

float average_maskPressure()
{
    maskPressure = 0;
    for(int i=0;i<5;i++)
    {
        maskPressure = maskPressure + pressureFromAnalog(pinMask, 1);
        delay(3);
    }
    return (maskPressure/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int count = 0;
  totVolume = 0;
  timeNow = millis();
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    
    servo.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    maskPressure = pressureFromAnalog(pinMask, count);
    diffPressure = pressureFromAnalog(pinDiff, count);  
    computePrintVolFlow();  
    //String data = set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";";
    Serial.println(set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";");
    //myFile.println(data);
    send_to_screen_graph();
    //send_to_screen_values();
    //nexLoop(nex_listen_list); 
    count++;
  }
}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  int count = 0;
  totVolume = 0;
  timeNow = millis();
  for(int pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                               
    servo.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    maskPressure = pressureFromAnalog(pinMask, count);    
    diffPressure = pressureFromAnalog(pinDiff, count);   
    computePrintVolFlow();
    //String data = set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";";
    Serial.println(set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";");
    //myFile.println(data);
    send_to_screen_graph();
    //send_to_screen_values();
    //nexLoop(nex_listen_list); 
    count++;
  }  
  return millis();
}

// ======================================================
// Fetch Potentiometer values and adjust separation time
// ======================================================
void fetchPotValues()
{
  // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = 1000*(60/BPM - (1+IE_ratio));  // convert to milliseconds
      // Correct separation time if needed
      if (separation < 0)
      { 
        IE_ratio = 60/BPM - 1;
        separation = (60/BPM - (1+IE_ratio))*1000;
      }
}


// ================= LAYER 3 FUNCTIONS =============
// =============================
// Pressure from Analog Function
// =============================
float pressureFromAnalog(int pin, int count)
{ float pressure;
  pressure = analogRead(pin);
  // Differential pressure sensor - output cmH2O
  if (pin == pinDiff)
  {
    pressure = (pressure - constPressureDiff)*1000/slopePressureDiff;  
    if (count != 1000) {diffPressureArr[count] = pressure;}
  }
  // Guage pressure sensor - output Pascal
  if (pin == pinMask)
  {
    pressure = pressure = (pressure - constPressureMask)*10.1972/slopePressureMask;;
    if (count != 1000) {maskPressureArr[count] = pressure;}
  }

  return pressure;
}


// =============================
// Alarm Sanity Check
// =============================

void sanityCheckBuzzer()
{
  float SDPressure;
  SDPressure = calcSD(maskPressureArr);
  //Serial.println(SDPressure);
  //Serial.println(SDPressure);
  if(SDPressure < 0.01) buzzAlarm(true);
  if(SDPressure >= 0.01) buzzAlarm(false);
}

// ================= LAYER 4 FUNCTIONS =============

// =============================
// Calculate standard deviation
// =============================
float calcSD(float data[])
{
  float avg = 0.0, SD = 0.0;
  int length = sizeof(data);

  for (int i = 0; i < length; i++)
  {
    avg += data[i];
  }
  avg = avg/length;

  for (int i = 0; i < length; i++)
  {SD += pow(data[i] - avg, 2);}
  return sqrt(SD/length);
}

// ================================================================
// Buzz Alarm if there is a problem; stop alarm if problem resolved
// ================================================================
void buzzAlarm(bool turnOn)
{
  if (turnOn == true)
  {
    ledState = HIGH;
    tone(buzzerPin,500);
  }

  if (turnOn == false)
  {
    ledState = LOW;
    noTone(buzzerPin);
  }
  
}

// =======================
// Copmute Vol Flow
// =======================
void computePrintVolFlow()
{ 
  
  volFlow =  1000*sqrt((abs(diffPressure)*2*rho)/((1/(pow(area_2,2)))-(1/(pow(area_1,2)))))/rho; 
  if (millis() - lastPrint >= uint32_t(100))
    { 
      //Serial.println(flow);
      lastPrint = millis();
    }
  if(volFlow > 0.4)totVolume = totVolume + volFlow*(millis() - timeNow);
  timeNow = millis();
  //Serial.println(totVolume);
}
// =======================
// Nextion Screen Functions
// =======================
/* void b0PopCallback(void *ptr) {
  set_mode = "MODE : ACV"; 
  t_mode.setText(set_mode.c_str());
}
void b1PopCallback(void *ptr) {
  set_mode = "MODE : SIMV"; 
  t_mode.setText(set_mode.c_str());  
}
void b2PopCallback(void *ptr) {
  set_mode = "MODE : None"; 
  t_mode.setText(set_mode.c_str());
} */

// =====================
// Print to Screen
// =====================
/* void print_to_screen()
{ 
  t_mode.setText(set_mode.c_str());
  static char ps_diff[6];
  dtostrf(diffPressure, 6, 2, ps_diff);
  static char ps_mask[6];
  dtostrf(maskPressure, 6, 2, ps_mask);
  t3.setText(ps_diff);
  t5.setText(ps_mask);
  static char ie_ratio[6];
  dtostrf(IE_ratio, 6, 2, ie_ratio);
  t_ie_ratio.setText(ie_ratio);
  static char bpm[6];
  dtostrf(BPM, 6, 2, bpm);
  t_bpm.setText(bpm);
  static char tidvol[6];
  dtostrf(TidVol, 6, 2, tidvol);
  t_tidvol.setText(tidvol);
  
  
} */


// =====================
// Transmit to DB
// =====================
void transmit(){
      Serial.println("Inside the transmit function");
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      const int capacity_data = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity_data> jb_data;
      JsonObject& doc = jb_data.createObject();
      doc["type"].set("response");
      doc["BPM"].set(BPM);
      doc["IE_ratio"].set(IE_ratio);
      doc["maskPressure"].set(maskPressure);
      doc["flowRate"].set(volFlow);
      doc["TidVol"].set(TidVol);
      doc["totVolume"].set(totVolume);
      doc.printTo(SUART);
      doc.printTo(Serial);
      }
      }


// =====================
// Print to Screen
// =====================

void send_to_screen_graph() {
  String to_send_p_mask = ad + id_1 + "," + ch + "," + int(maskPressure);
  print_screen(to_send_p_mask);
  String to_send_volFlow = ad + id_2 + "," + ch + "," + int(volFlow);
  print_screen(to_send_volFlow);
  String to_send_totVolume = ad + id_3 + "," + ch + "," + int(totVolume);
  print_screen(to_send_totVolume);
}

void send_to_screen_values() {
  dtostrf(BPM, 6, 2, buffer);
  t_bpm.setText(buffer);
  dtostrf(IE_ratio, 6, 2, buffer_2);
  t_ie_ratio.setText(buffer_2);
  dtostrf(TidVol, 6, 2, buffer_3);
  t_tidvol.setText(buffer_3);
  t_mode.setText(set_mode.c_str());
}

void print_screen(String to_send) {
  Serial.print(to_send);
  Serial.print("\xFF\xFF\xFF");
}

uno_simv_acv/Queue.h

Arduino
/*
 * Queue.h
 * 
 * By Steven de Salas
 * 
 * Defines a templated (generic) class for a queue of things.
 * Used for Arduino projects, just #include "Queue.h" and add this file via the IDE.
 * 
 * Examples:
 * 
 * Queue<char> queue(10); // Max 10 chars in this queue
 * queue.push('H');
 * queue.push('e');
 * queue.count(); // 2
 * queue.push('l');
 * queue.push('l');
 * queue.count(); // 4
 * Serial.print(queue.pop()); // H
 * Serial.print(queue.pop()); // e
 * queue.count(); // 2
 * queue.push('o');
 * queue.count(); // 3
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // o
 * 
 * struct Point { int x; int y; }
 * Queue<Point> points(5);
 * points.push(Point{2,4});
 * points.push(Point{5,0});
 * points.count(); // 2
 * 
 */

#ifndef QUEUE_H
#define QUEUE_H

#include <Arduino.h>

template<class T>
class Queue {
  private:
    int _front, _back, _count;
    T *_data;
    int _maxitems;
  public:
    Queue(int maxitems = 256) { 
      _front = 0;
      _back = 0;
      _count = 0;
      _maxitems = maxitems;
      _data = new T[maxitems + 1];   
    }
    ~Queue() {
      delete[] _data;  
    }
    inline int count();
    inline int front();
    inline int back();
    void push(const T &item);
    T peek();
    T pop();
    void clear();
};

template<class T>
inline int Queue<T>::count() 
{
  return _count;
}

template<class T>
inline int Queue<T>::front() 
{
  return _front;
}

template<class T>
inline int Queue<T>::back() 
{
  return _back;
}

template<class T>
void Queue<T>::push(const T &item)
{
  if(_count < _maxitems) { // Drops out when full
    _data[_back++]=item;
    ++_count;
    // Check wrap around
    if (_back > _maxitems)
      _back -= (_maxitems + 1);
  }
}

template<class T>
T Queue<T>::pop() {
  if(_count <= 0) return T(); // Returns empty
  else {
    T result = _data[_front];
    _front++;
    --_count;
    // Check wrap around
    if (_front > _maxitems) 
      _front -= (_maxitems + 1);
    return result; 
  }
}

template<class T>
T Queue<T>::peek() {
  if(_count <= 0) return T(); // Returns empty
  else return _data[_front];
}

template<class T>
void Queue<T>::clear() 
{
  _front = _back;
  _count = 0;
}

#endif

arduino.json

Arduino
{
    "board": "esp8266:esp8266:d1",
    "sketch": "acv_simv/acv_simv.ino",
    "port": "COM4",
    "configuration": "xtal=80,vt=flash,exception=legacy,ssl=all,eesz=4M2M,ip=lm2f,dbg=Disabled,lvl=None____,wipe=none,baud=921600"
}

uno_simv_acv/uno_simv_acv.ino

Arduino
// ========================
//          SETUP
// ========================
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <Nextion.h>
#include <SPI.h>
#include <SD.h>

//====== Serial Connection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

// setup servo
Servo servo;
int pos = 0;   

// ==== Analog Pins =====
int potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 2;
int pinMask = 4; 
int pinDiff = 3;
int ledState = LOW;


// ==== Digital Pins =====
const int buzzerPin = 5;
const int ledPin = 6;

// ==== Sensor Offset =====
float constPressureMask = 41;
float slopePressureMask = 92;
float constPressureDiff = 548;
float slopePressureDiff = 204.8;

// ===== Other vars ======
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float maskPressure;
float diffPressure;
float volFlow;
float diffPressureArr[90];
float maskPressureArr[90];
float area_1 = 0.0002835287370;
float area_2 = 0.00007853981634;
float rho = 1.225;
float totVolume;
float timeNow;
String acvLabel = "acv";
String simvLabel = "simv";

// ======= Mode changing vars =========
int state = HIGH;      
uint32_t lastPrint = millis();

// Declare your Nextion objects - Example (page id = 0, component id = 1, component name = "b0")
//====== LCD Variables ==============
int id_1 = 5;
int ch = 0;
int id_2 = 4;
int id_3 = 3;
String ad = "add ";
static char buffer[10] = {};
static char buffer_2[10] = {};
static char buffer_3[10] = {};
static char buffer_mode[10] = {};
String set_mode = "ACV";
NexText t_ie_ratio = NexText(0, 8, "t_ie_ratio");
NexText t_bpm = NexText(0, 9, "t_bpm");
NexText t_tidvol = NexText(0, 10, "t_tidvol");
NexText t_mode = NexText(0, 12, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");
NexTouch *nex_listen_list[] = {&b0, &b1, NULL};

/* NexText t_mode = NexText(0, 9, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");
NexButton b2 = NexButton(0, 4, "b2");
NexText t3 = NexText(1, 5, "t3");
NexText t4 = NexText(1, 6, "t4");
NexText t5 = NexText(1, 7, "t5");
NexText t_ie_ratio = NexText(0, 10, "t_ie_Ratio");
NexText t_bpm = NexText(0, 11, "t_bpm");
NexText t_tidvol = NexText(0, 12, "t_tidvol");
String set_mode;
NexTouch *nex_listen_list[] = {&b0,&b1,&b2,NULL}; */


void b0PopCallback(void *ptr) {
  set_mode = "ACV";
  t_mode.setText(set_mode.c_str());
}

void b1PopCallback(void *ptr) {
  set_mode = "SIMV";
  t_mode.setText(set_mode.c_str());
}

//======= SD Card File ===========
File myFile;

void setup()
{
  servo.attach(9);  
  Serial.begin(9600);
  SUART.begin(9600); 
  pinMode(ledPin,OUTPUT);
  pinMode(buzzerPin,OUTPUT);
  pinMode(10, OUTPUT);
  nexInit();
  b0.attachPop(b0PopCallback, &b0);
  b1.attachPop(b1PopCallback, &b1);

  if (!SD.begin(4)) {
   Serial.println("initialization failed!");
   return;
  }
  Serial.println("SD Card Initialization done.");
  /* myFile = SD.open("example.txt", FILE_WRITE);
  myFile.close(); */
}

//////////////////
////// Loop //////
//////////////////
// ===========================================
//              RUN RESPIRATOR
// =========================================== 
void loop()
{
  //acv_mode();
  /* fetchPotValues();
  Serial.println(IE_ratio);
  Serial.println(BPM);
  Serial.println(TidVol);
  delay(1000); */

  // Run ventilator
  acv_mode();
  /*   send_to_screen_values();
    if (set_mode == "ACV") {
    //myFile = SD.open("example.txt", FILE_WRITE);
    acv_mode();
    //myFile.close();
  }
  else if (set_mode == "SIMV") {
    //myFile = SD.open("example.txt", FILE_WRITE);
    simv_mode();
    //myFile.close();
  } */
  //while(set_mode == simvLabel) simv_mode();
//  get b0.val;
  //while(set_mode == acvLabel) acv_mode();

//maskPressure = pressureFromAnalog(pinMask,1000);
//diffPressure = pressureFromAnalog(pinDiff,1000); 
//fetchPotValues();

//nexLoop(nex_listen_list);
}
// ***************** END RUN RESPIRATOR  *******************

// ============ LAYER 1 FUNCTIONS ===============
// =================================================
//                 ACV MODE Function
// =================================================
void acv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;
  
  while(true)
  {   
      // Fetch all potentiometer values
      fetchPotValues();
      
      // Initiate first run
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }
      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation || maskPressure < -1)
      {
        myFile = SD.open("example.txt", FILE_WRITE);
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        myFile.close(); 
      }
      sanityCheckBuzzer();
      
      // ============ Update pressure values =========
      maskPressure = pressureFromAnalog(pinMask,1000);
      diffPressure = pressureFromAnalog(pinDiff,1000); 
      send_to_screen_values();
      send_to_screen_graph();
      nexLoop(nex_listen_list); 
      
      //Serial.println(maskPressure);
      //print_to_screen();
      //nexLoop(nex_listen_list);
      //computePrintVolFlow();
  }
  return;
}



// ===========================================
//            SIMV MODE Function
// ===========================================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(set_mode = simvLabel)
  {
      // Fetch all potentiometer values
      fetchPotValues();

      // ==== Initiate the cycle =====
      if(firstRun)
      {
        maskPressure = average_maskPressure();
        cycleEndTime = simv_logic(maskPressure, TidVol, IE_ratio);
        firstRun = false;
      }
      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation || average_maskPressure() < -1)
      {
        maskPressure = average_maskPressure();
        cycleEndTime = simv_logic(maskPressure, TidVol, IE_ratio);
      }
      send_to_screen_values();
      
      //send_to_screen_graph();
  }
  return;
}

// ============ LAYER 2 FUNCTIONS ================

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float maskPressure, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    maskPressure = int(floor(maskPressure));
    switch(int(maskPressure)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// Average Pressure Function
// =======================

float average_maskPressure()
{
    maskPressure = 0;
    for(int i=0;i<5;i++)
    {
        maskPressure = maskPressure + pressureFromAnalog(pinMask, 1);
        delay(3);
    }
    return (maskPressure/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int count = 0;
  totVolume = 0;
  timeNow = millis();
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    
    servo.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    maskPressure = pressureFromAnalog(pinMask, count);
    diffPressure = pressureFromAnalog(pinDiff, count);  
    computePrintVolFlow();  
    //String data = set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";";
    Serial.println(set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";");
    //myFile.println(data);
    send_to_screen_graph();
    //send_to_screen_values();
    //nexLoop(nex_listen_list); 
    count++;
  }
}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  int count = 0;
  totVolume = 0;
  timeNow = millis();
  for(int pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                               
    servo.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    maskPressure = pressureFromAnalog(pinMask, count);    
    diffPressure = pressureFromAnalog(pinDiff, count);   
    computePrintVolFlow();
    //String data = set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";";
    Serial.println(set_mode + "," + String(maskPressure) + "," + String(volFlow) + "," + String(totVolume) + ";");
    //myFile.println(data);
    send_to_screen_graph();
    //send_to_screen_values();
    //nexLoop(nex_listen_list); 
    count++;
  }  
  return millis();
}

// ======================================================
// Fetch Potentiometer values and adjust separation time
// ======================================================
void fetchPotValues()
{
  // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = 1000*(60/BPM - (1+IE_ratio));  // convert to milliseconds
      // Correct separation time if needed
      if (separation < 0)
      { 
        IE_ratio = 60/BPM - 1;
        separation = (60/BPM - (1+IE_ratio))*1000;
      }
}


// ================= LAYER 3 FUNCTIONS =============
// =============================
// Pressure from Analog Function
// =============================
float pressureFromAnalog(int pin, int count)
{ float pressure;
  pressure = analogRead(pin);
  // Differential pressure sensor - output cmH2O
  if (pin == pinDiff)
  {
    pressure = (pressure - constPressureDiff)*1000/slopePressureDiff;  
    if (count != 1000) {diffPressureArr[count] = pressure;}
  }
  // Guage pressure sensor - output Pascal
  if (pin == pinMask)
  {
    pressure = pressure = (pressure - constPressureMask)*10.1972/slopePressureMask;;
    if (count != 1000) {maskPressureArr[count] = pressure;}
  }

  return pressure;
}


// =============================
// Alarm Sanity Check
// =============================

void sanityCheckBuzzer()
{
  float SDPressure;
  SDPressure = calcSD(maskPressureArr);
  //Serial.println(SDPressure);
  //Serial.println(SDPressure);
  if(SDPressure < 0.01) buzzAlarm(true);
  if(SDPressure >= 0.01) buzzAlarm(false);
}

// ================= LAYER 4 FUNCTIONS =============

// =============================
// Calculate standard deviation
// =============================
float calcSD(float data[])
{
  float avg = 0.0, SD = 0.0;
  int length = sizeof(data);

  for (int i = 0; i < length; i++)
  {
    avg += data[i];
  }
  avg = avg/length;

  for (int i = 0; i < length; i++)
  {SD += pow(data[i] - avg, 2);}
  return sqrt(SD/length);
}

// ================================================================
// Buzz Alarm if there is a problem; stop alarm if problem resolved
// ================================================================
void buzzAlarm(bool turnOn)
{
  if (turnOn == true)
  {
    ledState = HIGH;
    tone(buzzerPin,500);
  }

  if (turnOn == false)
  {
    ledState = LOW;
    noTone(buzzerPin);
  }
  
}

// =======================
// Copmute Vol Flow
// =======================
void computePrintVolFlow()
{ 
  
  volFlow =  1000*sqrt((abs(diffPressure)*2*rho)/((1/(pow(area_2,2)))-(1/(pow(area_1,2)))))/rho; 
  if (millis() - lastPrint >= uint32_t(100))
    { 
      //Serial.println(flow);
      lastPrint = millis();
    }
  if(volFlow > 0.4)totVolume = totVolume + volFlow*(millis() - timeNow);
  timeNow = millis();
  //Serial.println(totVolume);
}
// =======================
// Nextion Screen Functions
// =======================
/* void b0PopCallback(void *ptr) {
  set_mode = "MODE : ACV"; 
  t_mode.setText(set_mode.c_str());
}
void b1PopCallback(void *ptr) {
  set_mode = "MODE : SIMV"; 
  t_mode.setText(set_mode.c_str());  
}
void b2PopCallback(void *ptr) {
  set_mode = "MODE : None"; 
  t_mode.setText(set_mode.c_str());
} */

// =====================
// Print to Screen
// =====================
/* void print_to_screen()
{ 
  t_mode.setText(set_mode.c_str());
  static char ps_diff[6];
  dtostrf(diffPressure, 6, 2, ps_diff);
  static char ps_mask[6];
  dtostrf(maskPressure, 6, 2, ps_mask);
  t3.setText(ps_diff);
  t5.setText(ps_mask);
  static char ie_ratio[6];
  dtostrf(IE_ratio, 6, 2, ie_ratio);
  t_ie_ratio.setText(ie_ratio);
  static char bpm[6];
  dtostrf(BPM, 6, 2, bpm);
  t_bpm.setText(bpm);
  static char tidvol[6];
  dtostrf(TidVol, 6, 2, tidvol);
  t_tidvol.setText(tidvol);
  
  
} */


// =====================
// Transmit to DB
// =====================
void transmit(){
      Serial.println("Inside the transmit function");
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      const int capacity_data = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity_data> jb_data;
      JsonObject& doc = jb_data.createObject();
      doc["type"].set("response");
      doc["BPM"].set(BPM);
      doc["IE_ratio"].set(IE_ratio);
      doc["maskPressure"].set(maskPressure);
      doc["flowRate"].set(volFlow);
      doc["TidVol"].set(TidVol);
      doc["totVolume"].set(totVolume);
      doc.printTo(SUART);
      doc.printTo(Serial);
      }
      }


// =====================
// Print to Screen
// =====================

void send_to_screen_graph() {
  String to_send_p_mask = ad + id_1 + "," + ch + "," + int(maskPressure);
  print_screen(to_send_p_mask);
  String to_send_volFlow = ad + id_2 + "," + ch + "," + int(volFlow);
  print_screen(to_send_volFlow);
  String to_send_totVolume = ad + id_3 + "," + ch + "," + int(totVolume);
  print_screen(to_send_totVolume);
}

void send_to_screen_values() {
  dtostrf(BPM, 6, 2, buffer);
  t_bpm.setText(buffer);
  dtostrf(IE_ratio, 6, 2, buffer_2);
  t_ie_ratio.setText(buffer_2);
  dtostrf(TidVol, 6, 2, buffer_3);
  t_tidvol.setText(buffer_3);
  t_mode.setText(set_mode.c_str());
}

void print_screen(String to_send) {
  Serial.print(to_send);
  Serial.print("\xFF\xFF\xFF");
}

Pressure_Mode.csv

Arduino
,Time,Pressure,Flow,Volume
0,0.0,0.4442870291872473,0.05527777369075705,0.7231685956780632
1,0.10000124970319549,0.290242623143001,1.238381943948462,0.14185068146210808
2,0.20000249940639098,-0.9661143414909829,-0.4578747504133094,-0.30787006396772376
3,0.3000037491095865,0.7670286457826542,0.11123732520524092,0.8026950827797061
4,0.40000499881278195,-0.3912524782101275,-0.7823200543589414,0.5108665517793185
5,0.5000062485159774,-0.5015751444292047,-0.08954781101522022,0.8675839263446976
6,0.600007498219173,0.20543354052935156,0.17445560157184573,0.28856850945243395
7,0.7000087479223684,0.8020437472443975,-0.1969349225359255,0.42073382497788975
8,0.8000099976255639,0.07804981688748058,0.06735389541562085,-0.7336418685965963
9,0.9000112473287594,0.4483468570667566,1.292941268530478,-0.5190181284041365
10,1.0000124970319548,0.7308336391623975,-0.22326437595845414,-1.324162607635834
11,1.1000137467351503,0.16967842870992667,-0.5287989030359169,0.26944213677359485
12,1.200014996438346,-0.13314909710868725,-0.4282891810405944,-0.10663551160100271
13,1.3000162461415414,0.6577929087437274,0.10735377503582623,0.6809128651602749
14,1.400017495844737,0.41350576770649766,0.010755520713676348,0.09991354144968986
15,1.5000187455479324,0.32962590282130055,0.3923639087639866,-0.2819797668841528
16,1.6000199952511278,-0.5248991303816627,-0.20479427402799077,-0.4298958946375976
17,1.7000212449543233,0.5099885725094043,-0.759639724328958,-0.3139085844349437
18,1.8000224946575187,-0.06332219171885607,0.7519121187662698,0.25167930895860413
19,1.9000237443607142,0.2612780017931324,0.0282643509738926,0.5471253608754644
20,2.0000249940639097,39.676356317296204,15.041893523073455,2.3509608414058105
21,2.1000262437671053,39.4772919920304,13.929725626672486,3.0280256685733806
22,2.2000274934703006,40.173790643284136,14.414888949979863,2.359494570127325
23,2.3000287431734963,39.651348336717525,14.417581372698036,3.0527550322836943
24,2.400029992876692,40.39447175736241,14.477622213245363,2.2971242572944646
25,2.500031242579887,39.934625269995664,14.420575610398407,2.6690191740072806
26,2.600032492283083,40.17624127926895,13.622508137453401,2.737473286084107
27,2.700033741986278,40.94641130080306,14.301741622729715,3.09044663275055
28,2.800034991689474,39.20922747176185,13.652751184515212,2.6102253576395116
29,2.900036241392669,39.99624638843631,14.0318218118711,3.5519670197747772
30,3.0000374910958647,40.45327163165292,13.31106954255396,2.636610284523015
31,3.10003874079906,40.24327860617379,13.38949632938472,4.446981450669239
32,3.2000399905022556,39.8647365581469,13.709599184398044,4.582517788137938
33,3.3000412402054513,39.70182186932854,12.97674803487895,3.5513640941071403
34,3.4000424899086465,40.378729489751116,12.810849179694664,2.967702718307856
35,3.5000437396118422,39.76241323842081,12.669817556381947,3.5513168464552
36,3.6000449893150375,39.827165071565815,11.346674037877134,3.4911700031252852
37,3.700046239018233,40.34081498163381,12.203924510034309,4.002998459230303
38,3.8000474887214284,39.34868769664976,12.778011745935773,4.174560381115509
39,3.900048738424624,40.79879202767033,11.88268298710951,3.853282350437871
40,4.000049988127819,39.82045592299935,10.820642582105169,5.005056009336865
41,4.100051237831015,40.24130031627691,12.442700711292837,3.6580697524909813
42,4.200052487534211,39.44095710041147,12.136708896166567,4.039299324656676
43,4.300053737237406,39.56882489919915,11.923697457177049,4.940488186169312
44,4.400054986940601,40.3752390048432,11.18248008871425,3.827410312646376
45,4.500056236643797,39.800764868747635,12.041125965139857,5.145324476394133
46,4.6000574863469925,39.55509236805168,10.916774886663402,4.178118045889503
47,4.700058736050188,40.69177571700485,11.449146086024362,4.393042322604586
48,4.800059985753384,39.60071791136262,11.205632367872298,5.027017901968952
49,4.900061235456579,40.74179226768329,9.553832897869768,4.182387672214753
50,5.000062485159774,39.46481243244443,9.973190314812205,4.422938434553982
51,5.10006373486297,40.645664701855054,10.690051884447964,5.165042013237117
52,5.200064984566166,39.75325610528615,10.381569094607691,5.502174765865349
53,5.3000662342693605,40.30047235894059,10.06175901719023,5.307197223035885
54,5.400067483972556,39.89557300338437,9.631460936007096,5.060935474394805
55,5.500068733675752,40.40143819035686,9.163804355962192,5.981883605669922
56,5.600069983378948,39.14840279738084,9.848880792242468,5.903996566414725
57,5.700071233082143,39.65393719758146,9.44824463173113,6.404275792572526
58,5.800072482785338,40.39790439386496,9.85076895567836,6.309085576817652
59,5.900073732488534,39.12591453513457,8.45136649431385,5.7071891969979935
60,6.000074982191729,40.24570611364736,9.466133499326032,5.623974651639048
61,6.100076231894925,39.681368538887845,8.933005557683456,5.309628343492222
62,6.20007748159812,39.39053668868258,8.418523747080911,6.5478816257619155
63,6.300078731301316,39.93810880394414,8.808400398037021,7.281867343876803
64,6.400079981004511,39.372480347387175,8.422659333178997,6.305619924269296
65,6.500081230707707,39.75988663692049,8.643138809567938,6.437816776798834
66,6.600082480410903,39.715516197149945,8.030924145105343,7.291585442071973
67,6.700083730114097,40.16381341546465,7.4718868296319405,6.7302261609054845
68,6.800084979817293,39.4178211517028,7.676789534594028,7.244328252721535
69,6.900086229520489,40.03133907658614,7.244753555387089,7.234709556914357
70,7.0000874792236845,40.73240339242001,7.3446244653377,7.042733392648405
71,7.100088728926879,39.810697693758705,7.262125565923559,7.7226589434641575
72,7.200089978630075,39.80402929281886,8.826140031932592,7.733721033338147
73,7.300091228333271,39.271944190401285,6.8990639977901385,8.253198861986629
74,7.400092478036466,39.396778797236166,7.344107790828642,8.750235382091818
75,7.500093727739662,39.9112470722853,7.003135415200865,8.730757614121815
76,7.600094977442857,39.14676323305678,5.993259960228134,7.933432342085189
77,7.7000962271460525,40.453562751482515,6.3807488532512,9.016270120262558
78,7.800097476849248,39.4333971392411,5.953325450142274,9.707187382382212
79,7.900098726552444,39.36294643302033,6.0513253708834975,9.316020022224723
80,8.000099976255639,39.58356475504564,5.517762822176594,7.992031491811579
81,8.100101225958834,39.60186277200088,6.709695267134425,9.590454886245745
82,8.20010247566203,39.32257483413808,5.2475635902129625,9.726703687308042
83,8.300103725365226,40.04459253532641,5.526694991176434,10.458700163207848
84,8.400104975068421,40.79697761320993,5.173577531699288,8.360984082014834
85,8.500106224771617,40.59850375838081,5.254956302678248,10.204565566669245
86,8.600107474474813,40.31829312577862,5.2015951187842155,10.925310684173722
87,8.700108724178007,39.78638435268903,4.8885384112620365,10.706554656833312
88,8.800109973881202,40.99017833476169,4.368755798300334,9.465308904674568
89,8.900111223584398,39.60413665225514,4.038282188711273,10.008265215526293
90,9.000112473287594,40.073986114489585,4.0068110177980545,10.896570563486101
91,9.10011372299079,40.67736754663993,4.705154935883748,12.048500519382172
92,9.200114972693985,40.07712961534579,4.0689152415845795,12.404855770893922
93,9.30011622239718,39.90627039718186,3.079479351019262,11.411325974769555
94,9.400117472100376,40.6145783124634,3.891646826532846,12.292666668645236
95,9.500118721803572,39.974544754503356,3.3973408256438695,11.640276268701795
96,9.600119971506768,40.37230738370352,4.731114287483841,12.20086320122582
97,9.700121221209962,39.6254779289669,4.035367470816082,13.10287502400191
98,9.800122470913157,40.45275487876092,2.3163248645485095,12.819493908421846
99,9.900123720616353,40.39764941645855,2.6454973259146093,13.49568274540658
100,10.000124970319549,40.47994938751996,2.1585201447712747,12.817329139714566
101,10.100126220022744,40.067979447625106,2.543384530639922,13.729745682508273
102,10.20012746972594,39.658600961660056,2.5937479357713107,13.966123760054813
103,10.300128719429136,39.185507020733226,1.8263953718892596,13.819210210685592
104,10.400129969132331,39.2186680232346,1.4621842353253,14.614597198290694
105,10.500131218835527,39.90266166260904,2.693333582118302,15.380737612327653
106,10.600132468538721,38.938198687048185,1.580680962026128,15.680362503448334
107,10.700133718241917,39.70584783318751,2.4023626075629814,15.499068150893693
108,10.800134967945112,40.42648125167482,0.933554114669065,16.028133621085146
109,10.900136217648308,40.234997324267795,1.3089122093803647,15.379684571252248
110,11.000137467351504,39.64643237531784,1.104467992916667,16.24830484705585
111,11.1001387170547,40.40433329538608,0.7140269594553049,17.497171392579
112,11.200139966757895,39.9841791015459,1.3488459383225955,17.263250423507976
113,11.30014121646109,40.41709716271218,0.901365448250614,17.874795818955068
114,11.400142466164287,39.7870803368051,0.8021359347002058,17.775098705495115
115,11.50014371586748,39.471595902318974,0.981512582711431,17.58443401920997
116,11.600144965570676,40.7029477552417,0.24264592897664164,19.039605894913727
117,11.700146215273872,40.03165803478826,0.3451339591321547,20.026841162259043
118,11.800147464977067,40.33441073545463,0.4065578189657301,19.692224273408698
119,11.900148714680263,39.52898333386905,0.009778212501932348,20.165994448646217
120,12.000149964383459,40.04244154964088,0.2126868477861593,19.66119982881949
121,12.100151214086655,39.82387343675968,-0.06402027191814542,19.963301046582192
122,12.20015246378985,39.6847319741217,-0.3284546997312651,19.48991320898399
123,12.300153713493046,39.767772921476265,-0.3188399285098851,19.494247442438596
124,12.40015496319624,39.25515531710004,-0.3059579181632069,18.93826650481899
125,12.500156212899435,40.124157921293126,0.11061468083531559,20.780210189569235
126,12.600157462602631,40.42735374292092,0.13418833617128476,19.856981306259488
127,12.700158712305827,40.09047982889096,0.41514577093598903,19.87854262019926
128,12.800159962009023,39.73920197921174,0.5802337929374928,20.332021078000096
129,12.900161211712218,39.90963645287713,-0.7607370111563254,19.454727955402884
130,13.000162461415414,39.986608861651504,0.23888783089931928,20.490471357948646
131,13.10016371111861,40.04776939308605,0.6068568989684164,20.76113534335185
132,13.200164960821805,39.826996683178045,-0.05364860394043094,19.94876700472235
133,13.300166210525,40.003302330103025,0.26259776282477143,19.8252279299547
134,13.400167460228195,39.845740480125784,-1.1440415167516296,19.902110697989258
135,13.50016870993139,40.11946105958178,0.1698106794744897,19.214274349032802
136,13.600169959634586,40.089977141607676,0.5809260379998814,20.031830447913936
137,13.700171209337782,39.613975846337375,0.18244778839212553,20.22235801086799
138,13.800172459040978,40.45066120789557,0.49506267966528045,19.620871002578117
139,13.900173708744173,39.72053768382128,-0.07813230491133699,19.442642198075646
140,14.000174958447369,40.31495197823957,0.04137313203674581,20.801361399994473
141,14.100176208150565,39.8392778405535,-1.041255047846596,18.965492576952155
142,14.200177457853759,40.18594807133878,-0.40915228530782843,19.208000465848315
143,14.300178707556954,40.33546169584521,-0.9477813802292147,19.809736042877773
144,14.40017995726015,40.35114125090207,-0.5740831375296427,20.22534565943953
145,14.500181206963346,39.57417496204906,0.001939610233716598,19.62351306651151
146,14.600182456666541,40.74540813777349,0.21483613106259317,20.54173472409379
147,14.700183706369737,39.640589698335994,-0.08353197045374126,19.547986618679293
148,14.800184956072933,39.758489687891,0.11976553708862919,19.637080841481772
149,14.900186205776128,41.06395299402328,0.1899227497189743,19.458575516899906
150,15.000187455479324,39.69275992715512,-0.5917904362723728,19.981687948270544
151,15.100188705182518,39.473604645318154,-1.235835029837858,19.82802178648086
152,15.200189954885714,41.04392803358852,-0.5077517996915466,19.608948386889118
153,15.30019120458891,39.39103209695981,0.35078855439711354,19.506304608519265
154,15.400192454292105,40.609473984927654,0.32451327615162445,20.199805398762216
155,15.5001937039953,39.47419190141931,-0.100179308553223,20.03500492713977
156,15.600194953698496,39.906368884935155,-0.33055234489553237,20.00233982786234
157,15.700196203401692,40.27679810220176,-0.23303188257122193,19.322187553051087
158,15.800197453104888,39.90656807969351,0.13420621870448848,19.76501240913102
159,15.900198702808083,39.63648018766545,0.6847280447018761,21.071638951176272
160,16.000199952511277,40.223146487853995,-0.22784424685842572,20.908732452108378
161,16.100201202214475,39.31753510545326,0.59995999152072,19.31041063078367
162,16.20020245191767,39.74717430829424,-0.37533769127437294,19.797719037128658
163,16.300203701620866,39.94805117402201,-0.16494757992412454,19.53289162605559
164,16.40020495132406,39.49711625172718,0.01061132666265391,19.792882192788802
165,16.500206201027254,39.463171682827955,0.5152436258454135,20.469122526819653
166,16.60020745073045,38.84374700251037,-0.6971967428309002,19.490517096411693
167,16.700208700433645,40.50445947605007,-0.6587423353150386,20.350934419143314
168,16.800209950136843,39.87243444803691,0.24135885528216985,20.076879878966967
169,16.900211199840037,39.57082868135997,-0.5005774633114837,19.18687362243611
170,17.000212449543234,-0.1785088927532954,-15.092599711397357,20.7899731469596
171,17.100213699246428,0.44605040876469887,-13.721630581662517,20.138629831780577
172,17.200214948949625,0.6578301908359092,-13.887934902106476,18.37927719500859
173,17.30021619865282,-0.17631781453903916,-13.35956426915024,19.682221490585395
174,17.400217448356013,-0.047409856239996856,-12.864001819270737,17.958100456218798
175,17.50021869805921,-0.010325512585888343,-12.739277115580078,19.412217585879777
176,17.600219947762405,-0.4539095546205968,-11.531258072195962,17.77879200167482
177,17.700221197465602,1.1250461548342343,-11.232707662845435,17.18034155346997
178,17.800222447168796,0.030574403711446076,-12.317939820348483,16.471642968302753
179,17.900223696871993,-0.971181181995755,-11.346778826907022,16.478026324103727
180,18.000224946575187,-0.7443128414957889,-11.942798285385303,16.14908985815823
181,18.100226196278385,-0.024778152636477903,-9.367427485853753,16.804224360534246
182,18.20022744598158,0.17088738964425723,-10.227210959990693,15.459578795543027
183,18.300228695684773,0.3271919050952578,-9.638872933793941,14.747283297150716
184,18.40022994538797,-0.20341448879692572,-9.432354356187822,14.347457648859168
185,18.500231195091164,0.49937380998191316,-9.480512275230605,14.725864203970108
186,18.60023244479436,-0.8943357579753672,-8.61233456970784,14.019519619131014
187,18.700233694497555,-0.2616564212981533,-9.115578388145218,13.31203598233721
188,18.800234944200753,-0.7606790580015792,-9.388740372960495,14.113814457382173
189,18.900236193903947,0.2192833741501351,-8.228067388162158,13.952477327344429
190,19.000237443607144,-0.1561229291521828,-7.504151444092682,13.040018154687605
191,19.100238693310338,-0.4146302105791862,-6.972919504978642,12.653520734041999
192,19.200239943013536,-0.7211069546325445,-7.444317081247453,12.877480614324138
193,19.30024119271673,-0.2906826729170969,-6.644078891460625,12.290311656466509
194,19.400242442419923,0.8200154498721364,-5.751625914118921,12.535702325657454
195,19.50024369212312,-0.660843619656955,-6.9106348372325925,11.235984865488929
196,19.600244941826315,-0.2053496791773829,-6.058686915926571,12.538655729494225
197,19.700246191529512,0.15552352209352097,-6.521861834781967,12.141143574413519
198,19.800247441232706,0.11797978815429686,-6.085574641555514,11.687098972185051
199,19.900248690935904,0.41053029522275813,-5.299205272307379,10.509478830786385
200,20.000249940639097,0.2726744347022862,-6.018352223225231,11.416617684509081
201,20.100251190342295,-0.3992444838458848,-5.3902314765806105,11.161101451527234
202,20.20025244004549,-0.20184315803729522,-5.023017002411536,10.38853810797803
203,20.300253689748683,0.14747549980065028,-4.584439356625502,10.6827719789919
204,20.40025493945188,0.23361304125831006,-4.233977902146246,9.593468772322812
205,20.500256189155074,-0.46251510445081145,-4.894176921944602,10.110517503972057
206,20.60025743885827,-1.0831045407360935,-4.3408041328459435,10.071466984454595
207,20.700258688561465,0.9340784796837284,-4.09567473882459,10.265712468301276
208,20.800259938264663,0.5155500086709576,-4.339149002314836,9.865369246809868
209,20.900261187967857,0.20322824036713746,-3.5800883651870192,9.678170517256037
210,21.000262437671054,0.36742064909099786,-3.6055335608042336,8.467871835657734
211,21.100263687374248,0.2910031542851348,-3.645462281496712,8.762667334334019
212,21.200264937077442,-0.9848320740624649,-3.1329679858731927,7.797596211101648
213,21.30026618678064,0.2516907457973592,-2.9685172267482796,8.948265776149235
214,21.400267436483833,-0.040588760894576886,-3.8101124140733695,9.107276968209002
215,21.50026868618703,-0.514090272822916,-2.989137800582234,7.871638790040251
216,21.600269935890225,-1.1857203511076329,-3.930749619282165,8.103209483669946
217,21.700271185593422,-0.4257312188893265,-2.795563798034787,7.181772338755655
218,21.800272435296616,-0.5632164577853029,-2.341313689909422,8.432153628217753
219,21.900273684999814,-0.5897096746932737,-3.2311031749690993,7.233905714830441
220,22.000274934703008,-0.012514118317094298,-2.450804988305012,6.567406418947303
221,22.1002761844062,-0.24553388593503908,-3.1734429312029944,6.905654250887844
222,22.2002774341094,-0.45674768134553756,-2.4913304978111417,7.079202048862789
223,22.300278683812593,0.2306041561897504,-1.5021817267908968,6.3082232405182195
224,22.40027993351579,0.6746613501545121,-1.9065213101012208,6.663115775376865
225,22.500281183218984,-0.48020552971875313,-2.2890819154359905,6.046272724730828
226,22.60028243292218,-0.2187856788500126,-2.601275442691607,6.271070066625869
227,22.700283682625376,-0.580824091361654,-3.230210876725518,6.622034289969561
228,22.800284932328573,-0.2066549535015631,-2.2781333831056623,5.95527776310882
229,22.900286182031767,-0.1342315244590671,-1.440093156720856,6.057875047101161
230,23.00028743173496,-0.6032364244826165,-1.80423145586485,6.4317270343579604
231,23.10028868143816,0.1722797009114965,-2.2413780753408807,5.261856415435559
232,23.200289931141352,-0.16210657013388508,-1.5543765316243916,6.818343393325334
233,23.30029118084455,-0.5683666312065596,-0.9145451795858129,6.007048330455265
234,23.400292430547744,0.40165992346355267,-1.4720522486530387,6.265589167761275
235,23.50029368025094,-0.48056886727860354,-1.6736636687875588,5.104752386036676
236,23.600294929954135,0.4483217605220577,-1.6459657402982772,5.006651497886325
237,23.700296179657332,-0.9553097153643031,-0.9427505238196487,6.032206648598208
238,23.800297429360526,-0.4945526010959481,-1.1005343677621502,5.348872549303184
239,23.90029867906372,0.9395074604323731,-1.818710651765827,5.050234730071944
240,24.000299928766918,0.6999208907848956,-1.75193651601671,5.61838931320419
241,24.10030117847011,0.07638187764188738,-1.6944869737964647,5.358634906810003
242,24.20030242817331,0.02451279604258332,-1.8373919282891642,4.872055219764909
243,24.300303677876503,0.5029402427488087,-1.0302147537839885,5.156093209575661
244,24.4003049275797,0.6226028056294746,-1.073493223211667,5.431647629118998
245,24.500306177282894,-0.6064941027910926,-0.3506512036605385,3.620248176896911
246,24.60030742698609,-0.43059152963984404,-1.3042124898890024,4.363489639302338
247,24.700308676689286,-0.44128467151875533,-0.6656504436452435,4.205975814125609
248,24.80030992639248,-0.060120194724471915,-1.3851501142953904,3.8707251900262145
249,24.900311176095677,-0.5472334719844256,-1.8187287089137052,4.105510083361967
250,25.00031242579887,0.5790159402619754,-2.265575986352071,4.226666824353724
251,25.10031367550207,1.0144579280955164,-1.0206227127605738,4.229107126239178
252,25.200314925205262,0.20022718141193824,-0.39143016227926997,3.483464175000946
253,25.30031617490846,0.24598894813700656,-1.6202625878098256,4.112332898272944
254,25.400317424611654,-0.01800058871034991,-0.7149816319866074,3.930375443783455
255,25.50031867431485,-0.30808047024284235,-0.611036340892936,2.963928874907258
256,25.600319924018045,-0.6824490898279862,-1.0251362721514372,4.005965628512626
257,25.70032117372124,0.3628118749564801,-0.633645132941954,2.9921292159932413
258,25.800322423424436,-0.4454491704481667,-1.6825736132667657,3.164228321578568
259,25.90032367312763,-0.4009415278355792,-0.819822103253498,3.059070892131489
260,26.000324922830828,0.8062237674555995,-1.5121389905542753,3.2636445341936167
261,26.10032617253402,-0.0741217450850633,-0.5466166548383957,3.1834244963205633
262,26.20032742223722,0.2195975738818563,-0.7508727362175224,3.4602358487472564
263,26.300328671940413,-0.04282445877077871,-0.9622769160583151,2.4551439111522693
264,26.40032992164361,0.2594124226138222,-0.20140918978637695,3.479771085555383
265,26.500331171346804,-0.2499616334543733,-0.21395014641235383,2.486621530086495
266,26.60033242105,-0.5559444324367177,-0.6916437068902936,3.1437990820654886
267,26.700333670753196,0.05651550792334975,-0.9034809314773147,2.817481125517155
268,26.80033492045639,0.922698486223253,-0.8989799481832756,2.9631315767661865
269,26.900336170159587,0.3090931462544841,0.593407811798474,3.0063712040322454
270,27.00033741986278,0.6140343165148041,-0.27102552880877867,2.1784554114402654
271,27.10033866956598,-0.11357393895922016,-1.0601053619227259,2.9539657965954724
272,27.200339919269172,-0.04105800482313144,-0.1462391104526678,2.1446481999805345
273,27.30034116897237,0.6372277375974297,-0.7818326682712007,2.327260068247776
274,27.400342418675564,0.5132092988268375,0.29600871915528526,1.9277378066523092
275,27.500343668378758,0.007180061820817078,-0.7840809345994573,1.6366443138500897
276,27.600344918081955,0.30812310606330073,0.3140666436436227,1.6524106333711286
277,27.70034616778515,-0.6021412875522757,-0.9702519766008957,2.8210524570851714
278,27.800347417488346,0.5645227452279913,-0.8376873872480041,2.3883760005730488
279,27.90034866719154,0.39673351938923634,0.09155637991246252,2.4619699768007486
280,28.000349916894738,0.3533263203251999,-0.18562317266737338,2.346021150092035
281,28.10035116659793,-0.47041662724997707,-0.022920277098389563,2.8935782284992446
282,28.20035241630113,-0.1940508859516996,-0.4832922639649192,2.0707087478709436
283,28.300353666004323,-0.009528684670654805,-0.29742677351939106,2.6082334056821006
284,28.400354915707517,-0.10037154240844583,-1.306587452854414,2.511791785967758
285,28.500356165410714,0.006728616372520484,-1.3523414628393693,2.5152156311730893
286,28.60035741511391,-0.5269765829004392,-0.21599233560408693,0.7892088082158655
287,28.700358664817106,-0.15407636388221316,0.42407363965981726,1.9205417675199947
288,28.8003599145203,0.5401131497508278,0.3052833564388524,1.9873008773056533
289,28.900361164223497,0.018988385661219416,0.5488919678047636,2.2669627277699793
290,29.00036241392669,0.10896491682198317,-0.47489396272403206,2.3304937874833427
291,29.10036366362989,-0.3790305326908696,-0.7618837583666359,1.6102908750732903
292,29.200364913333082,-0.08289408673643549,-0.30250448857094114,1.615664584770668
293,29.300366163036276,-0.14191745627163121,-0.11125552266112887,1.7960871328611372
294,29.400367412739474,0.17410340547791459,-0.02437233885291587,1.4696688465540417
295,29.500368662442668,-0.3448972260591714,-0.8086158101709903,2.034814090632702
296,29.600369912145865,-0.1124863555803243,-0.02910687744069934,2.1477550703290014
297,29.70037116184906,-0.511008538928229,-0.04551143285694981,1.1562151422662512
298,29.800372411552257,0.6753317745441653,-0.18849666298440035,0.8784705088646316
299,29.90037366125545,-0.7641233604704957,-0.27507584617408054,1.1480089123559805
300,30.000374910958648,0.10799411577351202,0.6583746664944901,2.0024814517297695
301,30.100376160661842,0.3273395426631095,-0.8137303686203822,1.3704369136852168
302,30.200377410365036,-1.398912392579495,-0.8584941950336938,1.6841196818509647
303,30.300378660068233,-0.2632391245197283,-0.29202684711161886,1.4116883873936257
304,30.400379909771427,-0.6302534785838024,0.8421183722353478,0.6723076273596086
305,30.500381159474625,0.0474814615026669,-0.7492508580955367,1.6604257513146161
306,30.60038240917782,-1.2555082941097513,-0.530945841847631,1.2145274136400397
307,30.700383658881016,-0.28446409822795077,0.27709384035185847,1.4511146239218813
308,30.80038490858421,-0.305748938915578,-0.23001850572504806,1.3446936653440387
309,30.900386158287407,0.2806877458347113,0.09136130636427023,1.7313445088851838
310,31.0003874079906,0.349790506320458,0.4863107571589449,1.25977565525866
311,31.100388657693795,0.08676395345492996,-0.4541006000099502,1.2992357108841346
312,31.200389907396993,-0.2912045475870747,0.005754185870726347,1.3518693070113152
313,31.300391157100186,-0.7702980819051193,-0.1789022038041326,0.9806182762869243
314,31.400392406803384,-0.4113473428967062,-1.5577274041498337,1.478842989578754
315,31.500393656506578,-0.3632193547950238,-0.2334985978437311,0.06756641101871641
316,31.600394906209775,-0.6657913730469791,-0.7763232761497891,0.5329383078519887
317,31.70039615591297,0.7054043683611706,0.5087074269989418,0.26803272839742587
318,31.800397405616167,1.0358125457228806,-0.1100437360222622,0.26488607833916855
319,31.90039865531936,0.024631245615807772,0.019470139429303576,1.092669923918276
320,32.000399905022554,-0.38278113917245044,0.2002152242195002,0.6047263309909294
321,32.10040115472575,0.6693109930643087,0.38828982489298536,0.7022106282079095
322,32.20040240442895,-1.069244456499178,0.12990316241640398,0.9172203391989053
323,32.30040365413214,0.4569536346828764,-0.20491693558387608,1.2275864069464375
324,32.40040490383534,0.20659451767792286,0.26991397794115013,1.0391540774458088
325,32.500406153538535,-0.6287964459423562,0.4449906088222113,1.093134482905502
326,32.60040740324173,-0.5622370946261498,-0.7362939523001684,0.47197112002336167
327,32.70040865294492,-0.3769272496906079,-0.18348069923436972,1.3844372257643898
328,32.80040990264812,0.3234076169139841,-0.23596645291343685,0.6547634424470017
329,32.90041115235132,-0.6805743934423097,0.08267595037735534,1.2220029098438179
330,33.00041240205451,0.15324054935982792,0.53218947865308,0.7067563911297774
331,33.100413651757705,0.23950031271928696,0.7479452609477525,1.2834297721373253
332,33.2004149014609,0.9179966469581334,-0.4712619105429583,1.250958438228755
333,33.3004161511641,0.12653565393977062,-0.2677894784445186,1.5021922646814572
334,33.40041740086729,-0.8925697616212201,0.6808533657748901,0.5883786838415268
335,33.50041865057049,0.22368387901012313,0.4836447666564644,0.5057881057648612
336,33.600419900273685,0.9927167280095681,0.7274306369480855,0.9720744150103153
337,33.70042114997688,-0.08685908058162549,-0.3876262052886231,1.6629928314164661
338,33.80042239968007,0.07614988963365081,1.113688605081813,0.7180406258678251
339,33.90042364938327,-0.03115928045819237,0.589329562599565,0.1772254516415548
340,34.00042489908647,-0.09712397827919302,-0.8211766484003648,0.5983336577635917
341,34.10042614878966,-0.2478231306794397,0.8970283870097506,1.369512549897006
342,34.200427398492856,0.5941748226343172,0.6645047741425265,1.196189740046285
343,34.30042864819605,0.6103610624944261,-0.5286517919811806,0.9901222651176498
344,34.40042989789925,-0.563286060341158,-0.43054277088591836,0.0016450541562379462
345,34.50043114760244,0.4050589911861173,-0.43966504128552986,0.6432064045992534
346,34.60043239730564,-0.00975285067987534,-0.5859586033554448,0.5772795441898312
347,34.700433647008836,-0.17143484462899808,0.5805913425063228,0.16667356716129977
348,34.80043489671203,-0.4374782841930333,-0.73685617139051,0.3580884015797958
349,34.900436146415224,-0.5743809758992933,-0.37943331670583813,1.0224856044233999
350,35.00043739611842,0.3402982597621469,-0.8533711111995887,0.67370302237125
351,35.10043864582162,-0.07027463777907075,0.9413671040834433,0.5462611156218449
352,35.20043989552481,0.046233599323354184,0.04323446482597313,0.3232191541814867
353,35.30044114522801,0.6521153368741729,0.46867210915987917,0.8869254220474525
354,35.400442394931204,-0.08216696531403561,0.5114093835832159,0.7030090839596624
355,35.5004436446344,-0.0712324496660549,-0.0944884399263341,0.7036158273106571
356,35.60044489433759,0.2716597997391413,0.7114872604552985,0.6064202563544556
357,35.70044614404079,0.422245092447095,0.09120241128339932,0.5302233585563154
358,35.80044739374399,0.16386687794435947,0.5656385089067723,0.6224823920270746
359,35.90044864344718,0.26060258642528217,-0.20885501487631755,0.5268601815730052
360,36.000449893150375,0.5886702508403113,1.1157903066863664,0.37558539560573834
361,36.10045114285357,0.2696134077235228,-0.17185681545344692,1.0308496444636255
362,36.20045239255677,-0.7563915766757054,0.020850900850406008,0.5715375581840709
363,36.30045364225996,-0.8565747987848513,-0.4953628933031489,-0.06824066204239598
364,36.40045489196316,0.2723080561621328,-0.18426074426025424,1.227145219360878
365,36.500456141666355,-0.11524223918365065,-0.4944244137213628,0.2962270128746025
366,36.600457391369545,-0.16056230410666555,0.4695912398546278,1.221964404922848
367,36.70045864107274,-0.2324448993038041,0.2973824106239364,0.6495112124385598
368,36.80045989077594,-0.9079639657260818,0.2575473242066954,0.29725175409476157
369,36.90046114047914,0.435545037604703,-0.49684721322814474,0.7439344421811509
370,37.00046239018233,-0.5252583546765264,-0.20067129199161585,0.29684633894943463
371,37.100463639885525,0.7003907531837258,-0.2649903909811535,1.417650597050395
372,37.20046488958872,0.4685739667704363,0.662875159427298,0.05317917085639429
373,37.30046613929192,0.48480113108163636,0.16652906815592075,-0.3544136243595659
374,37.40046738899511,-0.023887505368577727,0.5577256075196786,0.6318268451801726
375,37.50046863869831,-0.7370864605874327,0.8028677054648914,0.1534235249601409
376,37.600469888401506,-0.37753231523830577,0.42872543612102804,0.01283700860380188
377,37.700471138104696,-0.01894314575585269,-0.8863748403407633,0.9135627391228678
378,37.80047238780789,0.3977789326460563,0.43931347981314844,-0.008227294936981988
379,37.90047363751109,-0.02419336199564737,-0.9856445486921591,0.7292709520747656
380,38.00047488721429,-1.0479330545576977,0.34409207390636154,0.17604246225392994
381,38.10047613691748,-0.4936878504136678,-0.49070366872869237,0.7023689887254705
382,38.200477386620676,-0.0071232337177903745,-1.0320068694716187,0.4189755375234313
383,38.300478636323874,-0.5233011128590418,-0.903796211236963,1.073881216734415
384,38.40047988602707,-0.026450881473004496,-0.48143144477451594,1.542226767158134
385,38.50048113573026,0.06316558717107247,-1.401200525712624,0.5704274058046215
386,38.60048238543346,0.22124920067115866,0.1446353390012143,-0.19640924245989583
387,38.700483635136656,-0.26745482154789,0.03673657667962104,-0.23256929312836172
388,38.80048488483985,-0.4912375326528167,0.5640880835262373,0.19904906214046603
389,38.900486134543044,0.217282469549334,-0.4359582142452318,0.5854022013701266
390,39.00048738424624,-0.15389808663514792,0.511140528563363,0.09815842983717907
391,39.10048863394944,0.007033718440003367,-1.0157759194597444,0.518736005189163
392,39.20048988365263,-0.7075182935911912,-0.7050632348336199,0.416337685429345
393,39.30049113335583,-0.8901070386531407,-0.3134018777520316,0.45362731378389365
394,39.400492383059024,0.06575037521919692,-0.7159490530153947,0.19350381938221173
395,39.500493632762215,-0.46081842829533864,-0.03724315696910751,0.5872286587320363
396,39.60049488246541,0.1064926384808588,-0.433635657956601,0.2943119128052066
397,39.70049613216861,0.6130277477105182,0.2656189200343332,-0.1274288669378558
398,39.80049738187181,0.777537317444525,-0.2539423279331759,0.9310608501994638
399,39.900498631575,-0.31178460827185234,-0.16319148109440745,0.08838947945340178
400,40.000499881278195,-0.003510017905365614,0.15307473489114767,0.45131456625257044
401,40.10050113098139,-0.16070964544402425,0.22263766374313612,0.5286890357454751
402,40.20050238068459,-0.03794253858777639,0.5605744135899292,0.2771395551346222
403,40.30050363038778,0.35244178199354304,-0.15774671980847169,-0.215635788098264
404,40.40050488009098,-0.03437038552186465,-0.3959396869303354,0.48801876228044105
405,40.500506129794175,0.17479159986647086,0.1849025568095008,-0.19050131257925124
406,40.600507379497365,-0.8401005477249363,-0.6215479257249925,0.7595882015957592
407,40.70050862920056,-0.0008089150939781441,-0.7054327347858141,0.9453692595538532
408,40.80050987890376,-0.08302365645182572,-0.007577841793330839,0.398123797635363
409,40.90051112860696,-0.3913333245843906,0.4358683424782011,-0.19221096999292764
410,41.00051237831015,0.48507917189633737,0.11817603679848133,0.4849140055302694
411,41.100513628013346,0.5988112421599343,-0.4697913867285423,0.45879170780365586
412,41.20051487771654,-0.3670470838700742,0.17014099548331446,0.2016082944638188
413,41.30051612741973,-0.5066304583157968,1.0260375541680073,1.7285209445943155
414,41.40051737712293,0.7314169361540883,-0.10641882796894389,0.4119304899995434
415,41.50051862682613,0.03593749930811897,0.08573619228954049,0.043645169638011974
416,41.600519876529326,-0.6609606845543207,-0.03203452023680299,0.023871691305578258
417,41.700521126232516,0.17282157715065763,0.22804510050058702,-0.8239419566161932
418,41.800522375935714,0.05137785258124985,0.2807354115689501,0.04315329060138556
419,41.90052362563891,-0.29269172685477207,0.6582063767163457,-0.3218694495668631
420,42.00052487534211,40.367535535505596,15.553178795766593,2.9113813117661387
421,42.1005261250453,39.522232492332115,15.178107513886772,3.684385714719347
422,42.200527374748496,39.61641832002889,14.634440215419442,3.101735810124159
423,42.300528624451694,39.27382808149115,14.358964061516978,3.2138728655263993
424,42.400529874154884,40.04258223003834,14.917213283375489,2.289765269145548
425,42.50053112385808,40.15542108292739,13.726972491731322,3.2788147577487807
426,42.60053237356128,40.60904923430001,14.1848726232554,2.7483222856778045
427,42.70053362326448,39.45526251591603,14.397727373113163,3.242708357191047
428,42.80053487296767,41.24730035544504,13.777201196200703,3.138050886825649
429,42.900536122670864,40.48136347172712,14.250365964124343,3.5251554047570766
430,43.00053737237406,38.98335922801922,14.033819808734298,3.5597080689266116
431,43.10053862207725,40.21177672202841,13.988338224215367,2.688687954471396
432,43.20053987178045,39.66270503455816,13.342280705549172,3.533653969769797
433,43.30054112148365,39.65323097008696,12.499495694798043,2.9852797706986185
434,43.400542371186845,40.1819654788535,13.32995884530035,3.6370616282139996
435,43.500543620890035,39.783827029884954,12.673819097606899,3.8917934577146007
436,43.60054487059323,39.92555746658128,13.132230476345772,3.8803252925286107
437,43.70054612029643,39.87422016966427,12.036947310877913,3.6642767855824823
438,43.80054736999963,40.176301203974546,12.138849607292498,3.8270014963245282
439,43.90054861970282,39.4741295204798,11.397103773521621,4.2093731252313376
440,44.000549869406015,39.477775774968954,10.907908113418882,4.49241885509969
441,44.10055111910921,41.06367041773761,10.844959903094868,3.371827921068975
442,44.2005523688124,39.525181363328976,11.489008404279458,4.457980542302534
443,44.3005536185156,40.46114651081588,11.368399035187268,4.325294862353479
444,44.4005548682188,39.959100346971745,11.800363495834036,3.578453758887034
445,44.500556117921995,39.65128379278654,10.56062338832206,5.301544089058053
446,44.600557367625186,39.72023663564731,10.90647329852495,3.897925999814912
447,44.70055861732838,39.718434177818175,10.186339934872825,5.212346912205165
448,44.80055986703158,40.58041782623359,10.4351716676573,4.724931736174592
449,44.90056111673477,39.709953632085295,9.717660143019863,3.9917730547324792
450,45.00056236643797,40.6221208761236,11.050643021150046,5.290657858135361
451,45.100563616141166,39.56740766997174,10.290068806066218,5.1848263184147765
452,45.20056486584436,41.049199877017934,10.279277459457896,4.793633469133173
453,45.300566115547554,39.787828384504245,9.5976325140637,4.628001720003111
454,45.40056736525075,39.556243520553174,9.623964757680993,4.797686547789686
455,45.50056861495395,39.92779800309788,9.309210550488038,5.3403027334195
456,45.600569864657146,40.26541353997683,9.126398340900812,6.279017700185188
457,45.700571114360336,37.776336016759714,9.553514686554411,5.015323432139669
458,45.800572364063534,39.557174894511554,8.417907576278601,5.573830171369672
459,45.90057361376673,40.33351198763635,8.811823170428239,5.429940610691273
460,46.00057486346992,39.97468251368823,10.808229211367253,6.409201709663081
461,46.10057611317312,40.1686670170677,8.294067488322726,6.449911961808469
462,46.20057736287632,39.86122742603587,8.84246722409746,6.878110709947139
463,46.300578612579514,39.719392246152076,9.264212570791663,6.923410644043588
464,46.400579862282704,40.00003853061472,8.02474103499388,7.0554567284154075
465,46.5005811119859,40.18627538076857,7.834398837679574,6.622157527946981
466,46.6005823616891,39.467050167569965,8.304556739861017,6.862937408541541
467,46.70058361139229,39.68715559952044,7.777571388287945,7.022811151982618
468,46.80058486109549,40.51366441622048,7.644735497216198,6.724543483311204
469,46.900586110798685,40.08364496268514,6.1753122964374505,6.938945942937097
470,47.00058736050188,39.8314625846171,7.223725975365367,6.4214496693230405
471,47.10058861020507,40.201529901214855,6.825227318416458,7.9487811943066875
472,47.20058985990827,39.37133398421164,6.546923795222857,8.556337291126734
473,47.30059110961147,40.298059673198665,6.800535369438239,8.46200673844821
474,47.400592359314665,41.03358648278595,7.9648583569991604,8.21740523663089
475,47.500593609017855,40.10550178075836,6.3264934692159045,8.759442564156712
476,47.60059485872105,40.66265286133337,6.506348816889512,9.029309530015588
477,47.70059610842425,40.4799184903969,5.915136185221001,7.377704743486459
478,47.80059735812744,40.140233234930314,6.58098812738687,8.374714746137474
479,47.90059860783064,40.1681725173203,5.200065356705174,8.785817683771066
480,48.000599857533835,39.45327467219124,6.596326045490789,9.534287912921167
481,48.10060110723703,39.4209680111274,5.4505629891016385,10.032333394289264
482,48.20060235694022,40.30045469556589,5.861407919120208,9.630420737672742
483,48.30060360664342,39.65509713317745,5.655681867659559,10.436271250250488
484,48.40060485634662,39.21013371822499,4.985700422092017,8.984778999057072
485,48.50060610604981,40.19339799204044,4.88951256989066,9.838262903074586
486,48.600607355753006,40.63419433544133,5.445404694311612,10.178698814359539
487,48.7006086054562,40.63472533835423,5.146236209252317,10.758152443114879
488,48.8006098551594,40.01905239579958,3.97915772936314,10.930312612881973
489,48.90061110486259,39.705864051689396,4.235341906667419,11.42522500905613
490,49.00061235456579,39.5118150139969,3.8916515615629477,10.481130471886143
491,49.100613604268986,40.93591068090094,3.378688062854458,11.129556690132503
492,49.20061485397218,38.81883150518827,4.050009508967072,11.540284526373691
493,49.300616103675374,40.32114045477655,4.677903481965593,12.423444785612194
494,49.40061735337857,40.302436216739565,4.3838652712309765,11.631816271693474
495,49.50061860308177,40.6671345697205,3.824498243316757,12.502456317792783
496,49.60061985278496,39.93860214249938,3.0448444932509826,13.002450458006424
497,49.70062110248816,39.1875064108967,4.242447924445691,13.376338796733805
498,49.800622352191354,39.78157706012631,3.985294059572513,13.110474951562804
499,49.90062360189455,40.596118314456305,2.5574535452237432,13.500592970047565
500,50.00062485159774,40.490878101020485,2.213379991825819,13.21967890447637
501,50.10062610130094,40.01242374367696,3.2688301293780087,14.017354636752314
502,50.20062735100414,39.8087048839079,2.338940206902716,14.445776985158759
503,50.30062860070733,39.69189643032704,3.0029956085150835,15.057850763421651
504,50.400629850410525,39.92437470069736,2.4737363906038685,14.59729558928493
505,50.50063110011372,41.00756405444473,1.6831723106493375,15.42202187196812
506,50.60063234981692,40.01903302043295,1.5320654719090614,16.494220798605188
507,50.70063359952011,39.648335829324694,1.2235017630354323,15.171233186857705
508,50.80063484922331,40.08853345028571,1.4073825313505157,16.983956860460246
509,50.900636098926505,39.559740740315924,1.253348672877594,16.274396822451457
510,51.0006373486297,40.71695080747287,2.289906018996665,15.945085274336588
511,51.10063859833289,40.1400310015185,1.2088479344250984,17.107454309267972
512,51.20063984803609,39.75419622404141,0.5067205451996696,17.71145270072832
513,51.30064109773929,40.62230616658285,1.307244392319356,18.29712236995914
514,51.40064234744248,39.37916175651978,0.15593771316364413,17.85494876631772
515,51.500643597145675,39.595486032095614,0.7403182729575191,18.96197400621805
516,51.60064484684887,40.754172278246045,-0.29717403426758937,19.04584195753857
517,51.70064609655207,40.52328067547215,-0.06847364603803718,19.282421514370018
518,51.80064734625526,39.443370065729184,0.43482201639314594,20.086139788012495
519,51.90064859595846,39.81510295315894,-0.2466617605466893,20.204561226790638
520,52.000649845661655,39.5958821097157,-0.2826551234031901,19.402163589585772
521,52.10065109536485,40.40218719547425,-0.20604748433850784,19.532787988233142
522,52.20065234506804,40.374625943628914,-0.8641367375408756,20.590913432216897
523,52.30065359477124,39.01028883739243,-0.10368601172874532,20.613006274016556
524,52.40065484447444,39.60016058824756,0.7053405540092129,20.262847673081946
525,52.50065609417763,38.95570172305365,0.7645828935198035,19.744486085483707
526,52.600657343880826,39.735604317503686,-0.2653979984514223,20.468860047125844
527,52.70065859358402,38.91725163089441,0.4512710655132167,18.88703067846292
528,52.80065984328722,39.82236479124336,0.4129572146265617,19.720881033564392
529,52.90066109299041,39.89482573536698,1.4479861034531045,20.021374184303152
530,53.00066234269361,40.30657830913469,-0.28301786994632666,19.749169074695327
531,53.100663592396806,40.40599420893196,0.34472026926847193,19.937273257459953
532,53.2006648421,39.74872737037352,0.2970485362654567,20.85208126752463
533,53.300666091803194,38.921757993426205,-0.2353750847368221,20.061605957131388
534,53.40066734150639,39.89739672997418,0.08884417788866784,20.276505454435927
535,53.50066859120959,40.56490144393404,1.2522284962091734,19.771093075676337
536,53.60066984091278,39.82478812192287,-0.7568032833844521,20.06378293430843
537,53.70067109061598,40.06656518554563,-0.1724602041116854,19.246306633454974
538,53.800672340319174,40.249152011915676,-0.10577045467049763,20.68778492908201
539,53.90067359002237,39.85597629828887,-0.4633486283645847,20.368615284155823
540,54.00067483972556,40.412257861826106,-0.3380428151739098,19.565848483364704
541,54.10067608942876,40.66065288109627,0.3374149265530671,20.247163817482118
542,54.20067733913196,40.28651221626776,-0.3367800307166844,20.13176910774222
543,54.30067858883515,40.30445745154631,0.001656393198407107,19.41664666382375
544,54.400679838538345,39.69530803340636,-0.02308276190962008,20.437129603459578
545,54.50068108824154,40.3874212276384,-0.4873885408616198,19.97451852254646
546,54.60068233794474,39.96035349317232,-0.5313281044514999,21.078490196125767
547,54.70068358764793,39.91199963908577,-0.6304594565601044,19.539904257184062
548,54.80068483735113,39.387569887038175,0.5458121107341338,19.355930280242276
549,54.900686087054325,39.97891196263834,-0.279349593994459,20.263653676261782
550,55.000687336757515,40.03181033869881,-0.3115300673105409,19.828979956506025
551,55.10068858646071,39.829938264943735,0.6999013680855717,19.845919243923515
552,55.20068983616391,40.19001254297373,0.06436177103441343,19.637246261490926
553,55.30069108586711,40.513681127448756,0.219226561386349,20.622364749082912
554,55.4006923355703,40.057639466255864,-0.2419269098364511,19.707848524986947
555,55.500693585273496,39.49004527163662,0.19919469394515843,19.499239278241603
556,55.60069483497669,40.155352741932795,-0.2917013857203924,19.576330860530028
557,55.70069608467989,39.983294480536735,0.09911505198431281,19.662431396008355
558,55.80069733438308,40.03494398632076,0.31526414522952484,20.24205223396764
559,55.90069858408628,39.5931140408544,-0.48078722601641444,20.244008482226505
560,56.000699833789476,40.03213709353356,0.3977933766176128,20.427230688510107
561,56.100701083492666,40.25674816886016,0.3477898150815768,20.587714143188663
562,56.20070233319586,39.637182856336764,0.3172921339528508,19.88009563482123
563,56.30070358289906,39.90404030506809,-1.1191542105369618,20.43493700134053
564,56.40070483260226,40.42247572982841,-0.5347554006681104,19.37244996773055
565,56.50070608230545,39.21854672170354,-0.12579636751749335,20.682703380937514
566,56.600707332008646,40.29636903984662,-0.08706584612526322,19.833906976040147
567,56.700708581711844,39.133065960870724,0.22523480606857096,20.55816190288918
568,56.800709831415034,39.96932950796436,-0.7410804947280507,20.37739073958787
569,56.90071108111823,40.212693015931265,0.40085008558343516,19.45172495648045
570,57.00071233082143,-0.08370035987239423,-15.22675107000978,20.283379321314015
571,57.100713580524626,-0.596769016937881,-14.642937575294242,19.039659511810516
572,57.20071483022782,0.39763991651459646,-13.904159793677096,18.718761219825605
573,57.300716079931014,0.18956504719549863,-13.234140902697996,19.316463614642522
574,57.40071732963421,-0.291199090673212,-13.598811039959191,19.609652188937652
575,57.50071857933741,-1.2740359667005459,-12.861694107322538,18.249052703382674
576,57.6007198290406,-0.6075281513470956,-11.926367338701171,18.33222120149558
577,57.7007210787438,0.3107633491739548,-12.590322406959146,17.4825666715499
578,57.800722328446994,0.034887256150375294,-12.3882865701127,16.842784783259567
579,57.900723578150185,0.18081590467400846,-11.219993151592691,17.18489849022114
580,58.00072482785338,-0.47526124200339825,-10.93940467117473,15.554537865124697
581,58.10072607755658,0.25429952568869646,-9.393501997159326,16.58320376889108
582,58.20072732725978,-0.052776690785863674,-9.505811694502759,15.666912068132175
583,58.30072857696297,-0.025605941097546887,-9.594128929171125,15.643860322519217
584,58.400729826666165,0.20363595177764066,-10.130011571978955,15.47398666918569
585,58.50073107636936,-0.07212611066228153,-8.351721791611324,14.582468451194865
586,58.60073232607255,-0.29263371906773067,-8.87194363009968,14.159396043986641
587,58.70073357577575,0.5330274934100662,-8.074565990965102,14.737177867140584
588,58.80073482547895,-0.5425132082619779,-7.395785131842746,14.214941688120351
589,58.900736075182145,-0.3811461787055542,-8.117830413706804,13.472903093026519
590,59.000737324885336,0.09266591871778326,-7.275070448215937,13.641636973876327
591,59.10073857458853,0.46675500099016537,-7.308174491253321,13.134188617193914
592,59.20073982429173,-0.1873310636594938,-7.508544221682386,13.892154514767679
593,59.30074107399493,-0.02464417078759955,-7.699799279928747,12.282014184050198
594,59.40074232369812,0.11085300677347956,-6.422901356765626,13.529085832268272
595,59.500743573401316,0.4168625718335755,-7.488504740685635,12.381492349170156
596,59.60074482310451,-0.8051257361147919,-6.0577725895583665,11.498893579339184
597,59.7007460728077,0.3654276013115921,-6.71968618308757,11.832010214473828
598,59.8007473225109,0.0963815609734928,-5.635173479306096,11.04072556751779
599,59.9007485722141,-0.47556419895092983,-6.090433853173478,12.169718914146792
600,60.000749821917296,0.9765524880717515,-5.422765641792744,11.088932716177851
601,60.100751071620486,0.71441832281785,-5.4299600961284336,10.572098575218044
602,60.200752321323684,0.0979957489099917,-5.851083670738877,10.476446489968025
603,60.30075357102688,-0.23692894435759312,-3.9998816605713117,10.286586062047748
604,60.40075482073007,-0.719351945923542,-5.458122892951338,10.344419322459485
605,60.50075607043327,0.0651073318659994,-4.692549975807287,9.605010183453485
606,60.600757320136466,0.3382311284673309,-3.4930117971683616,10.428504565410286
607,60.700758569839664,-0.3833569926400068,-3.5267771874952665,9.269009409471979
608,60.800759819542854,-1.0091103677489859,-4.144959330898363,8.806241940730942
609,60.90076106924605,-0.2812233017834203,-3.750478230409853,8.426684264720349
610,61.00076231894925,-0.02776751461938526,-4.3678288275483705,8.501613323594336
611,61.10076356865245,0.9296733550256091,-3.095666446465522,8.97623196895406
612,61.20076481835564,0.04317231731504267,-3.417952226461098,8.435926366594455
613,61.300766068058834,-0.24175792223418105,-4.403529179283268,7.598238109908305
614,61.40076731776203,0.36493888821994197,-3.650800167129827,9.035556887581567
615,61.50076856746522,0.2014455242558327,-4.25047291050249,7.811413474536715
616,61.60076981716842,0.15817268708938187,-2.0937556634440386,8.359681355248506
617,61.70077106687162,0.09677070687219294,-3.729578547082329,7.26888687072444
618,61.800772316574815,-0.10064484229945728,-3.229370990005717,8.45771254236852
619,61.900773566278005,0.22688938475324313,-2.485173285434195,6.820195643023876
620,62.0007748159812,-0.6563375286266219,-3.8304602300535935,6.7623796858227
621,62.1007760656844,0.6234149302236461,-2.367184179794301,6.623721243205779
622,62.20077731538759,-0.7940424253396213,-2.3226013003871797,6.659855935321477
623,62.30077856509079,0.39502516285311434,-2.882332447866103,8.487974282702014
624,62.400779814793985,-0.33253571407144866,-2.198194970325519,6.791758431145039
625,62.50078106449718,-0.5055336861232246,-1.8445044163132318,6.780232538904284
626,62.60078231420037,0.18531418855292706,-2.2801474084196873,6.264588632400274
627,62.70078356390357,0.4155424139598071,-2.2007687477469133,6.175706189322873
628,62.80078481360677,0.05088130031023903,-1.9661552657815953,6.41772748210086
629,62.900786063309965,0.6260775146265349,-3.038385118895874,6.02099887224332
630,63.000787313013156,0.5572922911110427,-2.1676297691213415,6.190377079031032
631,63.10078856271635,0.1396184770620744,-2.1505814462855377,5.584508738723592
632,63.20078981241955,0.49696056424597596,-2.31690845362082,6.396084903177048
633,63.30079106212274,0.7861781853959989,-1.6935132618357276,5.695406981806581
634,63.40079231182594,-0.6906806025279,-1.3794237880420122,4.383532364106711
635,63.500793561529136,-0.4140051112873568,-1.8129733342673389,5.393633379260412
636,63.60079481123233,-0.6321650599592237,-2.0961628573714486,5.511406046340298
637,63.700796060935524,-0.8997347083824652,-1.3711167561755395,4.681465627559474
638,63.80079731063872,-0.25739170397601174,-1.9974789771854198,6.114062821048251
639,63.90079856034192,-1.0222551186094404,-1.0331032124409303,4.927143531184121
640,64.00079981004511,0.4045341495685054,-0.9317199356266309,5.074909975515441
641,64.1008010597483,0.22395946110175946,-2.1844165776047317,5.773053339559562
642,64.2008023094515,0.3013863494854845,-0.7985998693108479,4.908582658982798
643,64.3008035591547,-0.16517766684446264,-0.8426709733196139,4.037042152369973
644,64.4008048088579,0.045141556189978976,-0.9806457884687325,4.239978197427014
645,64.5008060585611,0.21543587395229563,-0.3330459273879537,4.582397897559937
646,64.60080730826428,0.14920091091915416,-0.9225835030516504,4.667294564894758
647,64.70080855796748,-0.09685401777785575,-1.0458234289077721,4.15440872775631
648,64.80080980767067,-0.48314827959631956,-1.251823827838273,5.18806691257911
649,64.90081105737387,-0.6170200784771405,-1.4403207418411,3.237489733224005
650,65.00081230707707,-0.6565446962091704,-0.7972008735422947,4.321299459896578
651,65.10081355678027,-0.6275065736361253,-0.22018089147662046,4.2126563290399535
652,65.20081480648346,-0.6225013838736704,-0.5452450878402684,3.136106216301278
653,65.30081605618665,0.04462582886851227,-0.8765267217216375,3.409948158584477
654,65.40081730588984,-0.44843311300085337,-0.43356489086204425,4.340394167958336
655,65.50081855559304,0.9337108438964318,-0.9252224226321883,3.1970463208647537
656,65.60081980529624,0.07887848131778363,-0.33397084514071407,4.277370849067835
657,65.70082105499944,0.9721985800569365,-1.3600692882674628,3.73156390144525
658,65.80082230470263,-0.2882351550823874,-1.0283459905466579,3.6838513819151077
659,65.90082355440583,0.8187792079695783,-1.1287042002985728,2.5019077934891407
660,66.00082480410902,-0.33912665591877444,0.11554057872134749,3.110173533997605
661,66.10082605381221,0.7486548725565725,-0.45341152808731183,4.056641877628011
662,66.20082730351541,-0.3362564512874541,-0.8445290031434521,3.662876357654432
663,66.30082855321861,0.07403760511888466,-1.0810218935928555,2.5548883985202817
664,66.4008298029218,0.07191665159374401,-0.4162083308804617,3.2044382045199167
665,66.500831052625,0.4475228806913538,-0.7330453479046573,3.118915900770787
666,66.6008323023282,-0.01869576448053408,-0.19542393878609693,2.7169199897542735
667,66.7008335520314,0.3600519696305426,-1.013157380888868,2.619337953255793
668,66.80083480173458,0.5132199626942534,-0.3938839456068447,2.8902269649613097
669,66.90083605143778,1.2232502044119615,-0.4351441192028207,3.3851529842537085
670,67.00083730114098,-0.34332087794501165,-0.05235535016787407,2.959716421007272
671,67.10083855084417,-0.1507986103161757,-0.7022069484561972,2.9158632359007903
672,67.20083980054737,0.0007451052929750234,-0.7524998713236009,2.742100108846343
673,67.30084105025057,-0.23287489275654236,-0.4061402836070325,2.698529021293906
674,67.40084229995377,0.6849165391656825,-0.2933697770842436,3.0174184700593507
675,67.50084354965695,0.31863921564529807,-0.41547132404815595,2.0882107586258583
676,67.60084479936015,-0.21941627120618093,-0.7838622147855889,2.5756544515346307
677,67.70084604906334,0.43951562659151056,-0.31878448453249464,1.8017299252122125
678,67.80084729876654,-0.6618906689897418,0.4190179615607733,1.4070203534363093
679,67.90084854846974,0.7585419473035498,-0.7661224270520086,2.1957133613289765
680,68.00084979817294,-0.18117269824206161,-0.05677146053622406,2.547813687757814
681,68.10085104787613,0.5140430270410821,-0.36390519097700746,2.196540031391878
682,68.20085229757932,-0.2781414810373977,0.10891760185977994,1.3659738558279861
683,68.30085354728251,0.057334975939251714,-0.25186485604999354,2.731393625228953
684,68.40085479698571,0.43800681251939544,-0.34329942411943987,1.0312858485019714
685,68.50085604668891,-0.1852393356834152,-0.6623951302092896,1.2407407718816996
686,68.6008572963921,-0.06293798236272226,-0.05615864743941937,1.5735314709517905
687,68.7008585460953,0.3185090451084704,-0.5807548613678978,2.078275879827766
688,68.8008597957985,-0.4524038412766819,-0.3709727359542831,1.6427623949390389
689,68.90086104550168,-0.2953633748534464,-0.5650587949014496,2.4223287561690805
690,69.00086229520488,0.10672025233523363,0.5530129863442211,1.0431565288339004
691,69.10086354490808,0.549589529822362,-0.20640617337375872,2.1651671188274753
692,69.20086479461128,0.46384163287219843,0.34218703054639965,2.178961136718477
693,69.30086604431447,0.3716292575942021,-0.10827218390596391,2.246022818834481
694,69.40086729401767,0.6010679926641385,-0.7149881469742672,1.7273891945143112
695,69.50086854372087,-0.24255327930459628,-0.4732735651390537,0.9937506260949703
696,69.60086979342405,0.37444757331309775,-0.06095939603284045,2.7220028345784675
697,69.70087104312725,-0.3812888787857306,-0.6497996285916248,1.3530330092440734
698,69.80087229283045,0.029165608302124366,0.31560189059345334,2.3418343737099665
699,69.90087354253365,-0.18622255502153942,0.07574034294697218,1.5544259069529125
700,70.00087479223684,0.45847380170668783,0.30932091867803446,1.8423464929222377
701,70.10087604194004,-1.0027781337760684,-1.0618036825471673,0.2905234930729925
702,70.20087729164324,0.2630154301642577,0.6566994711304104,1.3137183203469045
703,70.30087854134644,-0.34127716027904564,0.2961683108400025,1.4902430792202084
704,70.40087979104962,-0.4595442263025891,-0.42930983027565855,1.4958684472677422
705,70.50088104075282,0.8095540400046362,0.4564900462915973,1.381693753761121
706,70.60088229045601,0.5817319238447971,-0.391909470451113,1.4786038005867004
707,70.70088354015921,-0.16562222798295612,-0.22243731307007575,1.0723181167389175
708,70.80088478986241,0.45537884219192354,-0.1618654640815078,0.16123361042608564
709,70.9008860395656,-0.06656784830409548,-0.4323342437598357,1.399281784415416
710,71.0008872892688,-0.6684776022640787,0.20908290157835602,1.4448937679568463
711,71.10088853897199,0.5364491710235327,0.3049239068026371,1.3909351061177286
712,71.20088978867518,0.045831767729990154,1.0063544628765684,1.2002114048606045
713,71.30089103837838,0.22356858222867929,-0.3463863755400345,1.4443312731271654
714,71.40089228808158,-0.17558823673116508,-0.7524334166943641,1.3780930619801925
715,71.50089353778478,0.4045863341463832,-0.28059738786475075,0.5258011235163312
716,71.60089478748797,0.7657753095648208,0.2800217439451116,1.0495539436835306
717,71.70089603719117,-0.608938223617164,0.5845450253301586,0.6738227763818094
718,71.80089728689435,-0.45441107328310054,0.8278207624607051,1.3435396204726144
719,71.90089853659755,-0.22059071431888283,0.5740741641549232,2.078786205781594
720,72.00089978630075,1.37893082513669,0.459777906253697,0.7424719517539324
721,72.10090103600395,0.27624380356950806,-1.0490339901174575,1.3800697348381523
722,72.20090228570714,-0.006479917935897768,-0.03217318749695747,0.9306580880978921
723,72.30090353541034,0.6230959095689119,-0.8828382097223103,1.2226816961148104
724,72.40090478511354,-0.11858245788290057,0.15411393261285042,0.549915388099111
725,72.50090603481672,-0.06888452959050327,0.4311009258155841,1.0006428332374706
726,72.60090728451992,0.4276976988943089,0.030605620775865865,1.85721108471748
727,72.70090853422312,-0.1313177081444161,-0.23528487992518837,1.539927178260934
728,72.80090978392631,-0.1769926389497063,0.3199056549349148,1.2111444642600586
729,72.90091103362951,0.14439050556642805,-0.17307119803740603,1.1575634802808306
730,73.00091228333271,0.5472047473894334,-0.47772098644216815,0.42033889172737515
731,73.10091353303591,0.12681712718467467,0.24607885828631818,0.23797665690840308
732,73.20091478273909,-0.312409120649845,0.7395410546306139,0.48065230713661944
733,73.30091603244229,0.11867672100079214,-0.7238467151953466,-0.06883007682350584
734,73.40091728214549,0.41235495065405914,-0.11140374593784724,-0.018589954933495578
735,73.50091853184868,-0.14450019900040656,0.9033619461182725,1.2249803761851807
736,73.60091978155188,0.37433543491628063,0.03683254235892005,1.0159804283504121
737,73.70092103125508,-0.15786318860112758,-0.34927989165163115,0.14076616504326056
738,73.80092228095828,-0.9655993979104917,-0.09276195510250342,0.3185135913530666
739,73.90092353066147,-0.6583501013521663,-0.10553546388525163,0.25556533603623255
740,74.00092478036466,0.2726019629567167,0.1484025248219597,-0.47131539956405466
741,74.10092603006785,0.265764039424273,-0.3476182594199317,0.06977063418831331
742,74.20092727977105,0.4436805603011194,0.16734480440723198,1.0789537979141874
743,74.30092852947425,-1.1422595588836437,0.39127219880267616,0.8776717137718741
744,74.40092977917745,0.1937192979547509,0.6793044242428534,1.1182755050289503
745,74.50093102888064,0.011858166988222868,-0.30488044984944696,0.38061115192162265
746,74.60093227858384,-1.0264098364115721,-0.501322581567479,0.263097332496123
747,74.70093352828702,0.298823506926967,-0.734726907306257,0.589029108143103
748,74.80093477799022,-0.45958261208893714,0.04300637261565212,0.7171139559071573
749,74.90093602769342,0.4535316579921512,0.16793496543504724,1.0721231694246913
750,75.00093727739662,-0.8907617931570191,-0.7866287333958089,0.6972994762411069
751,75.10093852709981,-0.9015722078337688,-0.37374676395264317,0.8499602519553506
752,75.20093977680301,-0.4078703152552693,0.4965001352769394,-0.2238341883217101
753,75.30094102650621,-0.6804406326504319,0.6836564923723312,0.5320957506406865
754,75.40094227620939,0.3440725104630058,0.313479293364427,0.5588734718829335
755,75.50094352591259,0.3659994671538331,-0.015061295050640995,0.16921583560659514
756,75.60094477561579,0.3418106270510686,0.3798837497871951,0.09607814662922914
757,75.70094602531898,-0.5397975503629162,0.6136218986882213,0.19921119077651916
758,75.80094727502218,-0.03209525629730518,-0.08654933145976647,0.15252301803117096
759,75.90094852472538,0.3753913319412422,-0.03343325705819428,0.5769152082232321
760,76.00094977442858,0.049292422364833915,-0.055679366489362114,1.0944188988798123
761,76.10095102413176,-0.3624621328187335,-0.4854975287610252,0.7497396178584249
762,76.20095227383496,-0.6547483942939636,-0.07300552328919546,1.056311471643954
763,76.30095352353815,-0.46611679684245816,0.0438120821089171,0.5421484429076272
764,76.40095477324135,0.46970427062821013,0.06317151696490808,0.1074013975213648
765,76.50095602294455,-0.3394499467892878,0.07326753307571482,0.4642410192738998
766,76.60095727264775,-0.3621811387530202,-0.20621106686790378,0.41344749390492685
767,76.70095852235094,-0.3517370026920056,-0.33144114157530863,0.6198963112265051
768,76.80095977205414,0.4542487820984304,0.24890732812422542,0.9074215306310168
769,76.90096102175733,0.6782016910986886,-0.16638812602982433,0.6235537782540058
770,77.00096227146052,-0.3331411239099514,-0.4630380751841084,-0.4246274577241226
771,77.10096352116372,0.8355111140277923,-0.11120113199691072,0.2667856222764599
772,77.20096477086692,-0.19954405649044907,0.04883307688715793,-0.09590555364613601
773,77.30096602057012,-0.2371702521063778,0.6480843324298861,-0.10723430481770718
774,77.40096727027331,0.16611984707937166,-0.14961980167408706,0.39026737647645204
775,77.50096851997651,-1.277101077609219,0.24329046481353941,0.5967838547027662
776,77.6009697696797,-0.06941932624932382,-0.2667018978303071,1.1373897319444792
777,77.70097101938289,0.18545152954518868,0.3276196373281439,0.729979554793672
778,77.80097226908609,-0.33444183510901687,0.3356627936259977,0.7058648354032979
779,77.90097351878929,0.2587792603439574,0.1714463402238103,-0.17284002961061384
780,78.00097476849248,0.7629397673208714,-0.1630139779621466,0.2286719358985636
781,78.10097601819568,-0.46426194299228757,0.49959023538149533,-0.29331993716684157
782,78.20097726789888,-0.9354816571217863,-0.56890654874712,0.5781627731053415
783,78.30097851760206,-0.6205904312464522,-0.2668291338170599,-0.004911404391120422
784,78.40097976730526,-0.08344642896792517,0.06036886868400358,0.08900268794848246
785,78.50098101700846,-0.9812815803793913,0.296030819106915,0.8084203100312299
786,78.60098226671165,0.198848476832813,-0.2826481052370207,0.4610846493952833
787,78.70098351641485,0.08410796590498229,-0.21215158798000183,-0.6089396682376487
788,78.80098476611805,1.0030888953545911,0.5086331716517443,0.03510491578238109
789,78.90098601582125,1.2807059533731155,-0.22329961185392486,0.8296183942490791
790,79.00098726552443,0.2420228208250635,-0.46722361045107874,1.1076127122750135
791,79.10098851522763,0.1611701478808601,-0.1391048484864442,-0.0018769222707197275
792,79.20098976493082,-0.15967216794150565,-0.08946105783648026,-0.04804283653484548
793,79.30099101463402,0.3347494252292377,-0.04575453293529026,-0.1311707016822389
794,79.40099226433722,0.39663285502001033,-0.1863688455457191,0.8766036333327843
795,79.50099351404042,-0.7210248338162627,0.30355899516984075,-0.25439841127342583
796,79.60099476374361,0.17939076645316943,-0.6599709153853344,0.6104415802833049
797,79.7009960134468,-0.6373175607194036,-0.08483888883495166,0.4436271191948594
798,79.80099726315,-0.36740665757463603,0.05267310623894388,-0.718992232713141
799,79.90099851285319,0.11345533536841455,0.22312406504863228,0.1710457769253053
800,80.00099976255639,0.41564925220141863,-0.26898545235060506,-0.27824493475586276
801,80.10100101225959,0.4701211757079769,-0.3538430873255347,-0.6153250562111855
802,80.20100226196278,0.2554734675336971,-0.4179288686956058,-0.06569707274874961
803,80.30100351166598,-0.5045475426943454,1.1484594383419897,0.4450448096961154
804,80.40100476136918,0.03313179018813345,0.13111315440622334,-1.1059585448116875
805,80.50100601107236,-0.7017272143967729,0.3919280978981487,0.564343783665294
806,80.60100726077556,0.1868656336521362,-0.13067023998781443,0.3296995781962917
807,80.70100851047876,-0.07329947815254696,-0.2943559875649734,1.3171102855266144
808,80.80100976018196,-0.1231136065632208,-0.24164682439618776,-0.2792168319377222
809,80.90101100988515,0.02821354425245753,0.5600332554930844,0.012572976267476027
810,81.00101225958835,-0.7337157296106005,0.23483084139035304,0.4870986271036642
811,81.10101350929155,0.8785645076156224,0.3385501315073869,0.8510686577554323
812,81.20101475899473,-0.7819537365362044,0.37787858796447493,-0.18701693986613954
813,81.30101600869793,-0.6825233063067725,0.0616159620968954,0.3057487913316246
814,81.40101725840113,-0.6238886331754103,-0.28055908651560574,0.17170766131113205
815,81.50101850810432,-0.24202813974612555,-0.004693932149262948,0.16660867212839178
816,81.60101975780752,-0.3452710347639048,0.3189194419953305,-0.39058252512499214
817,81.70102100751072,-0.03889230505562797,-0.48909573144162655,0.3737440953420331
818,81.80102225721392,-0.34870122089633077,-0.703554408959717,0.5552292046663747
819,81.9010235069171,0.6168933478142381,0.508508956365804,0.16473289386302353
820,82.0010247566203,39.96865852558703,15.031849639840617,2.315913167927773
821,82.1010260063235,39.6699096087505,13.846861070440418,2.842764377847977
822,82.20102725602669,39.540714590668074,14.449908100759131,2.7522574979183796
823,82.30102850572989,39.80122435027673,14.984521053879842,3.340443429737861
824,82.40102975543309,40.45250189417557,14.515677721812857,3.4204888527850765
825,82.50103100513628,40.195482779496665,14.583839644029906,2.73782957919928
826,82.60103225483947,39.711564399988895,14.09213651655843,2.264950290663088
827,82.70103350454266,39.94623440046725,14.591765602646113,2.991411396812392
828,82.80103475424586,40.499240797448145,13.559359058877295,4.232556029247068
829,82.90103600394906,39.948992057252575,13.914254245035282,3.5750955155811805
830,83.00103725365226,39.74000727015414,13.45910643414678,3.604069490676372
831,83.10103850335545,39.620688873660995,13.397536847321692,3.4457362193017103
832,83.20103975305865,39.97435655243045,13.688783267314284,3.325842760919984
833,83.30104100276183,40.08850231709025,14.070094492987792,3.4375699826538604
834,83.40104225246503,39.162492366944576,14.187490193745187,3.8220129102685965
835,83.50104350216823,39.63683986054727,13.447383284368648,3.839165422023397
836,83.60104475187143,39.07137150255819,12.560441838871858,4.012314834519034
837,83.70104600157462,39.47883320294523,12.392026323718932,4.027262977317451
838,83.80104725127782,40.547572961972534,11.843278869305513,4.0051671418163215
839,83.90104850098102,40.10600019274047,12.110955603974768,2.871997595378345
840,84.00104975068422,39.745517160641285,12.649496844353575,3.83505804998657
841,84.1010510003874,39.83525422053637,12.74980177089365,3.845105795820587
842,84.2010522500906,40.25754421307318,12.314598894325119,4.172070252900343
843,84.3010534997938,40.478879197514125,11.676242346442587,4.073103625357348
844,84.40105474949699,39.88125705276562,10.919867439005827,3.858936290168658
845,84.50105599920019,39.60450152377146,10.558063390274452,4.708467311423843
846,84.60105724890339,40.53528844616767,11.409323508024114,4.237211975926544
847,84.70105849860659,40.15017777557522,10.485363546099103,5.784312164052983
848,84.80105974830977,39.480906822261545,10.232685207143366,5.840457559275901
849,84.90106099801297,40.10219540279734,11.079942150565012,3.90175778161723
850,85.00106224771616,40.86433669146865,9.836285172500213,5.859485342627723
851,85.10106349741936,39.02482033040615,9.631308601597363,4.72027693867901
852,85.20106474712256,40.42203391447172,9.991575123263946,5.640268609950048
853,85.30106599682576,39.65807132910298,10.36411932814622,6.038685984356955
854,85.40106724652895,39.88966967920849,10.176405392081158,6.139765170197898
855,85.50106849623214,41.84637837666513,9.498982814433818,5.72160524046056
856,85.60106974593533,40.08585811840786,9.108156948203241,5.8159167361287984
857,85.70107099563853,40.09027128499287,9.292020998048693,6.224190387934614
858,85.80107224534173,40.822484211616604,9.004141025445191,6.10360889903453
859,85.90107349504493,39.92580490962565,9.309445304840075,6.7020396414222
860,86.00107474474812,40.00131553291941,9.359352539345586,5.642390497399868
861,86.10107599445132,40.342114992516336,9.162535378131214,7.128806118628466
862,86.2010772441545,40.2566101513145,8.18304501690423,7.5628779573454725
863,86.3010784938577,39.911010222816685,8.40322750236656,7.964605332746716
864,86.4010797435609,40.18511923773608,7.479479666911665,6.325995525082895
865,86.5010809932641,39.47935216621265,8.467519885317525,5.577491918128732
866,86.6010822429673,39.97907432068032,9.089633829374948,7.102769797619919
867,86.70108349267049,39.625124861183686,8.106697437339115,6.303500844167868
868,86.80108474237369,40.63537256696982,8.033758759649839,6.6474796648286185
869,86.90108599207687,39.447950675922236,7.351628525305455,7.415995777512524
870,87.00108724178007,39.663095583355954,7.101690697029932,8.153701716006557
871,87.10108849148327,39.4875596178007,7.385897659545492,7.583193255696913
872,87.20108974118646,39.91028318202084,7.526020374799852,7.609695301687982
873,87.30109099088966,39.937341759215016,6.502739119074776,8.164364321171622
874,87.40109224059286,39.49328557453016,6.892919062075386,8.069414970781724
875,87.50109349029606,39.88557275110081,6.264379529184375,8.485392089107618
876,87.60109473999925,39.40160558651665,5.98913624164597,9.376598682013814
877,87.70109598970244,40.56648709374098,5.80222232734601,8.591931105842944
878,87.80109723940564,39.27624806564488,5.872696891438236,8.386174818059747
879,87.90109848910883,40.03028780376013,6.43798813681838,9.775695213247204
880,88.00109973881203,39.67508495606067,5.761821500532165,8.18006213991412
881,88.10110098851523,40.3028734940109,6.487385518590558,8.916062848908918
882,88.20110223821843,40.259373746099826,6.136045372451032,9.505919042844287
883,88.30110348792162,40.25273908910426,5.368482597015908,9.405664539625889
884,88.4011047376248,40.74759180854924,4.820017848723196,9.97761950544062
885,88.501105987328,38.93085840872031,5.279760166069355,9.516692024633747
886,88.6011072370312,40.58861894362477,5.036083811744341,10.571104813416651
887,88.7011084867344,40.01810713394813,4.657598906000468,9.879500138633468
888,88.8011097364376,39.55334671758594,4.644409878322904,11.498924597735952
889,88.9011109861408,40.019650452412364,4.57137405528923,10.937971680721146
890,89.00111223584399,40.5561930054472,4.869802862705651,11.015770907814929
891,89.10111348554717,39.91547006398132,3.736439238934479,11.203855888802934
892,89.20111473525037,39.9824678234972,3.819725572805024,11.237175818899795
893,89.30111598495357,40.36313323405653,3.533061713191823,11.924804759433345
894,89.40111723465677,40.46205106269625,4.347134155311632,11.596685257382559
895,89.50111848435996,39.19710822865453,3.456486078700358,12.457705742069612
896,89.60111973406316,39.973538509919855,3.5790533298487515,11.834383630071843
897,89.70112098376636,39.61026895645267,3.566799571315048,13.141819639932221
898,89.80112223346954,39.73094201419819,3.746385904410462,12.669048128585235
899,89.90112348317274,40.3952911130965,3.4860458762382383,14.206992554473775
900,90.00112473287594,39.39799566759925,2.7674962530679315,13.669753622277142
901,90.10112598257913,38.76832119367951,2.8688194377897354,14.422852351497562
902,90.20112723228233,40.51697255424536,3.315539975257193,14.033736043971844
903,90.30112848198553,39.64829545705206,3.0026596064151403,13.627377060813505
904,90.40112973168873,39.513336335409434,2.866687224868529,13.849653086394609
905,90.50113098139192,39.51511528268643,1.9742161798843214,15.363565539948954
906,90.60113223109511,39.37051790555876,1.1414987089530515,14.488156758091131
907,90.7011334807983,40.912771003314994,1.4020053959792858,16.08856434380269
908,90.8011347305015,39.69524846083921,1.3923360135207756,16.124270842721835
909,90.9011359802047,40.1208492098407,2.3961451625931334,16.546133723444484
910,91.0011372299079,40.31523283026237,1.0956291980908048,16.06088533977718
911,91.1011384796111,38.876998729052595,1.5038810069941555,17.581356306682565
912,91.20113972931429,39.71289607418759,1.2465405176358006,16.31107756911515
913,91.30114097901748,40.194806476104105,2.170461200097316,17.97040565663285
914,91.40114222872067,40.37008799733154,1.1022940536330241,17.81863093693309
915,91.50114347842387,40.10850846712197,0.7568046335401319,17.591832080321446
916,91.60114472812707,40.07892570420404,-0.1998917042055387,18.724344290076004
917,91.70114597783027,40.51702171391384,0.159572868951673,19.610501881215065
918,91.80114722753346,39.864905502069334,0.4680633923000188,19.624993004276746
919,91.90114847723666,41.092034365265214,-0.05773601393018525,19.332770774549434
920,92.00114972693984,39.925761428809004,-1.1049893697118554,21.130300073802008
921,92.10115097664304,39.73427711336076,0.11274827014458731,19.550392123438236
922,92.20115222634624,39.37712958492115,-1.2150449797757483,20.104411477420243
923,92.30115347604944,39.9692005450302,0.4102073894951419,19.039638952297825
924,92.40115472575263,39.49108853946137,-0.19478636650591133,19.972356266479228
925,92.50115597545583,38.96774196809778,-0.4348077416062104,20.14685133663465
926,92.60115722515903,40.24415329373392,0.10241702291534771,20.452617911120644
927,92.70115847486221,40.08047563071153,0.22535164288913398,20.426778452102333
928,92.80115972456541,39.76736369659186,-0.4618401329369904,20.46325022867451
929,92.9011609742686,39.87241300794221,-0.3208141089785252,18.98139408784806
930,93.0011622239718,40.51521890329606,-0.19764434489791285,19.984343932267915
931,93.101163473675,40.021857587835825,-0.13250978917367584,19.848501322472973
932,93.2011647233782,40.30492464034387,0.7130697263524145,19.605513878255234
933,93.3011659730814,40.2917723424431,-0.39074797253740556,20.097467644131125
934,93.40116722278458,40.432584512336206,-0.8974390908674515,20.102429595853724
935,93.50116847248778,40.27799107203056,-0.12696625617927282,20.26766841798357
936,93.60116972219097,39.989588710102915,-1.3064332696559264,20.12229309180863
937,93.70117097189417,39.73664758026414,0.4495194662485125,19.5905046911846
938,93.80117222159737,40.125132525499,0.014566736761136227,19.882117375256158
939,93.90117347130057,40.305757959303826,-0.3206655342659407,19.834175871332025
940,94.00117472100376,40.01240504023484,-0.2340146607048009,20.13994259051019
941,94.10117597070696,38.767886467456755,-0.4125561275337808,20.08663447251454
942,94.20117722041014,39.09462308465794,-0.06401353762852006,19.70602464899434
943,94.30117847011334,39.28458606055149,-0.4616787541302383,20.392872030960856
944,94.40117971981654,40.30319235283127,-0.10014757121155941,21.080092576353792
945,94.50118096951974,39.31900998268223,-0.05426414321474121,20.435223245026272
946,94.60118221922293,38.85450252494595,-0.08569264562690133,20.225554707070028
947,94.70118346892613,39.68903015575324,0.21052132544709867,20.311051401239663
948,94.80118471862933,39.30000976099479,-1.0597448729472974,20.54525704859531
949,94.90118596833251,39.71414606408619,-0.8579833774024874,20.158528745029667
950,95.00118721803571,40.85318401289787,0.05271463078305758,19.99465141128703
951,95.10118846773891,40.38230278587799,-0.4806105313271299,19.7786056785518
952,95.2011897174421,39.29191211192522,0.5810395945873024,19.493863612127537
953,95.3011909671453,39.602967805607854,0.6851648453744501,18.99364954678785
954,95.4011922168485,40.28162975196367,0.015581428962603398,20.46375821772923
955,95.5011934665517,40.02007928944769,-0.6145815356530568,20.345453049084607
956,95.60119471625488,39.67006519165385,-0.5872861346004871,19.73257406957774
957,95.70119596595808,40.18631521318079,-0.9674134476742277,20.185558885519487
958,95.80119721566128,40.23729178784496,0.3310814745214145,19.594123621299758
959,95.90119846536447,40.10550227327129,-0.1470520784350978,19.295616738797303
960,96.00119971506767,40.25277133983536,0.33309630781757266,20.09633586756035
961,96.10120096477087,40.17072452744798,-0.6707449760435619,21.29742263485153
962,96.20120221447407,40.847820059802004,-0.18845184163877685,19.75244903150541
963,96.30120346417725,41.10098240809924,-0.37169941186413613,20.04573790799331
964,96.40120471388045,39.92372601842418,-0.20199538367931796,20.018252604378684
965,96.50120596358364,39.67726767866232,-1.5823839134086886,20.12738735065675
966,96.60120721328684,39.795456398479466,-0.622299116299538,20.088947109016157
967,96.70120846299004,39.893515317698096,0.1519399192505748,19.837280014972734
968,96.80120971269324,39.714860086936,0.2133243597610395,20.175694711490276
969,96.90121096239643,40.453977891922705,0.443692842704583,19.811361328288122
970,97.00121221209962,0.25719467217677366,-14.758931438107801,19.859257339032293
971,97.10121346180281,0.1222698716079941,-14.170943436668363,20.031356083232435
972,97.20121471150601,-0.03668056840769275,-13.984219205427591,19.00592785557164
973,97.30121596120921,0.3008646593048977,-13.629686543117677,18.870040464195345
974,97.4012172109124,0.31274143658657216,-12.839091613234926,18.597806908409733
975,97.5012184606156,0.4345709298872005,-12.590615902739549,18.489224516423068
976,97.6012197103188,-0.05733075314963223,-11.813934428083288,18.326098367940265
977,97.701220960022,-0.443047616409815,-10.960467209921966,17.42928016907922
978,97.80122220972518,0.15005242977101899,-11.230800287894745,16.590763041436396
979,97.90122345942838,0.5371850142064974,-11.133334218046464,16.870701686394515
980,98.00122470913158,0.5788572931838148,-10.606102367769589,16.0710520902649
981,98.10122595883477,-0.016571162388118642,-10.376490238416896,14.64078764244539
982,98.20122720853797,-0.17380739156439193,-9.400610778904062,15.229962271355435
983,98.30122845824117,-0.11660979004635448,-9.067693300584839,15.564238568108927
984,98.40122970794437,-0.7630924088159229,-9.160502408665906,14.637983888146563
985,98.50123095764755,-0.2736071722253269,-8.695557177748134,15.903964437363667
986,98.60123220735075,0.34569608007549585,-8.958765335654999,15.675629735235766
987,98.70123345705395,0.11389496727926525,-9.354660738813203,15.490467134468027
988,98.80123470675714,-0.3283527933117781,-7.692410306074707,13.801758105129826
989,98.90123595646034,-0.4079776331938477,-7.908062548715819,14.019587382221967
990,99.00123720616354,-0.4457138782317989,-7.304541339810423,13.735934510741059
991,99.10123845586673,0.06884301762777284,-7.720256759222734,12.233022410240158
992,99.20123970556992,0.5273926810223554,-7.198648964971571,13.259091772685496
993,99.30124095527312,0.6045587797307787,-6.4087386473825045,12.523562468128086
994,99.40124220497631,0.3181262404321561,-6.208616883100106,12.153179455978506
995,99.50124345467951,0.6701897860434355,-7.089418939998286,11.654264796928931
996,99.60124470438271,0.193483615353933,-6.295307386886263,11.561662901761082
997,99.7012459540859,-0.08374239441619283,-6.536883654496854,11.490671415460582
998,99.8012472037891,-0.8537507156592196,-6.051973823837041,10.903709082527277
...

This file has been truncated, please download it to see its full contents.

c_cpp_properties.json

Arduino
{
    "configurations": [
        {
            "name": "Mac",
            "includePath": [
                "/Users/poojan/Library/Arduino15/packages/esp8266/tools/**",
                "/Users/poojan/Library/Arduino15/packages/esp8266/hardware/esp8266/2.6.3/**",
                "/Applications/Arduino.app/Contents/Java/tools/**",
                "/Applications/Arduino.app/Contents/Java/hardware/arduino/avr/**",
                "/Users/poojan/anaconda/include/c++/v1",
                "C:\\Users\\Ranjith\\AppData\\Local\\Arduino15\\packages\\esp8266\\hardware\\esp8266\\2.6.3\\**",
                "C:\\Users\\Ranjith\\AppData\\Local\\Arduino15\\packages\\esp8266\\tools\\**"
            ],
            "forcedInclude": [
                "/Applications/Arduino.app/Contents/Java/hardware/arduino/avr/cores/arduino/Arduino.h"
            ],
            "macFrameworkPath": [
                "/System/Library/Frameworks",
                "/Library/Frameworks"
            ],
            "intelliSenseMode": "clang-x64",
            "compilerPath": "/Users/poojan/anaconda/bin/clang",
            "cStandard": "c11",
            "cppStandard": "c++17"
        },
        {
            "name": "Win32",
            "includePath": [
                "C:\\Users\\Ranjith\\AppData\\Local\\Arduino15\\packages\\esp8266\\tools\\**",
                "C:\\Users\\Ranjith\\AppData\\Local\\Arduino15\\packages\\esp8266\\hardware\\esp8266\\2.6.3\\**"
            ],
            "forcedInclude": []
        }
    ],
    "version": 4
}

gen_dataset.py

Arduino
import numpy as np
import matplotlib.pyplot as plt
import pandas as pd

# Exponential function
def exp_rise(time=10, max=40, shift=0, exp=0.2):
    mult=max-shift
    expt=[]
    t_arr = np.linspace(start=0, stop=time, num=time*10)
    expt_max = mult*np.exp(time*exp)/mult
    for t in t_arr:
        expt.append(shift+((mult*np.exp(t*exp))/expt_max))
    return expt

# Saturating Exponential function 
def exp_sat_rise(time=10, mult=20, shift = -20, exp=2):
    exp_sat =[]
    t_arr = np.linspace(start=0, stop=time, num=time*10)
    for t in t_arr:
            exp_sat.append(shift + mult*(1 - np.exp(-t/exp)))
    return exp_sat

def exp_sat_fall(time=10, mult=40, exp=5):
    exp_sat =[]
    t_arr = np.linspace(start=0, stop=time, num=time*10)
    for t in t_arr:
        exp_sat.append(mult*(np.exp(-t/exp)))
    return exp_sat

# Ramp Increment function
def ramp(time=10, left=5, right=40):
    ramp = []
    slope = (right-left)/time
    t_arr = np.linspace(start=0, stop=time, num=time*10)
    for t in t_arr:
        ramp.append(left + (t*slope))
    return ramp

# Square Function
def square (time=10,val=40):
    sqr = []
    t_arr = np.linspace(start=0, stop=time, num=time*10)
    for t in t_arr:
        sqr.append(val)
    return sqr

# Noise Function
def add_gauss_noise(arr,amp=0.5):
    noise = amp*np.random.normal(size=len(arr))
    arr = arr + noise
    return arr

def add_time(time):
    return np.linspace(start=0, stop=time, num=time*10)
    


##### VOLUME MODE #####
time=[]
pressure=[]
flow=[]
volume=[]
tot_time=0

##2sec
tot_time+=2
pressure.extend(square(2,0))
flow.extend(square(2,0))
volume.extend(square(2,0))

for j in range (200):
    ##15sec
    tot_time+=15
    pressure.extend(ramp(15,5,40))
    flow.extend(square(15,15))
    volume.extend(ramp(15,0,20))
    
    ##2sec
    tot_time+=2
    pressure.extend(square(2,35))
    flow.extend(square(2,0))
    volume.extend(square(2,20))
    
    ##25sec
    tot_time+=25
    pressure.extend(exp_sat_fall(25,35))
    flow.extend(exp_sat_rise(25,15,-15))
    volume.extend(exp_sat_fall(25,20))

##total_time=86sec
time.extend(add_time(tot_time))


pressure = add_gauss_noise(pressure)
flow = add_gauss_noise(flow)
volume = add_gauss_noise(volume)


vol_mod_fig, (pre, flo, vol) = plt.subplots(3)
vol_mod_fig.suptitle('Volume Mode')
pre.plot(time,pressure)
flo.plot(time,flow)
vol.plot(time,volume)

vol_mode_df = pd.DataFrame(
    {'Time': time,
     'Pressure': pressure,
     'Flow': flow,
     'Volume': volume
    })

vol_mode_df.to_csv(r'/Users/saumilgogri/reSPIRE_proj/devPost/dataset/Volume_Mode.csv')

##### PRESSURE MODE #####


time=[]
pressure=[]
flow=[]
volume=[]
tot_time=0

##2sec
tot_time+=2
pressure.extend(square(2,0))
flow.extend(square(2,0))
volume.extend(square(2,0))

for j in range (200):
    ##15sec
    tot_time+=15
    pressure.extend(square(15,40))
    flow.extend(ramp(10,15,0))
    flow.extend(square(5,0))
    volume.extend(exp_rise(10,20))
    volume.extend(square(5,20))
      
    ##25sec
    tot_time+=25
    pressure.extend(square(25,0))
    flow.extend(exp_sat_rise(15,15,-15,3))
    flow.extend(square(10,0))
    volume.extend(exp_sat_fall(25,20))

##total_time=86sec
time.extend(add_time(tot_time))


pressure = add_gauss_noise(pressure)
flow = add_gauss_noise(flow)
volume = add_gauss_noise(volume)

pres_mode_df = pd.DataFrame(
    {'Time': time,
     'Pressure': pressure,
     'Flow': flow,
     'Volume': volume
    })
pres_mode_df.to_csv(r'/Users/saumilgogri/reSPIRE_proj/devPost/dataset/Pressure_Mode.csv')


pre_mode_fig, (pre, flo, vol) = plt.subplots(3)
pre_mode_fig.suptitle('Pressure Mode')
pre.plot(time,pressure)
flo.plot(time,flow)
vol.plot(time,volume)

nextion_write.ino

Arduino
#include <SoftwareSerial.h>

SoftwareSerial mySerial(10, 11); /*Even though you can use the hardware serial port in this case I think it is better to
  leave the hardware serial open for debugging purposes*/

void setup() {
  // put your setup code here, to run once:
  pinMode(0, INPUT); //This is our analog input pin

  Serial.begin(57600); //open the hardware serial port
  while (!Serial) { // wait for serial port to connect. Needed for native USB port only
    ;
  }

  Serial.println("Serial On"); //Print this messages when the serial port is connected
  mySerial.begin(9600); // set the data rate for the SoftwareSerial port
}

void loop() {
  String sendThis = ""; //Declare and initialise the string we will send

  delay(300); //Probably unneccessary, but I give the screen some time to respond
  sendThis = "n0.val="; //Build the part of the string that we know
  sendThis.concat(analogRead(0)); //Add the variable we want to send
  writeString(sendThis); /*Use a function to write the message character by character to the Nextion because
  mySerial.write(sendThis) gives you an error due to a datatype mismatch*/
}

//NOTE: A great big thanks to: RamjetX for writing this function. You can find his/her post here: http://forum.arduino.cc/index.php?topic=89143.0. Please go give him/her some Karma!
void writeString(String stringData) { // Used to serially push out a String with Serial.write()

  for (int i = 0; i < stringData.length(); i++)
  {
    mySerial.write(stringData[i]);   // Push each char 1 by 1 on each loop pass  
  }

  mySerial.write(0xff); //We need to write the 3 ending bits to the Nextion as well
  mySerial.write(0xff); //it will tell the Nextion that this is the end of what we want to send.
  mySerial.write(0xff);

}// end writeString function

nextion_2_pages.HMI

HAML
No preview (download only).

nextion_2_pages.tft

Textile
No preview (download only).

nextion_lcd_functions.ino

Arduino
mit(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
  p_mask = map(pressure_mask, 5.00, 20.00, 0, 255);
  p_expiration = map(pressure_mask, 5.00, 20.00, 0, 255);
  p_diff = map(pressure_mask, 5.00, 20.00, 0, 255);
  String to_send_p_mask = ad + id_1 + "," + ch + "," + int(p_mask);
  print_screen(to_send_p_mask);
  String to_send_p_diff = ad + id_2 + "," + ch + "," + int(p_diff);
  print_screen(to_send_p_diff);
  String to_send_p_exp = ad + id_1 + "," + ch + "," + int(p_expiration);
  print_screen(to_send_p_exp);
  dtostrf(BPM, 6, 2, buffer);
  t0.setText(buffer);
  dtostrf(IE_ratio,6,2,buffer_2);
  t1.setText(buffer_2);
  dtostrf(TidVol,6,2,buffer_2);
  t1.setText(buffer_3);
}


void print_screen(String to_send){
  Serial.print(to_send);
  Serial.write(0xff);
  Serial.write(0xff);
  Serial.write(0xff);
}

nextion_test.ino

Arduino
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <Nextion.h>
#include "NexButton.h"

//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

Servo servoright;
int pos = 0;   

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
//int inPin = 4;

// Declare your Nextion objects - Example (page id = 0, component id = 1, component name = "b0") 
NexText t_mode = NexText(0, 9, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");
NexButton b2 = NexButton(0, 4, "b2");
NexText t3 = NexText(1, 5, "t3");
NexText t4 = NexText(1, 6, "t4");
NexText t5 = NexText(1, 7, "t5");
NexText t_ie_ratio = NexText(0, 10, "t_ie_Ratio");
NexText t_bpm = NexText(0, 11, "t_bpm");
NexText t_tidvol = NexText(0, 12, "t_tidvol");
String set_mode = "";

NexTouch *nex_listen_list[] = {&b0,&b1,&b2,NULL};

void b0PopCallback(void *ptr) {
  t_mode.setText("MODE : ACV");
  set_mode = "acv";
  Serial.println(set_mode);
  //acv_mode();
  
}

void b1PopCallback(void *ptr) {
  t_mode.setText("MODE : SIMV");
  //simv_mode();
  set_mode = "simv"; 
  
}

void b2PopCallback(void *ptr) {
  t_mode.setText("MODE : None");
  //no_mode();
  set_mode = "None"; 
  Serial.println(set_mode);
}



// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(9600); //enable SUART Port for communication with NODEMCU
  nexInit();

  // Register the pop event callback function of the components
  b0.attachPop(b0PopCallback, &b0);
  b1.attachPop(b1PopCallback, &b1);
  b2.attachPop(b2PopCallback, &b2);
  
}



void loop()
 
{ nexLoop(nex_listen_list);
  
/*   if (set_mode == "simv")
  {
      while(set_mode=="simv")
      {
        simv_mode();
      }
  }
  else 
  {   while(set_mode == "acv")
      {
        acv_mode();  
      }
      
  } */
}


// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(set_mode == "acv")
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }
      print_to_screen(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(set_mode == "simv")
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
      }
      print_to_screen(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}

// =====================
// Transmit to DB
// =====================




// =====================
// Print to Screen
// =====================
void print_to_screen(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
  static char ps_diff[6];
  dtostrf(pressure_diff, 6, 2, ps_diff);
  static char ps_exp[6];
  dtostrf(pressure_expiration, 6, 2, ps_exp);
  static char ps_mask[6];
  dtostrf(pressure_expiration, 6, 2, ps_exp);
  t3.setText(ps_diff);
  t4.setText(ps_exp);
  t5.setText(ps_mask);
  static char ie_ratio[6];
  dtostrf(IE_ratio, 6, 2, ie_ratio);
  t_ie_ratio.setText(ie_ratio);
  static char bpm[6];
  dtostrf(BPM, 6, 2, bpm);
  t_bpm.setText(bpm);
  static char tidvol[6];
  dtostrf(TidVol, 6, 2, tidvol);
  t_tidvol.setText(tidvol);
}

maulik_test.ino

Arduino
#include <Servo.h>

Servo servoright;

void setup() {
  // put your setup code here, to run once:
servoright.attach(9);  // attaches the servo on pin 9 to the servo object
}

void loop() {
  // put your main code here, to run repeatedly:
  int pos;
  for(pos = 0; pos <= 90; pos += 1) // goes from 0 degrees to 180 degrees
    {                                  // in steps of 1 degree
      servoright.write(pos);
      delay(10);                       
  
      // ============ Update pressure valu
      //Serial.println(pressure_diff);
      //Serial.println(pressure_expiration);
    }
  delay(3000);
   for(pos = 90; pos >= 0; pos -= 1) // goes from 0 degrees to 180 degrees
    {                                  // in steps of 1 degree
      servoright.write(pos);
      delay(10);                       
  
      // ============ Update pressure valu
      //Serial.println(pressure_diff);
      //Serial.println(pressure_expiration);
    }
    delay(3000);
}

uno_simv_acv_json_series_firebase.ino

Arduino
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include "Nextion.h"

//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

Servo servoright;
int pos = 0;   

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int mode;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


// ======= JSON For storing data =========
String message = "";
boolean messageReady = false;
int obj_number = 1;
const int send_doc_capacity = JSON_ARRAY_SIZE(10) + 2*JSON_OBJECT_SIZE(7);
StaticJsonBuffer<send_doc_capacity> send_doc_json_buffer;
JsonArray& arr = send_doc_json_buffer.createArray();

void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(9600); //enable SUART Port for communication with NODEMCU
//  attachInterrupt(0, pin_ISR, CHANGE);
}
 
void loop()
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
        while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
        transmit(message);
      }
  }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();
        while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
        transmit(message);
      }  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }
      make_json(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
      
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
      }
      make_json(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}

// =====================
// Transmit to DB
// =====================

void transmit(String message){
      // The only messages we'll parse will be formatted in JSON
      const int capacity = JSON_OBJECT_SIZE(2);
      StaticJsonBuffer<capacity> jb;
      JsonObject& doc = jb.parseObject(message);
      //DynamicJsonDocument doc(1024); // ArduinoJson version 6+
      // Attempt to deserialize the message
      if(!(doc.success())){
        Serial.println("Doc conversion failed");
        messageReady = false;
        doc["type"] = "incorrect";
      }
      if(doc["type"] == "request") { 
        arr.printTo(SUART);
        send_doc_json_buffer.clear();
      }
      }



// =====================
// Make the JSON
// =====================

void make_json(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
  JsonObject& obj = send_doc_json_buffer.createObject();
  obj["type"] = "response";
  obj["BPM"] = BPM;
  obj["IE_ratio"] = IE_ratio;
  obj["pressure_mask"] = pressure_mask;
  obj["pressure_expiration"] = pressure_expiration;
  obj["TidVol"] = TidVol;
  obj["pressure_diff"] = pressure_diff;
  arr.add(obj);
  obj.remove("type");
  obj.remove("TidVOl");
  obj.remove("pressure_expiration");
  obj.remove("pressure_mask");
  obj.remove("IE_ratio");
  obj.remove("BPM");
  
}

nodemcu_simv_acv_json_series_firebase.ino

Arduino
#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif
#include <ArduinoJson.h>
#include <Wire.h>
#include <FirebaseArduino.h>
#include <NTPClient.h>
#include <WiFiUdp.h>

#include<SoftwareSerial.h>
SoftwareSerial SUART(4, 5); //SRX=Dpin-D2; STX-DPin-D1

#define FIREBASE_HOST "respire-447da.firebaseio.com"
#define FIREBASE_AUTH "vsloiSErdIEyQMV6ydzwaELOPVSP5dPqiOobAURm"
#define NTP_OFFSET   60 * 60      // In seconds
#define NTP_INTERVAL 60 * 1000    // In miliseconds
#define NTP_ADDRESS  "europe.pool.ntp.org"

WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP, NTP_ADDRESS, NTP_OFFSET, NTP_INTERVAL);

//=======================================
unsigned long time_1;
bool test_2;
String last_char = "}";
time_t t;

// Replace with your network credentials
const char* ssid     = "NETGEAR43";
const char* password = "smilingnest196";  

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "http://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "San Diego";

void setup() {
  Serial.begin(9600); //enable Serial Monitor
  SUART.begin(9600); //enable SUART Port
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
  Firebase.begin(FIREBASE_HOST, FIREBASE_AUTH);
  Serial.println("Connected to Firebase");
  timeClient.begin();
}

void loop() {
  timeClient.update();
  const int capacity = JSON_OBJECT_SIZE(1);
  StaticJsonBuffer<capacity> jb;
  JsonObject& doc = jb.createObject();
  doc["type"] = "request";
  String message = "";
  String test = "";
  boolean messageReady = false;
  doc.printTo(test);
  Serial.println(test);
  doc.printTo(Serial);
  doc.printTo(SUART);
  SUART.println(test);
  while(messageReady == false) { // blocking but that's ok
    if(SUART.available()) {
      message = SUART.readString();
      Serial.println("message was received");
      Serial.println(message);
      test_2 = message.endsWith(last_char);
      Serial.println(test_2);
      if (!(test_2)){
        return;
      }
      messageReady = true;
    }
  }
  send_data(message);
  delay(3000);
  }
  

//======================================


void send_data(String message) {
const int capacity = JSON_ARRAY_SIZE(10)+ 15*JSON_OBJECT_SIZE(7);
StaticJsonBuffer<capacity> jb;
JsonArray& doc = jb.parseArray(message);
if(WiFi.status()== WL_CONNECTED){
    String time_now = timeClient.getFormattedTime();
    Serial.println(time_now);
    //doc["send_time"] = time_now;
    String message_fb = "";
    doc.printTo(message_fb);
    Firebase.pushString(time_now, message_fb);
    Serial.println(message_fb);
    if(Firebase.success()){
    Serial.println("The push was successful");  
    }
    else
    {
      Serial.println("The push to Firebase failed");
    }
    
}}

test.ino

Arduino
#include "Queue.h"

Queue<char> queue = Queue<char>(5);

void setup() {
  Serial.begin(9600);
}

void loop() {

    queue.push("1");

  Serial.print(millis() / 1000);
  Serial.print(": ");
  int count = queue.count();
  if (count > 0) {
    Serial.print("Found ");
    Serial.print(count);
    Serial.print(" items.. '");
    Serial.print(int(queue.pop()));
    Serial.print("' is the oldest. We are ");
    Serial.print(queue.front());
    Serial.print(" in front and ");
    Serial.print(queue.back());
    Serial.print(" in back. Next is.. '");
    Serial.print(queue.peek());
    Serial.println("'.");
  } else {
    Serial.println("Nothing to process..."); 
  }
  delay(2000);
}

vent_3controls.ino

Arduino
#include <Guino.h>

#include <Servo.h>
 
Servo servoright;
int pos = 0;    

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float valIE_ratio;  
float valTidVol;  
float valBPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_valBPM;
int display_valTidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;



void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
}
 
void loop()
 
{
  // ** Main update call for the guino
  //guino_update();
  // ========== Read all analog input =============
  pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
  pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
  pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
  valIE_ratio = analogRead(potpinIE_ratio);            // reads the value of the potentiometer (value between 0 and 1023)
  valIE_ratio = map(valIE_ratio, 0, 1023, 1.00, 4.00);     // scale it to use it with the servo (value between 0 and 180)
  valTidVol = analogRead(potpinTidVol);            // reads the value of the potentiometer (value between 0 and 1023)
  valTidVol = map(valTidVol, 0, 1023, 40.00, 90.00);     // scale it to use it with the servo (value between 0 and 180)
  valBPM = analogRead(potpinBPM);            // reads the value of the potentiometer (value between 0 and 1023)
  valBPM = map(valBPM, 0, 1023, 8.00, 30.00);     // scale it to use it with the servo (value between 0 and 180)
 
  // ====== Copmute respiration separation time based on pot inputs ==========
  separation = 60/valBPM - (1+valIE_ratio);
  if (separation < 0)
  {
    valIE_ratio = 60/valBPM - 1;
    separation = 60/valBPM - (1+valIE_ratio);
  }

  // ========= Servo a-Clockwise motion =============
  for(pos = 30; pos <= valTidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/valTidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    Serial.println(pressure_diff);
    Serial.println(pressure_expiration);
  }
  delay(15);
  
  // ========= Servo Clockwise motion ============
  for(pos = valTidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*valIE_ratio/valTidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    Serial.println(pressure_diff);
    Serial.println(pressure_expiration);
  }  
  delay(separation*1000);
}

test/Queue.h

Arduino
/*
 * Queue.h
 * 
 * By Steven de Salas
 * 
 * Defines a templated (generic) class for a queue of things.
 * Used for Arduino projects, just #include "Queue.h" and add this file via the IDE.
 * 
 * Examples:
 * 
 * Queue<char> queue(10); // Max 10 chars in this queue
 * queue.push('H');
 * queue.push('e');
 * queue.count(); // 2
 * queue.push('l');
 * queue.push('l');
 * queue.count(); // 4
 * Serial.print(queue.pop()); // H
 * Serial.print(queue.pop()); // e
 * queue.count(); // 2
 * queue.push('o');
 * queue.count(); // 3
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // l
 * Serial.print(queue.pop()); // o
 * 
 * struct Point { int x; int y; }
 * Queue<Point> points(5);
 * points.push(Point{2,4});
 * points.push(Point{5,0});
 * points.count(); // 2
 * 
 */

#ifndef QUEUE_H
#define QUEUE_H

#include <Arduino.h>

template<class T>
class Queue {
  private:
    int _front, _back, _count;
    T *_data;
    int _maxitems;
  public:
    Queue(int maxitems = 256) { 
      _front = 0;
      _back = 0;
      _count = 0;
      _maxitems = maxitems;
      _data = new T[maxitems + 1];   
    }
    ~Queue() {
      delete[] _data;  
    }
    inline int count();
    inline int front();
    inline int back();
    void push(const T &item);
    T peek();
    T pop();
    void clear();
};

template<class T>
inline int Queue<T>::count() 
{
  return _count;
}

template<class T>
inline int Queue<T>::front() 
{
  return _front;
}

template<class T>
inline int Queue<T>::back() 
{
  return _back;
}

template<class T>
void Queue<T>::push(const T &item)
{
  if(_count < _maxitems) { // Drops out when full
    _data[_back++]=item;
    ++_count;
    // Check wrap around
    if (_back > _maxitems)
      _back -= (_maxitems + 1);
  }
}

template<class T>
T Queue<T>::pop() {
  if(_count <= 0) return T(); // Returns empty
  else {
    T result = _data[_front];
    _front++;
    --_count;
    // Check wrap around
    if (_front > _maxitems) 
      _front -= (_maxitems + 1);
    return result; 
  }
}

template<class T>
T Queue<T>::peek() {
  if(_count <= 0) return T(); // Returns empty
  else return _data[_front];
}

template<class T>
void Queue<T>::clear() 
{
  _front = _back;
  _count = 0;
}

#endif

arduino_lcd.ino

Arduino
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <SPI.h>
#include <SD.h>
#include <Nextion.h>

// ==== Analog Pins =====
float potpinIE_ratio = 0;
int potpinTidVol = 1;
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ===== Other vars ======
float check_value;
float IE_ratio;
float TidVol;
float BPM;
float separation;
float sensorvalue;
//float pressure_mask;
//float pressure_expiration;
//float pressure_diff;

//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

//====== LCD Variables ==============
int id_1 = 5;
int ch = 0;
int id_2 = 4;
int id_3 = 3;
String ad = "add ";
static char buffer[10] = {};
static char buffer_2[10] = {};
static char buffer_3[10] = {};
static char buffer_mode[10] = {};
String set_mode = "ACV";
NexText t_ie_ratio = NexText(0, 8, "t_ie_ratio");
NexText t_bpm = NexText(0, 9, "t_bpm");
NexText t_tidvol = NexText(0, 10, "t_tidvol");
NexText t_mode = NexText(0, 12, "t_mode");
NexButton b0 = NexButton(0, 2, "b0");
NexButton b1 = NexButton(0, 3, "b1");

float pressure_mask = 4.55;
float pressure_diff = 5.55;
float pressure_expiration = 6.55;
      
NexTouch *nex_listen_list[] = {&b0, &b1, NULL};


void b0PopCallback(void *ptr) {
  set_mode = "ACV";
  //set_mode.toCharArray(buffer_mode,5);
  t_mode.setText(set_mode.c_str());
}

//Button b1 component popcallback function
// When OFF button is released the LED turns OFF and the state text changes

void b1PopCallback(void *ptr) {
  set_mode = "SIMV";
  t_mode.setText(set_mode.c_str());
}


// ==== Sensor Offset =====
const float guageSensorOffset = 41;

const float pressureDiffSensorOffset = 41;

//===== Variables =====
Servo servoright;
int pos = 0;

//======= SD Card File ===========
File myFile;

String mode = "";

void setup() {
  Serial.begin(9600);
  SUART.begin(9600);
  servoright.attach(9);
  pinMode(10, OUTPUT);
  if (!SD.begin(4)) {
   Serial.println("initialization failed!");
   return;
  }
  Serial.println("SD Card Initialization done.");
  nexInit();
  b0.attachPop(b0PopCallback, &b0);
  b1.attachPop(b1PopCallback, &b1);

}

void loop() {
  // put your main code here, to run repeatedly:
    myFile = SD.open("example.txt", FILE_WRITE);
    if(myFile){
      Serial.println("The file is open");
      myFile.close();
    }
    else
    {
      Serial.println("Error opening this file");
      myFile.close();
      }
    // Run ventilator
    send_to_screen_values(BPM, IE_ratio, TidVol);
    if (set_mode == "ACV") {
    myFile = SD.open("example.txt", FILE_WRITE);
    acv_mode();
    myFile.close();
  }
  else if (set_mode == "SIMV") {
    myFile = SD.open("example.txt", FILE_WRITE);
    simv_mode();
    myFile.close();
  }
    
}

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "ACV";


  // Fetch all potentiometer values
  IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);
  TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);
  BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);
  separation = (60 / BPM - (1 + IE_ratio));
  if (separation < 0)
  { IE_ratio = 60 / BPM - 1;
    separation = 60 / BPM - (1 + IE_ratio);
  }

  // Fetch pressure sensor values
  pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset) * 10.1972 / 92;
  pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset) * 10.1972 / 92;
  pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset) * 10.1972 / 92;
  // Initiate the cycle
  if (firstRun)
  {
    inspiration(TidVol, mode);
    delay(15);
    cycleEndTime = expiration(TidVol, IE_ratio, mode);
    firstRun = false;
  }

  // ========= Identify trigger and initiate the cycle =============
  if (millis() - cycleEndTime >= (uint32_t)separation * 1000 || pressure_mask < -1)
  {
    inspiration(TidVol, mode);
    delay(15);
    cycleEndTime = expiration(TidVol, IE_ratio, mode);
  }
  send_to_screen_values(BPM, IE_ratio, TidVol);
}

void inspiration(float TidVol, String mode)
{
  int pos;
  for (pos = 30; pos <= TidVol + 30; pos += 2) // goes from 0 degrees to 180 degrees
  {
    
    servoright.write(pos);
    delay(1000 / TidVol);

    // ============ Update pressure values =========
    //pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
    //pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
    //pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      String data = mode + "," + String(pressure_mask) + "," + String(pressure_diff) + "," + String(pressure_expiration) + ";";
      myFile.println(data);
      send_to_screen_graph(pressure_mask, pressure_expiration, pressure_diff);
      //send_to_screen_values(BPM, IE_ratio, TidVol);
      //nexLoop(nex_listen_list);
  }
  transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio, String mode)
{
  for (pos = TidVol + 30; pos >= 30; pos -= 2) // goes from 180 degrees to 0 degrees
  { 
    //nexLoop(nex_listen_list);
    servoright.write(pos);
    delay(1000 * IE_ratio / TidVol);
    // ============ Update pressure values =========
    //pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
    //pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
    //pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      //Serial.println("Here inside inspiration");
      String data = mode + "," + String(pressure_mask) + "," + String(pressure_diff) + "," + String(pressure_expiration) + ";";
      myFile.println(data); 
      send_to_screen_graph(pressure_mask, pressure_expiration, pressure_diff);
      //send_to_screen_values(BPM, IE_ratio, TidVol);
  }
  transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  return millis();
}

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "SIMV";
  // Fetch all potentiometer values
  IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);
  TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);
  BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);
  separation = (60 / BPM - (1 + IE_ratio));
  if (separation < 0)
  { IE_ratio = 60 / BPM - 1;
    separation = 60 / BPM - (1 + IE_ratio);
  }
  // Fetch pressure sensor values
  pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset) * 10.1972 / 92;
  pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset) * 10.1972 / 92;
  pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset) * 10.1972 / 92;


  // Initiate the cycle
  if (firstRun)
  {
    pressure_mask = average_pressure_mask();
    cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
    firstRun = false;
  }

  // ========= Identify trigger and initiate the cycle =============
  if (millis() - cycleEndTime >= (uint32_t)separation * 1000 || average_pressure_mask() < -1)
  {
    pressure_mask = average_pressure_mask();
    cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
  }
  send_to_screen_values(BPM, IE_ratio, TidVol);
}


// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio, String mode)
{
  uint32_t cycleEndTime;
  pressure_mask = int(floor(pressure_mask));
  switch (int(pressure_mask)) {
    case -6:
    case -5:
    case -4:
      TidVol = TidVol * 0.25;
      inspiration(TidVol, mode);
      delay(15);
      cycleEndTime = expiration(TidVol, IE_ratio, mode);
      break;
    case -3:
      TidVol = TidVol * 0.50;
      inspiration(TidVol, mode);
      delay(15);
      cycleEndTime = expiration(TidVol, IE_ratio, mode);
      break;
    case -2:
      TidVol = TidVol * 0.75;
      inspiration(TidVol, mode);
      delay(15);
      cycleEndTime = expiration(TidVol, IE_ratio, mode);
      break;
    case -1:
      TidVol = TidVol * 0.75;
      inspiration(TidVol, mode);
      delay(15);
      cycleEndTime = expiration(TidVol, IE_ratio, mode);
      break;
    default:
      inspiration(TidVol, mode);
      delay(15);
      cycleEndTime = expiration(TidVol, IE_ratio, mode);
      break;
  }
  return cycleEndTime;
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
  pressure_mask = 0;
  for (int i = 0; i < 5; i++)
  {
    pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset) * 10.1972 / 92;
    delay(3);
  }
  return (pressure_mask/5);
}


// =====================
// Print to Screen
// =====================

void send_to_screen_graph(float pressure_mask, float pressure_expiration, float pressure_diff) {
  float p_mask = map(pressure_mask, 5.00, 20.00, 0, 255);
  float p_expiration = map(pressure_mask, 5.00, 20.00, 0, 255);
  float p_diff = map(pressure_mask, 5.00, 20.00, 0, 255);
  String to_send_p_mask = ad + id_1 + "," + ch + "," + int(p_mask);
  print_screen(to_send_p_mask);
  String to_send_p_diff = ad + id_2 + "," + ch + "," + int(p_diff);
  print_screen(to_send_p_diff);
  String to_send_p_exp = ad + id_3 + "," + ch + "," + int(p_expiration);
  print_screen(to_send_p_exp);
}

void send_to_screen_values(float BPM, float IE_ratio, float TidVol) {
  dtostrf(BPM, 6, 2, buffer);
  t_bpm.setText(buffer);
  dtostrf(IE_ratio, 6, 2, buffer_2);
  t_ie_ratio.setText(buffer_2);
  dtostrf(TidVol, 6, 2, buffer_3);
  t_tidvol.setText(buffer_3);
  t_mode.setText(set_mode.c_str());
}

void print_screen(String to_send) {
  Serial.print(to_send);
  Serial.print("\xFF\xFF\xFF");
}


// =====================
// Transmit to DB
// =====================

void transmit(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
      Serial.println("Inside the transmit function");
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      // The only messages we'll parse will be formatted in JSON
      
      const int capacity_data = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity_data> jb_data;
      JsonObject& doc = jb_data.createObject();
      doc["type"].set("response");
      doc["BPM"].set(BPM);
      doc["IE_ratio"].set(IE_ratio);
      doc["pressure_mask"].set(pressure_mask);
      doc["pressure_expiration"].set(pressure_expiration);
      doc["TidVol"].set(TidVol);
      doc["pressure_diff"].set(pressure_diff);
      doc.printTo(SUART);
      doc.printTo(Serial);
      }
      }

      

nodemcu_code.ino

Arduino
#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif
#include <ArduinoJson.h>
#include <Wire.h>
#include <FirebaseArduino.h>
#include <NTPClient.h>
#include <WiFiUdp.h>

#include<SoftwareSerial.h>
SoftwareSerial SUART(4, 5); //SRX=Dpin-D2; STX-DPin-D1

#define FIREBASE_HOST "respire-447da.firebaseio.com"
#define FIREBASE_AUTH "vsloiSErdIEyQMV6ydzwaELOPVSP5dPqiOobAURm"
#define NTP_OFFSET   60 * 60      // In seconds
#define NTP_INTERVAL 60 * 1000    // In miliseconds
#define NTP_ADDRESS  "europe.pool.ntp.org"

WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP, NTP_ADDRESS, NTP_OFFSET, NTP_INTERVAL);

//=======================================
unsigned long time_1;
bool test_2;
String last_char = "]";
time_t start_time;
//const byte numChars = 300;
//char receivedChars[numChars];   // an array to store the received data

// Replace with your network credentials
const char* ssid     = "NETGEAR28";
const char* password = "bluesky089";  

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "http://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "San Diego";

boolean newData = false;

void setup() {
  Serial.begin(9600); //enable Serial Monitor
  SUART.begin(9600); //enable SUART Port
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
  Firebase.begin(FIREBASE_HOST, FIREBASE_AUTH);
  Firebase.setFloat("test_number", 42.0); 
  Serial.println("Connected to Firebase");
  
  timeClient.begin();
}

void loop() {
  timeClient.update();
  const int capacity = JSON_OBJECT_SIZE(1);
  StaticJsonBuffer<capacity> jb;
  JsonObject& doc = jb.createObject();
  doc["type"] = "request";
  String message = "";
  String test = "";
  boolean messageReady = false;
  doc.printTo(SUART);
  start_time = millis();
  while(messageReady == false) { // blocking but that's ok
      message = SUART.readString();
      Serial.println("message was received");
      if(message == ""){
        return;
      }
      messageReady = true;
    }
  send_data(message);
  jb.clear();
  delay(1000);
  }
  

//======================================


void send_data(String message) {
if(WiFi.status()== WL_CONNECTED){
    String time_now = timeClient.getFormattedTime();
    Firebase.setString(time_now, message);
    Serial.println(message);
    Serial.println("The string was pushed");
}}

vent_3controls_mode.ino

Arduino
#include <Servo.h>
 
Servo servoright;
int pos = 0;    

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins =====

int inPin = 2;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float valIE_ratio;  
float valTidVol;  
float valBPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_valBPM;
int display_valTidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int reading;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
}
 
void loop()
 
{
  // ** Main update call for the guino
  //guino_update();
  // ========== Read all analog input & Detecting Mode Settings =============
  pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
  pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
  pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
  if (reading == HIGH && previous == LOW && millis() - time > debounce) {
    if (state == HIGH){ 
		valIE_ratio = analogRead(potpinIE_ratio);            // reads the value of the potentiometer (value between 0 and 1023)
		valIE_ratio = map(valIE_ratio, 0, 1023, 1.00, 4.00);     // scale it to use it with the servo (value between 0 and 180)
		valTidVol = analogRead(potpinTidVol);            // reads the value of the potentiometer (value between 0 and 1023)
		valTidVol = map(valTidVol, 0, 1023, 40.00, 90.00);     // scale it to use it with the servo (value between 0 and 180)
		valBPM = analogRead(potpinBPM);            // reads the value of the potentiometer (value between 0 and 1023)
		valBPM = map(valBPM, 0, 1023, 8.00, 30.00);     // scale it to use it with the servo (value between 0 and 180)
		state = LOW;
	}
    else {
      valIE_ratio = 2;
      valTidVol = 50;
      valBPM = 15;
      state = HIGH;
    }
  }
  
  
  // ====== Copmute respiration separation time based on pot inputs ==========
  separation = 60/valBPM - (1+valIE_ratio);
  if (separation < 0)
  {
    valIE_ratio = 60/valBPM - 1;
    separation = 60/valBPM - (1+valIE_ratio);
  }

  // ========= Servo a-Clockwise motion =============
  for(pos = 30; pos <= valTidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/valTidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    Serial.println(pressure_diff);
    Serial.println(pressure_expiration);
  }
  delay(15);
  
  // ========= Servo Clockwise motion ============
  for(pos = valTidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*valIE_ratio/valTidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    Serial.println(pressure_diff);
    Serial.println(pressure_expiration);
  }  
  delay(separation*1000);
  
  previous = reading;
}

node_mcu_serial_firebase.ino

Arduino
#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif
#include <ArduinoJson.h>
#include <Wire.h>
#include <FirebaseArduino.h>
#include <NTPClient.h>
#include <WiFiUdp.h>

#include<SoftwareSerial.h>
SoftwareSerial SUART(4, 5); //SRX=Dpin-D2; STX-DPin-D1

#define FIREBASE_HOST "respire-447da.firebaseio.com"
#define FIREBASE_AUTH "vsloiSErdIEyQMV6ydzwaELOPVSP5dPqiOobAURm"
#define NTP_OFFSET   60 * 60      // In seconds
#define NTP_INTERVAL 60 * 1000    // In miliseconds
#define NTP_ADDRESS  "europe.pool.ntp.org"

WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP, NTP_ADDRESS, NTP_OFFSET, NTP_INTERVAL);

//=======================================
unsigned long time_1;
bool test_2;
String last_char = "}";
time_t t;

// Replace with your network credentials
const char* ssid     = "NETGEAR43";
const char* password = "smilingnest196";  

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "http://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "San Diego";

void setup() {
  Serial.begin(9600); //enable Serial Monitor
  SUART.begin(9600); //enable SUART Port
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
  Firebase.begin(FIREBASE_HOST, FIREBASE_AUTH);
  Serial.println("Connected to Firebase");
  timeClient.begin();
}

void loop() {
  timeClient.update();
  const int capacity = JSON_OBJECT_SIZE(1);
  StaticJsonBuffer<capacity> jb;
  JsonObject& doc = jb.createObject();
  doc["type"] = "request";
  String message = "";
  String test = "";
  boolean messageReady = false;
  doc.printTo(test);
  Serial.println(test);
  doc.printTo(Serial);
  doc.printTo(SUART);
  SUART.println(test);
  while(messageReady == false) { // blocking but that's ok
    if(SUART.available()) {
      message = SUART.readString();
      Serial.println("message was received");
      Serial.println(message);
      test_2 = message.endsWith(last_char);
      Serial.println(test_2);
      if (!(test_2)){
        return;
      }
      messageReady = true;
    }
  }
  send_data(message);
  delay(3000);
  }
  

//======================================


void send_data(String message) {
if(WiFi.status()== WL_CONNECTED){
    t = now();
    String time_now = String(t);
    Serial.println(time_now);
    Firebase.pushString(time_now, message);
    if(Firebase.success()){
    Serial.println("The push was successful");  
    }
    else
    {
      Serial.println("The push to Firebase failed");
    }
    
}}

uno_firebase_sd_screen.ino

Arduino
#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <SPI.h>
#include <SD.h>
#include <Nextion.h>


//======== Information about SD Card ====
/*
 ** MOSI - pin 11
 ** MISO - pin 12
 ** CLK - pin 13
 ** CS - pin 4
 */
 
//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

//====== LCD Variables ==============
int id_1 = 1;
int ch = 0;
int id_2 = 8;
int id_3 = 9;
String ad = "add ";
char buffer[100] = {0};
char buffer_2[100] = {0};
char buffer_3[100] = {0};
NexText t0 = NexText(0, 2, "t0");
NexText t1 = NexText(0, 3, "t0");
NexText t2 = NexText(0, 4, "t2");

//===== Variables =====
Servo servoright;
int pos = 0;   

//======= SD Card File ===========
File ventilator_data;

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers

String mode = "";


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(9600); //enable SUART Port for communication with NODEMCU
  pinMode(10,OUTPUT);
  if (!SD.begin(4)) {
    Serial.println("initialization failed!");
    return;
  }
  Serial.println("SD Card Initialization done.");
  ventilator_data = SD.open("ventilator_data.txt",FILE_WRITE);
  
}
 
void loop()
 
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
      }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "ACV";

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol, mode);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio, mode);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol, mode);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio, mode);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
      send_to_screen(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio, String mode)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        default:
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "SIMV";

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
      
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
      send_to_screen(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol, String mode)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    String data = mode + "," + pressure_mask + "," + pressure_diff + "," + pressure_expiration + ";";
    ventilator_data.println(data);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio, String mode)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    String data = mode + "," + pressure_mask + "," + pressure_diff + "," + pressure_expiration + ";";
    ventilator_data.println(data);
  }  
  return millis();
}

// =====================
// Transmit to DB
// =====================

void transmit(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      // The only messages we'll parse will be formatted in JSON
      const int capacity = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity> jb;
      JsonObject& doc = jb.parseObject(message);
      //DynamicJsonDocument doc(1024); // ArduinoJson version 6+
      // Attempt to deserialize the message
      if(!(doc.success())){
        Serial.println("Doc conversion failed");
        messageReady = false;
        doc["type"] = "incorrect";
      }
      if(doc["type"] == "request") {
        doc["type"] = "response";
        doc["BPM"] = BPM;
        doc["IE_ratio"] = IE_ratio;
        doc["pressure_mask"] = pressure_mask;
        doc["pressure_expiration"] = pressure_expiration;
        doc["TidVol"] = TidVol;
        doc["pressure_diff"] = pressure_diff; 
        doc.printTo(SUART);
      }
      }
      }

// =====================
// Print to Screen
// =====================

void send_to_screen(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
  float p_mask = map(pressure_mask, 5.00, 20.00, 0, 255);
  float p_expiration = map(pressure_mask, 5.00, 20.00, 0, 255);
  float p_diff = map(pressure_mask, 5.00, 20.00, 0, 255);
  String to_send_p_mask = ad + id_1 + "," + ch + "," + int(p_mask);
  print_screen(to_send_p_mask);
  String to_send_p_diff = ad + id_2 + "," + ch + "," + int(p_diff);
  print_screen(to_send_p_diff);
  String to_send_p_exp = ad + id_3 + "," + ch + "," + int(p_expiration);
  print_screen(to_send_p_exp);
  dtostrf(BPM, 6, 2, buffer);
  t0.setText(buffer);
  dtostrf(IE_ratio,6,2,buffer_2);
  t1.setText(buffer_2);
  dtostrf(TidVol,6,2,buffer_3);
  t2.setText(buffer_3);
}

void print_screen(String to_send){
  Serial.print(to_send);
  Serial.write(0xff);
  Serial.write(0xff);
  Serial.write(0xff);
}

uno_serial_firebase.ino

Arduino
#include <Guino.h>

#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>

//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

Servo servoright;
int pos = 0;   

 

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int mode;           // the current reading from the input pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(9600); //enable SUART Port for communication with NODEMCU
//  attachInterrupt(0, pin_ISR, CHANGE);
}
 
void loop()
 
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
      }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
        default:
            inspiration(TidVol);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
      
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
    Serial.println(pressure_mask);
    //Serial.println(pressure_diff);
    //Serial.println(pressure_expiration);
  }  
  return millis();
}

// =====================
// Transmit to DB
// =====================

void transmit(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      // The only messages we'll parse will be formatted in JSON
      const int capacity = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity> jb;
      JsonObject& doc = jb.parseObject(message);
      //DynamicJsonDocument doc(1024); // ArduinoJson version 6+
      // Attempt to deserialize the message
      if(!(doc.success())){
        Serial.println("Doc conversion failed");
        messageReady = false;
        doc["type"] = "incorrect";
      }
      if(doc["type"] == "request") {
        doc["type"] = "response";
        doc["BPM"] = BPM;
        doc["IE_ratio"] = IE_ratio;
        doc["pressure_mask"] = pressure_mask;
        doc["pressure_expiration"] = pressure_expiration;
        doc["TidVol"] = TidVol;
        doc["pressure_diff"] = pressure_diff; 
        doc.printTo(SUART);
      }
      }
      }

uno_serial_sd_firebase.ino

Arduino
#include <Guino.h>

#include <Servo.h>
#include<SoftwareSerial.h>
#include <ArduinoJson.h>
#include <SPI.h>
#include <SD.h>


//======== Information about SD Card ====
/*
 ** MOSI - pin 11
 ** MISO - pin 12
 ** CLK - pin 13
 ** CS - pin 4
 */
 
//====== Serial COnnection with NODEMCU =====
SoftwareSerial SUART(2, 3); //SRX=Dpin-2; STX-DPin-3

Servo servoright;
int pos = 0;   

//======= SD Card File ===========
File ventilator_data;

// ==== Analog Pins =====
float potpinIE_ratio = 0;  
int potpinTidVol = 1;  
int potpinBPM = 5;
int pinguage_mask = 4;
int pinguage_expiration = 3;
int pinguage_diff = 2;

// ==== Analog Pins ====
int inPin = 4;

// ==== Sensor Offset =====
const float guageSensorOffset = 41;
const float pressureDiffSensorOffset = 41;

// ===== Other vars ======
float check_value;
float IE_ratio;  
float TidVol;  
float BPM;
float separation;  
float sensorvalue;
float pressure_mask;
float pressure_expiration;
float pressure_diff;

int display_IE_ratio;
int display_BPM;
int display_TidVol;
int display_sensorvalue_cmh2o;
int display_sensorvalue_gp_cmh2o;

// ======= Mode changing vars =========

int state = HIGH;      // the current state of the output pin
int previous = LOW;    // the previous reading from the input pin
long t_time = 0;         // the last time the output pin was toggled
long debounce = 200;   // the debounce time, increase if the output flickers

String mode = "";


void setup()
{
  servoright.attach(9);  // attaches the servo on pin 9 to the servo object
  Serial.begin(9600);
  SUART.begin(9600); //enable SUART Port for communication with NODEMCU
  pinMode(10,OUTPUT);
  if (!SD.begin(4)) {
    Serial.println("initialization failed!");
    return;
  }
  Serial.println("SD Card Initialization done.");
  ventilator_data = SD.open("ventilator_data.txt",FILE_WRITE);
  
}
 
void loop()
 
{
  if (digitalRead(inPin) == LOW)
  {
      while(digitalRead(inPin)==LOW)
      {
        simv_mode();
      }
  }
  else 
  {   while(digitalRead(inPin) == HIGH)
      {
        acv_mode();  
      }
      
  }

}

// =======================
// ACV MODE Function
// =======================

void acv_mode()
{
  float IE_ratio;
  float TidVol;
  float BPM;
  float per_breath_time;
  float per_inspiration_time;
  float per_expiration_time;
  float human_effort;
  float separation;
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "ACV";

  while(digitalRead(inPin) == HIGH)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
      { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);
       }

      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
      // Initiate the cycle
      if(firstRun)
      {
        inspiration(TidVol, mode);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio, mode);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || pressure_mask < -1)
      {
        inspiration(TidVol, mode);
        delay(15);
        cycleEndTime = expiration(TidVol, IE_ratio, mode);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
  
}

// =======================
// SIMV Logic Function
// =======================

uint32_t simv_logic(float pressure_mask, float TidVol, float IE_ratio, String mode)
{
    uint32_t cycleEndTime;
    pressure_mask = int(floor(pressure_mask));
    switch(int(pressure_mask)){
        case -6:
        case -5:
        case -4:
            TidVol = TidVol*0.25;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -3:
            TidVol = TidVol*0.50;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -2:
            TidVol = TidVol*0.75;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        case -1:
            TidVol = TidVol*0.75;
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
        default:
            inspiration(TidVol, mode);
            delay(15);
            cycleEndTime = expiration(TidVol, IE_ratio, mode);
            break;
    }
    return cycleEndTime;
}

// =======================
// SIMV MODE Function
// =======================

void simv_mode()
{
  uint32_t cycleEndTime;
  bool firstRun = true;
  mode = "SIMV";

  while(digitalRead(inPin) == LOW)
  {
      // Fetch all potentiometer values
      IE_ratio = map(analogRead(potpinIE_ratio), 0, 1023, 1.00, 4.00);    
      TidVol = map(analogRead(potpinTidVol), 0, 1023, 40.00, 90.00);     
      BPM = map(analogRead(potpinBPM), 0, 1023, 8.00, 30.00);     
      separation = (60/BPM - (1+IE_ratio));
      if (separation < 0)
    { IE_ratio = 60/BPM - 1;
        separation = 60/BPM - (1+IE_ratio);}
      // Fetch pressure sensor values
      pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
      pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92;
      pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    
      
      // Initiate the cycle
      if(firstRun)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
        firstRun = false;
      }

      // ========= Identify trigger and initiate the cycle =============
      if(millis() - cycleEndTime >= (uint32_t)separation*1000 || average_pressure_mask() < -1)
      {
        pressure_mask = average_pressure_mask();
        cycleEndTime = simv_logic(pressure_mask, TidVol, IE_ratio, mode);
      }
      transmit(BPM, IE_ratio, pressure_mask, pressure_expiration, TidVol, pressure_diff);
  }
}

// =======================
// Average Pressure Function
// =======================

float average_pressure_mask()
{
    pressure_mask = 0;
    for(int i=0;i<5;i++)
    {
        pressure_mask = pressure_mask + (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;
        delay(3);
    }
    return (pressure_mask/5);
}


// =======================
// Inspiration Function
// =======================
void inspiration(float TidVol, String mode)
{ int pos;
  for(pos = 30; pos <= TidVol+30; pos += 1) // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoright.write(pos);
    delay(1000/TidVol);                       

    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    String data = mode + "," + pressure_mask + "," + pressure_diff + "," + pressure_expiration + ";";
    ventilator_data.println(data);
  }

}

// =====================
// Expiration Function
// =====================

uint32_t expiration(float TidVol, float IE_ratio, String mode)
{
  for(pos = TidVol+30; pos>=30; pos-=1)     // goes from 180 degrees to 0 degrees
  {                                
    servoright.write(pos);
    delay(1000*IE_ratio/TidVol);                       
    // ============ Update pressure values =========
    pressure_mask = (map(analogRead(pinguage_mask), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92;    
    pressure_diff = (map(analogRead(pinguage_diff), 0, 1023, 0, 1023) - pressureDiffSensorOffset)*10.1972/92; 
    pressure_expiration = (map(analogRead(pinguage_expiration), 0, 1023, 0, 1023) - guageSensorOffset)*10.1972/92; 
    String data = mode + "," + pressure_mask + "," + pressure_diff + "," + pressure_expiration + ";";
    ventilator_data.println(data);
  }  
  return millis();
}

// =====================
// Transmit to DB
// =====================

void transmit(float BPM, float IE_ratio, float pressure_mask, float pressure_expiration, float TidVol, float pressure_diff){
      String message = "";
      boolean messageReady = false;
      while(SUART.available()) {
        message = SUART.readString();
        Serial.println(message);
        messageReady = true;
        }
      if(messageReady) {
      // The only messages we'll parse will be formatted in JSON
      const int capacity = JSON_OBJECT_SIZE(7);
      StaticJsonBuffer<capacity> jb;
      JsonObject& doc = jb.parseObject(message);
      //DynamicJsonDocument doc(1024); // ArduinoJson version 6+
      // Attempt to deserialize the message
      if(!(doc.success())){
        Serial.println("Doc conversion failed");
        messageReady = false;
        doc["type"] = "incorrect";
      }
      if(doc["type"] == "request") {
        doc["type"] = "response";
        doc["BPM"] = BPM;
        doc["IE_ratio"] = IE_ratio;
        doc["pressure_mask"] = pressure_mask;
        doc["pressure_expiration"] = pressure_expiration;
        doc["TidVol"] = TidVol;
        doc["pressure_diff"] = pressure_diff; 
        doc.printTo(SUART);
      }
      }
      }

wifi_sample_code.ino

Arduino
/*
  Rui Santos
  Complete project details at https://RandomNerdTutorials.com/esp32-esp8266-mysql-database-php/
  
  Permission is hereby granted, free of charge, to any person obtaining a copy
  of this software and associated documentation files.
  
  The above copyright notice and this permission notice shall be included in all
  copies or substantial portions of the Software.
*/

#ifdef ESP32
  #include <WiFi.h>
  #include <HTTPClient.h>
#else
  #include <ESP8266WiFi.h>
  #include <ESP8266HTTPClient.h>
  #include <WiFiClient.h>
#endif

#include <Wire.h>
//#include <Adafruit_Sensor.h>
//#include <Adafruit_BME280.h>

// Replace with your network credentials
const char* ssid     = "1.21 Jiggawatts!";
const char* password = "itburnswhenIP";

// REPLACE with your Domain name and URL path or IP address with path
const char* serverName = "https://respire.000webhostapp.com/post-esp-data.php";

// Keep this API Key value to be compatible with the PHP code provided in the project page. 
// If you change the apiKeyValue value, the PHP file /post-esp-data.php also needs to have the same key 
String apiKeyValue = "xPmAT5Ab3j7F6";

String sensorName = "MPXDIFF";
String sensorLocation = "SD";

/*#include <SPI.h>
#define BME_SCK 18
#define BME_MISO 19
#define BME_MOSI 23
#define BME_CS 5*/

//#define SEALEVELPRESSURE_HPA (1013.25)

//Adafruit_BME280 bme;  // I2C
//Adafruit_BME280 bme(BME_CS);  // hardware SPI
//Adafruit_BME280 bme(BME_CS, BME_MOSI, BME_MISO, BME_SCK);  // software SPI

void setup() {
  Serial.begin(115200);
  
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());

  // (you can also pass in a Wire library object like &Wire2)
  //bool status = bme.begin(0x76);
  //if (!status) {
  //Serial.println("Could not find a valid BME280 sensor, check wiring or change I2C address!");
  //while (1);
  
}

void loop() {
  //Check WiFi connection status
  if(WiFi.status()== WL_CONNECTED){
    HTTPClient http;
    
    // Your Domain name with URL path or IP address with path
    http.begin(serverName);
    
    // Specify content-type header
    http.addHeader("Content-Type", "application/x-www-form-urlencoded");
    
    // Prepare your HTTP POST request data
    String httpRequestData = "api_key=" + apiKeyValue + "&sensor=" + sensorName
                          + "&location=" + sensorLocation + "&value1=" + String("Sample_value_1")
                          + "&value2=" + String("Sample_Value_2") + "&value3=" + String("Sample_value_3") + "";
    Serial.print("httpRequestData: ");
    Serial.println(httpRequestData);
    
    // You can comment the httpRequestData variable above
    // then, use the httpRequestData variable below (for testing purposes without the BME280 sensor)
    //String httpRequestData = "api_key=tPmAT5Ab3j7F9&sensor=BME280&location=Office&value1=24.75&value2=49.54&value3=1005.14";

    // Send HTTP POST request
    int httpResponseCode = http.POST(httpRequestData);
     
    // If you need an HTTP request with a content type: text/plain
    //http.addHeader("Content-Type", "text/plain");
    //int httpResponseCode = http.POST("Hello, World!");
    
    // If you need an HTTP request with a content type: application/json, use the following:
    //http.addHeader("Content-Type", "application/json");
    //int httpResponseCode = http.POST("{\"value1\":\"19\",\"value2\":\"67\",\"value3\":\"78\"}");
        
    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");
  }
  //Send an HTTP POST request every 30 seconds
  delay(30000);  
}

Github

Credits

Mo Hany

Mo Hany

1 project • 0 followers

Comments