Can't display the right sensor value

Hi!

I am fairly new to Arduino and programming overall and I currently have a slight issue displaying the sensor value that I want.

What I intend to do is first of all map down the range of the analog read from 0 - 1023 to 0 - 10. Then, if the read stays the same for 300ms it prints the mapped sensor value. Right now it displays 0 as the value and I assume it has to do something with what has been defined before this function below.

if(currentTime - previousTime_sensorValue1 >= eventTime_sensorValue1 && timedSensorValue1 - scaledSensorValue1 == 0)

I am trying to set the timedSensorValue1 to the same as scaledSensorValue1 but need to differentiate them.

int timedSensorValue1 = scaledSensorValue1; is what I think is causing the issue but I don't know how to solve it unfortunately.

As I want them to be different depending on when it was read so that it can check if the scaledSensorValue1 is still the same after 300ms, then print the value if the statement is true.

Any ideas of how I can make this possible? Also, I want to use multiple sensors that reads and prints the sensor values at the same time.

Thanks in advance/ noob trying to learn

int sensor1 = A0;
int sensorValue1 = analogRead (sensor1);
const unsigned long eventTime_sensorValue1 = 300;
unsigned long previousTime_sensorValue1 = 0;
  
void setup(){
  Serial.begin(9600);
}

void loop(){
  int scaledSensorValue1 = map(sensorValue1, 0, 1023, 0, 10);
  int timedSensorValue1 = scaledSensorValue1;
  unsigned long currentTime = millis();

  if(currentTime - previousTime_sensorValue1 >= eventTime_sensorValue1 && timedSensorValue1 - scaledSensorValue1 == 0){

  Serial.print ("Sensor 1: ");
  Serial.println (scaledSensorValue1);

  previousTime_sensorValue1 = currentTime;
  }
}

You have posted code using text tags instead of code tags. The code tags make the code look

like this

when posting source code files. It makes it easier to read, and can be copied with a single mouse click. Also, if you don’t do it, some of the character sequences in the code can be misinterpred by the forum code as italics or funny emoticons. The “Code: [Select]” feature allows someone to select the entire sketch so it can be easily copied and pasted into the IDE for testing.
If you have already posted without using code tags, open your message and select “modify” from the pull down menu labelled, “More”, at the lower left corner of the message. Highlight your code by selecting it (it turns blue), and then click on the “</>” icon at the upper left hand corner. Click on the “Save” button. Code tags can also be inserted manually in the forum text using the code and /code metatags.

Before you do that, please remove all the superfluous blank lines from your sketch. They are bad form.

Like this? =)

You are attempting to use "analogRead" before the hardware is properly initialized, don't do that. In order to get updated values from the sensor, you should read from it in "loop()" instead.

Thank you. I'm having trouble understanding your program requirement. Is it, "if a time interval has elapsed and the reading has changed, then print it"?

You have to present it in really clear unambiguous language.

@aarg No, if after the time interval, the reading is the same. Then print it. If it has changed, do nothing.

@Danois90 that seems to have resolved the issue. Thanks a lot!

Now I stand for the next issue hehe. If I add another sensor, double the variables and constants (anything that has a 1 in it now has another with a 2 instead (see below)).

If copy paste the if statement and change it to the 2nd sensor. I only get that one. Can I somehow have everything in the same function? How do I build the statement then?

int sensor1 = A0;
int sensor2= A1;
int sensorValue1 = analogRead (sensor1);
int sensorValue2 = analogRead (sensor2);
const unsigned long eventTime_sensorValue1 = 300;
const unsigned long eventTime_sensorValue2 = 300;
unsigned long previousTime_sensorValue1 = 0;
unsigned long previousTime_sensorValue2 = 0;

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

}

void loop(){
int scaledSensorValue1 = map(sensorValue1, 0, 1023, 0, 10);
int scaledSensorValue2 = map(sensorValue2, 0, 1023, 0, 10);
int timedSensorValue1 = scaledSensorValue1;
int timedSensorValue2 = scaledSensorValue2;
unsigned long currentTime = millis();

  if(currentTime - previousTime_sensorValue1 >= eventTime_sensorValue1 && timedSensorValue1 - scaledSensorValue1 == 0){

  Serial.print ("Sensor 1: ");
  Serial.println (scaledSensorValue1);

  previousTime_sensorValue1 = currentTime;
  
  }

  if(currentTime - previousTime_sensorValue2 >= eventTime_sensorValue2 && timedSensorValue2 - scaledSensorValue1 == 0){

  Serial.print ("Sensor 2: ");
  Serial.println (scaledSensorValue2);

  previousTime_sensorValue2 = currentTime;
  }
}

Zapoo:
@aarg No, if after the time interval, the reading is the same. Then print it. If it has changed, do nothing.

Do you mind if I ask why? If I print something only when it doesn't change, the last thing that was printed is by definition, the same as the current thing. So why would I need to update it or view it?

Zapoo:
@Danois90 that seems to have resolved the issue. Thanks a lot!

Your code is still wrong with the same issue, though…

aarg:
Do you mind if I ask why? If I print something only when it doesn't change, the last thing that was printed is by definition, the same as the current thing. So why would I need to update it or view it?

The reason to why is that I only want the readings printed if it is somewhat stabilized. This is so that I can later send that data to a pc or smartphone. From there I will interpret the data.

Danois90:
Your code is still wrong with the same issue, though..

I get both sensors values printed now as I wanted. However, this gives me a time interval of how often it should be printed, not checking if the scaledSensorValue is the same as it was 300ms ago.

The reason to why is that I only want the readings printed if it is somewhat stabilized.

Most people would want to understand why are the readings NOT stable, because instability indicates a problem.

jremington:
Most people would want to understand why are the readings NOT stable, because instability indicates a problem.

Because the sensors will be sensing finger movement. If I continuously move my hand, I don't want it to be recognized. But as my hand is stable for a short period of time, then I want to read that data. Makes more sense?

Therefore I have narrowed down the range to be less precise (as the precision is not needed). This way I can more easily stay at an exact value for a longer time even if my finger moves just a tiny bit. But then I will need to get the data from when I hold my fingers still for a set period of time. When all fingers have been still for that time, I want the readings to be printed.

What if the readings are unstable for some other reason (bad connection, broken sensor) than finger movement?

Zapoo:
Because the sensors will be sensing finger movement. If I continuously move my hand, I don't want it to be recognized. But as my hand is stable for a short period of time, then I want to read that data. Makes more sense?

I say no, because you're focusing on the readings, not the outcome. If somewhere downstream (e.g. at the PC or smartphone), you want to detect a period of time when no movement has occurred, then you have to implement some timing there. In that case, what is the point of screening out readings that do change? You can easily perform all that timing and logic at the PC/phone software end. I believe you will already be forced to do some of it there, with your current scheme.

Looking from the PC's point of view, you could equally well send data only when it changes, then keep track of the time of the last data change report. If a certain time has expired then the input has been constant for that time.

How, on the PC end, do you "mark" the beginning of a change, if you have screened out any changes? It would be when two consecutive readings on the Arduino are the same, and then the continuously sent stream value changes ONCE. After that, you must be simply ignoring all the identical data items. It is as futile for a machine as it is for a human, to deal with all that redundant data. Effectively, when the data value in your stream changes, it is exactly when the value changes (so that technically, either method can work). But your method is a counter-intuitive and data intensive way to do it.

Does that not make sense?

@aarg
The idea is to take the value from the sensors and multiply them by 1 up to 10000.
scaledSensorValue1 * 10000
scaledSensorValue2 * 1000
scaledSensorValue3 * 100
scaledSensorValue4 * 10
scaledSensorValue5 * 1

Then i sum them up and add an s before so that i can find it in the dictionairy on my pc with a "serial-code" that has the format of s12345. From there i can get the commands that i want for each "serial-code" in my pc.

So basicallt I just want to get that "serial-code" . But it has to take the value of the reads from when they have not changed in a specified amount of time. Elsewise I will not be able to get this "Serial-code" very precise. So if the scaledSensorvalues has been the same for x amount of ms(time) it will create this "serial-code" that I can later use on my pc.

So, as I explained previously, don't send anything unless it changes. Then time the incoming data. If you don't receive any new data within a specified time, the datum that you last received is valid.

That is the most obvious and straightforward implementation. You can take it or leave it.

If you have multiple sensors where each sensor will require the same readout but with different multipliers, you should use arrays - this would make it A LOT easier. You should not waste “int” (16 bit values) for pin constants - use “byte” (8 bit) instead.

int sensorValue1 = analogRead (sensor1);
int sensorValue2 = analogRead (sensor2);

The snippet above will perform 2 analogRead’s before the hardware is initialized. You should perform these initial reads in “setup()” and new reads in “loop()”.

#define SENSOR_COUNT 2

const byte sensorPins[SENSOR_COUNT] = {A0, A1};
unsigned long sensorValues[SENSOR_COUNT] = {0};

void setup()
{
  for (byte i = 0; i < SENSOR_COUNT; i++)
  {
    sensorValues[i] = analogRead(sensorPins[i]);
  }
}

void loop()
{
  for (byte i = 0; i < SENSOR_COUNT; i++)
  {
    int sv = analogRead(sensorPins[i]);
    if (sv != sensorValues[i])
    {
      //Handle sensor change
      sensorValues[i] = sv;
    }
  }
}

Now you fill in the blanks! :slight_smile: