Go Down

Topic: Receiving different strings of data (Read 828 times) previous topic - next topic

DirtGambit

I have a little program that logs temp and rh, My arduino sends out a string of data every 4 seconds consisting of ints and a "]" at the end which i split in processing and assign to variables, I have a few buttons on my app, button 1 resets graph cursor to 0, resetting the graph output on screen, the second button sends a "1" down the serial port, when the arduino receives this it resets the max/min values held on eprom to the current temp/rh/time/date. The 3rd button sends a 2 done the serial port and the arduino reads all the stored historic data from these sensors and sends it to  the serial port, on the arduino serial monitor everything seems to be working fine, i type 2 and the arduino stops sending out usual data stream, reads the eprom and sends all the data followed by an "@".

Whats the best way of getting processing recognising the new datastream? Im thinking i need to add start of string markers or something like that and incorporate it into my serialEvent, im a little unsure how to go about that, or can I make another function that handles this new stream by itself?


PaulS

Quote
can I make another function that handles this new stream by itself?

No. One serial port == one serial event. The serial port has no idea what the bits coming down that port might mean.

Quote
Whats the best way of getting processing recognising the new datastream?

The "best" way is to stop thinking of it as a new data stream. The stream of data, no matter how intermittent, continues. The difference is what the data in that stream means to the receiving application.

You have each packet being sent use a different end of packet marker. Using the end of packet markers is good. Now, add a start of packet marker, too. Use a different start of packet marker for the two different kinds of packets, and react accordingly.

Personally, I like symmetric markers, like < and > or [ and ] or { and }, rather than asymmetric markers like nothing and ] or nothing and @, but, the choice of markers is up to you.

DirtGambit

Your right its not a new datastream to the serial port cos it just reads what I tell it too read depending on the end packet marker, Ok so I have changed my arduino to send out the 4sec data between "[" and "]", i changed the extra data that i will send when the button is press so the start and end marker is "{" and "}" on the serial monitor everything seems to be working fine.

On processing Im a little unsure how to read the start marker, Im using myport.read() and no data is coming through, I also used readChar() still nothing happening, Ill post my serialEvent

Code: [Select]


void serialEvent(Serial myPort){
  //DataStream = "";
  int mapped_tempc = 0;
  int mapped_rh = 0;
  int mapped_ldr =0;
  char readdata;
  //while(myport.available() > 0)
    readdata = myport.readChar();
    if(readdata == '[')
    {
      String inString = myport.readStringUntil(']');
      inString = inString.substring(0, inString.length() - 1);
        if(inString != null )
        {
          inString = trim(inString);
          int inputs[] = int(split(inString, ','));
          Temp_C = inputs[0];
          Temp_F = inputs[1];
          RH = inputs[2];
   
         //Lightlev = inputs[3];
          mapped_tempc = inputs[4];
          mapped_rh = inputs[5];
          mapped_ldr = inputs[3];
          date_day = inputs[7];
          date_month = inputs[8];
          date_year = inputs[9];
          time_hours = inputs[10];
          time_minutes = inputs[11];
          Max_TempC = inputs[12] + "C";
          Min_TempC = inputs[13] + "C";
          Max_TempF = inputs[14] + "F";
          Min_TempF = inputs[15] + "F";
          Max_RH = inputs[16] + "%";
          Min_RH = inputs[17] + "%";
          MaxTempDate = inputs[18] + "/" + inputs[19] + "/" + inputs[20];
          MaxTempTime = inputs[21] + ":";
          if(inputs[22] < 10) { MaxTempTime += "0";}
          MaxTempTime += inputs[22];
         
          MinTempDate = inputs[23] + "/" + inputs[24] + "/" + inputs[25];
          MinTempTime = inputs[26] + ":";
          if(inputs[27] < 10) { MinTempTime += "0";}
          MinTempTime += inputs[27];
         
          MaxRHDate = inputs[28] + "/" + inputs[29] + "/" + inputs[30];
          MaxRHTime = inputs[31] + ":";
          if(inputs[32] < 10) { MaxRHTime += "0";}
          MaxRHTime += inputs[32];
         
          MinRHDate = inputs[33] + "/" + inputs[34] + "/" + inputs[35];
          MinRHTime = inputs[36] + ":";
          if(inputs[37] < 10) { MinRHTime += "0";}
          MinRHTime += inputs[37];
           
          All_TempC = Temp_C + "C";
          All_TempF = Temp_F + "F";
          All_RH = RH + "%";
          for(int i = 0; i < 38; i ++)
          {
            DataStream += inputs[i] + ":";
          }
          if(Lightlev > 5)
          {
            lightlevel = true;
          }
          else
          {
            lightlevel = false;
          }
          Array_Data.addval(mapped_tempc, mapped_rh,checkStatus(0,Temp_C), checkStatus(1,RH));
        }
        if(time_minutes < 10)
        {
          All_Time = time_hours + ":" + "0" + time_minutes;
        }
        else
        {
          All_Time = time_hours + ":" + time_minutes;
        }
        All_Date = date_day + "/" + date_month + "/" + date_year;
        ExcelGraphData.print(Temp_C + " ," + RH + " ," + Lightlev + " ," + All_Date + " ," + All_Time + "\n");
        ExcelGraphData.flush();
      }
  //}
 
  if(myport.read() == '{'){
  String inhistString = myport.readStringUntil('}');
  inhistString = inhistString.substring(0, inhistString.length() - 1);
  if(inhistString != null )
  {
    inhistString = trim(inhistString);
    int history_ints[] = int(split(inhistString, ','));
    for(int i = 0; i < 621;)
    {
      int t = 0;
      int h = 0;
      if(i%2 == 0)
      {
        t = history_ints[i];
        i++;
        h = history_ints[i];
        ArrayData.addhistval(t,h);
      }
    }
  }
}

}





PaulS

Quote
Im using myport.read() and no data is coming through, I also used readChar() still nothing happening, Ill post my serialEvent

A simple print at the top of serialEvent will tell you whether it ever gets called.

Code: [Select]
    readdata = myport.readChar();
    if(readdata == '[')
    {
      }
  //}
 
  if(myport.read() == '{'){

So, if the character read isn't a square bracket, ignore it, read another one and see it it is a curly bracket. Got it. Not.

DirtGambit

In my setup() i forgot to change bufferUntil('*') to ('\n'), I dont really get what your saying?

Im having more success with this serialEvent, at least its graphing out the the selection of '[' but when i press the button on application the program pauses for 5 seconds then carries on, it doesnt get as far as print("Max/Min").

Code: [Select]


void serialEvent(Serial myPort){
  println("Called");
  int mapped_tempc = 0;
  int mapped_rh = 0;
  int mapped_ldr =0;
  if(myport.read() == '[')
  {
    print("Data");
    String inString = myport.readStringUntil(']');
    inString = inString.substring(0, inString.length() - 1);
    if(inString != null )
     {
     inString = trim(inString);
     int inputs[] = int(split(inString, ','));
     Temp_C = inputs[0];
     Temp_F = inputs[1];
     RH = inputs[2];
   
     Lightlev = inputs[3];
     mapped_tempc = inputs[4];
     mapped_rh = inputs[5];
     mapped_ldr = inputs[6];
   
     date_day = inputs[7];
     date_month = inputs[8];
     date_year = inputs[9];
     time_hours = inputs[10];
     time_minutes = inputs[11];
     Max_TempC = inputs[12] + "C";
     Min_TempC = inputs[13] + "C";
     Max_TempF = inputs[14] + "F";
     Min_TempF = inputs[15] + "F";
     Max_RH = inputs[16] + "%";
     Min_RH = inputs[17] + "%";
     MaxTempDate = inputs[18] + "/" + inputs[19] + "/" + inputs[20];
     MaxTempTime = inputs[21] + ":";
     if(inputs[22] < 10) { MaxTempTime += "0";}
          MaxTempTime += inputs[22];
         
     MinTempDate = inputs[23] + "/" + inputs[24] + "/" + inputs[25];
     MinTempTime = inputs[26] + ":";
     if(inputs[27] < 10) { MinTempTime += "0";}
          MinTempTime += inputs[27];
         
     MaxRHDate = inputs[28] + "/" + inputs[29] + "/" + inputs[30];
     MaxRHTime = inputs[31] + ":";
     if(inputs[32] < 10) { MaxRHTime += "0";}
         MaxRHTime += inputs[32];
         
     MinRHDate = inputs[33] + "/" + inputs[34] + "/" + inputs[35];
     MinRHTime = inputs[36] + ":";
     if(inputs[37] < 10) { MinRHTime += "0";}
         MinRHTime += inputs[37];
           
     All_TempC = Temp_C + "C";
     All_TempF = Temp_F + "F";
     All_RH = RH + "%";
     for(int i = 0; i < 38; i ++)
     {
       DataStream += inputs[i] + ":";
     }
     if(Lightlev > 5)
     {
       lightlevel = true;
     }
     else
     {
       lightlevel = false;
     }
     Array_Data.addval(mapped_tempc, mapped_rh,checkStatus(0,Temp_C), checkStatus(1,RH));

    if(time_minutes < 10)
    {
      All_Time = time_hours + ":" + "0" + time_minutes;
    }
    else
    {
      All_Time = time_hours + ":" + time_minutes;
    }
    All_Date = date_day + "/" + date_month + "/" + date_year;
    ExcelGraphData.print(Temp_C + " ," + RH + " ," + Lightlev + " ," + All_Date + " ," + All_Time + "\n");
    ExcelGraphData.flush();
   }
  }
  if(myport.read() == '{')
  {
    println("Max/Min");
    Display_SevenDay = true;
  String inhistString = myport.readStringUntil('}');
  inhistString = inhistString.substring(0, inhistString.length() - 1);
  if(inhistString != null )
  {
    inhistString = trim(inhistString);
    int history_ints[] = int(split(inhistString, ','));
   
    for(int i = 0;i < 50;)
    {
      println(history_ints[i]);
      int t = 0;
      int h = 0;
        t = history_ints[i];
        i++;
        h = history_ints[i];
       Array_Data.addsevenval(t, h,checkStatus(0,t), checkStatus(1,h));
    }
  }
  }
  myport.clear();
}

PaulS

Code: [Select]
void serialEvent(Serial myPort){
  if(myport.read() == '[')
  {
    print("Data");
  }
  if(myport.read() == '{')
  {
    println("Max/Min");
  }
  myport.clear();
}

Suppose that this function gets called, and the serial buffer contains "[SomeData]". You read the first character ('['), and determine that it is a open square bracket. So, you read the rest of the data.

Now, suppose that this function gets called with "{SomeData}". You read the first character ('{'), and determine that it is not a open square bracket. Then, you read the next character ('S'), and determine that it is not a open curly brace, so you delete the rest of the data in the serial buffer.

You need to read AND STORE the first character. Then, test whether that character is a [. If it is, do something.

Then, test whether that first character is a {, instead of reading another character.

DirtGambit

Hi, Ive been at Uni this week so didnt have much time to work on it, I have put myport.read() through switch() and Im having better success, is it better to store myport.read() in a variable or no difference to just use switch(myport.read()) ?

PaulS

Quote
is it better to store myport.read() in a variable or no difference to just use switch(myport.read()) ?

If you store the value read, you can use it more than once. The switch statement effectively does that. Which to use depends on how many cases there are. One or two, save the value and use if statements. More than a dozen? The switch statement is better. In between? Your call.

Go Up