Problem reading two sensors with analogRead()

Post here about your Arduino projects, get help - for Adafruit customers!

Moderators: adafruit_support_bill, adafruit

Re: Problem reading two sensors with analogRead()

Postby physicsonion » Wed Nov 14, 2012 9:43 pm

My $0.05 solution to this problem is as following. As people earlier in the thread have indicated the arduino itself has a multiplexer and only one ADC. Problem occurs when flipping between different voltage sources that they introduce transient which takes a while to disappear. Source of the transient is the input capacitance of the ADC and its huge input resistance (hence the large time constant).

This said, of 6 input channels of arduino, I take one - say A0 - and through a 5k resistor I ground it. Then, before I try to read any other analog channels, I first connect the ADC to the ground by reading from A0.

!!Code snippet
analogRead(A0); // dummy read to discharge ADC
delay (20); // wait a little
analogRead(A1); // now hook up ADC to the channel we really want to read
delay (20); // doze a little
temp = 100*(analogRead(A1)*5/1025 -0.5); // now read once more
!!End of code snippet

With this approach I was able to read 4 additional analog inputs - in my case these were 4 x TMP36 temperature sensors at rate 50, or so, milliseconds per sensor.

Hope this helps,
PhysicsOnion
physicsonion
 
Posts: 2
Joined: Wed Jan 04, 2012 10:10 am

Re: Problem reading two sensors with analogRead()

Postby gregario » Fri Nov 16, 2012 6:53 am

Hi All,

I'm having a similar problem. I'm running a photoresistor and a TMP36 and logging the data on an arduino.
The temperature sensor is fine but the photoresistor is very noisy. Any tips?

Details, the photoresistor is in a voltage divider with a 1K resistor (the lower resistor is there to increase the range).
I've tried the tricks suggested and then some, here's an excerpt of code for example:

Code: Select all
  analogRead(gndPin);
  delay(100);
  analogRead(photocellPin);
  delay(100);
  int photocellReading = analogRead(photocellPin); 
  delay(100);
  analogRead(gndPin);
  delay(100);
  analogRead(tempPin);
  delay(100);
  int tempReading = analogRead(tempPin);   
  delay(100);
  // converting that reading to voltage, for 3.3v arduino use 3.3, for 5.0, use 5.0
  float voltage = tempReading * aref_voltage / 1024;
  float temperatureC = (voltage - 0.5) * 100;
  float voltage1 = photocellReading * aref_voltage / 1024;
  // float temperatureF = (temperatureC * 9 / 5) + 32;
  //Converts Photocell Reading to Lux Reading, This will be unique for each Sensor and will change between diodes/Photoresistors
  // Sensor 12 (C) = y = 626.06x6 - 3395.4x5 + 7395.5x4 - 7264.1x3 + 3743.7x2 - 148.26x
  double luxReading = ((626.06*(pow(voltage1,6)) -(3395.4*(pow(voltage1,5))) + (7195.5*(pow(voltage1,4))) - (7264.1*(pow(voltage1,3))) + (3743.7*(pow(voltage1,2))) - (148.26*voltage1)));


The ground pin is a 5K resistor tied to ground to try and flush the ADC cap between measurements. The 6th order polynomial is my attempt to get an accurate lux measurement from one of these sensors. (I calibrated using an OLED taped to the top of a dremel tube and a lux meter)

Here's an output under a controlled light source
Code: Select all
Seconds (S)   Light (10 bit)   Light (lux)
1   244   544.59
2   265   607.21
3   275   638.49
4   251   565.03
5   245   547.49
6   276   641.67
7   256   579.89
8   247   553.3
9   276   641.67
10   272   629
11   254   573.92
12   253   570.95
13   276   641.67
14   254   573.92
15   245   547.49
16   271   625.86
17   276   641.67
18   248   556.22
19   250   562.09
20   275   638.49


The measurements quoted above under fluorescent, I must dig out the response times of these sensors in case its light flicker I'm seeing...

Any help would be greatly appreciated guys, micro's are not my strong point!
gregario
 
Posts: 3
Joined: Fri Jun 11, 2010 8:18 am

Re: Problem reading two sensors with analogRead()

Postby adafruit_support_bill » Fri Nov 16, 2012 10:34 am

CdS cells are fairly slow, but the fluorescent flicker could be part of the problem. You can minimize the 60Hz flicker and other noise as well by taking the average of multiple samples over some multiple of 16ms. If you are only logging once per second, you have plenty of time to take multiple samples.
User avatar
adafruit_support_bill
 
Posts: 15918
Joined: Sat Feb 07, 2009 9:11 am

Re: Problem reading two sensors with analogRead()

Postby Strohkopf » Sat Nov 24, 2012 6:09 am

Hi! Seems I have problems w/ reading sensors too.

I have arduini uno board, seeeduino wifly-shield http://www.seeedstudio.com/wiki/Wifi_Shield and extension DFRduino shield.
I need to send results from IR and Ultra Sound length-meters via WiFi on PC, just making a robot.

Simple code of my programm is
Code: Select all
#include "Wifly.h"
#include <SoftwareSerial.h>
WiflyClass Wifly(2,3);

int sensors[6];

void setup()
{
  Serial.begin(9600);//use the hardware serial to communicate with the PC
  bool wifi = true;
  if(wifi){
    Wifly.init();//Initialize the wifishield
    Wifly.setConfig("MyWiFi","12345678");//here to set the ssid and password of the Router
    Wifly.join("MyWiFi");
    Wifly.checkAssociated();
    while(!Wifly.connect("192.168.137.1","40020"));//connect the remote service
    Wifly.writeToSocket("Connected!");
  }
}

void loop(){
  Serial.print("Sensors:");
  for( int i = 0 ; i < 6 ; i++ ){
    analogRead(i);
    delay(10);
    sensors[i] = analogRead(i);
    Serial.print(sensors[i]);
    Serial.print(", ");
    delay(30);
  }
  Serial.println(";");
 
}


If i set wifi = true, then sensors show me some rubbish, every pin shows value is about 1010, and does not change on differenr ranges.
But when I set wifi = false, i.e. do not do wifly initialisation, everything works propally. I found that priblem in function WiFly.init() which do the next:

Code: Select all
void WiflyClass::init() {
   
   pinMode(WIFLY_RST, OUTPUT);
   pinMode(WIFLY_GPIO6, INPUT);
   SoftwareSerial::begin(9600);
   reset();
   unavailConn = 0;
}


This WiFly class is a child of SoftwareSerial class. I guess here some conflict between serial prints. Dd anyone face this problem?
Sorry for bad english.
Cheers!
Strohkopf
 
Posts: 2
Joined: Sat Nov 24, 2012 5:44 am

Re: Problem reading two sensors with analogRead()

Postby adafruit_support_bill » Sat Nov 24, 2012 6:19 am

If i set wifi = true, then sensors show me some rubbish, every pin shows value is about 1010, and does not change on differenr ranges.

Could be interference from the WiFly radio. Have you posted this over at Sparkfun to see if it is a known issue?
User avatar
adafruit_support_bill
 
Posts: 15918
Joined: Sat Feb 07, 2009 9:11 am

Re: Problem reading two sensors with analogRead()

Postby Strohkopf » Wed Dec 05, 2012 2:50 am

adafruit_support wrote:Could be interference from the WiFly radio. Have you posted this over at Sparkfun to see if it is a known issue?

Nope, they said that they do not support this shield.
Strohkopf
 
Posts: 2
Joined: Sat Nov 24, 2012 5:44 am

Re: Problem reading two sensors with analogRead()

Postby adafruit_support_bill » Wed Dec 05, 2012 5:48 am

Nope, they said that they do not support this shield.

Sorry, I meant SeeedStudio instead of SparkFun. They make a version of this shield also.
We do not have any experience with these shields and do not sell or support them here.
User avatar
adafruit_support_bill
 
Posts: 15918
Joined: Sat Feb 07, 2009 9:11 am

Re: Problem reading two sensors with analogRead()

Postby manrussian » Tue Jan 15, 2013 7:57 pm

Just registered here to say thanks for the informative thread. Had stability issues reading only a single TMP36 with my Uno while working on a smart web-enabled thermostat project where I would like to keep the temperature with 1 degree F.

I used the mentioned solution of just taking many samples and finding an average. In my case I'm sticking with 64 samples. Speed isn't a big issue as even with the over-sampling all other project functions seems responsive (web server, user parameter parsing, NTP time synchronization, etc).

Without this fix I would get swings of multiple degrees. With 16 samples it still wasn't to my liking. 64 seems to do the trick.

I'm using the default 5v reference, with power from USB. TMP36 current on breadboard via some cheap jumper cables.

Didn't explore hardware fixes like low-pass RC/LC filters as there's no need to increase physical space with the above software fix.

Here's the code in case it helps someone:

Code: Select all

#define tsp 5                  //temp sensor input port
#define ADCsamples 64          //Number of temperature sensor values to take for average
float tempCurrent = 0.0;       //current temperature

void readTemp() {
  float tempFlast = tempCurrent;                    //For monitoring temperature sensor/ADC noise
  float ADCavg = 0.0;                               //To store average ADC value
  float ADCsum = 0.0;                               //Store sum of ADC samples
  for (int i = 0; i < ADCsamples; i++) {
    ADCsum += analogRead(tsp);
  }
  ADCavg=ADCsum / (float)ADCsamples;
  float tspVolts = ADCavg * (aRef/1024.0);           //convert ADC value to voltage
  float tempC = (tspVolts - 0.5) * 100.0;            //convert voltage to Centigrate temp for TMP36 temp sensor
  float tempF = (tempC * 9.0 / 5.0) + 32.0;          //Convert Centigrade to Farenheit
  tempCurrent = tempF;                               //Set current temperature to user expected Farenheit value
  Serial.println(tempF - tempFlast);                 //Output difference from last average
}
manrussian
 
Posts: 2
Joined: Tue Jan 15, 2013 7:45 pm

Re: Problem reading two sensors with analogRead()

Postby adafruit_support_bill » Tue Jan 15, 2013 8:00 pm

I'm using the default 5v reference,

This does tend to be the noisiest reference on the Arduino, since it supplies all the digital logic too. The 3.3v reference is typically the most stable on this platform.
User avatar
adafruit_support_bill
 
Posts: 15918
Joined: Sat Feb 07, 2009 9:11 am

Re: Problem reading two sensors with analogRead()

Postby manrussian » Wed Jan 16, 2013 3:56 pm

Any thoughts on whether the 3.3V is more or less stable than the "INTERNAL" analog reference described here?

http://arduino.cc/en/Reference/AnalogReference

Seems for my Uno that would be 1.1V. If my arithmetic is correct, with a TMP36 (.5v offset and 10mV per degree C) I can still measure up to 60 degrees C, or 140 degrees F. This would be plenty for my home thermostat project.

The advantages I see to this are:

1 - Less external connections (no need to connect 3.3V pin to aRef pin)
2 - Doesn't rely on external 3.3V regulator on Arduino.

Of course in all of the above I'm ignoring other noise sources like stray capacitance and unshielded cables that have been discussed earlier, but I'm willing to take what I can get while keeping external parts/connection to a minimum.
manrussian
 
Posts: 2
Joined: Tue Jan 15, 2013 7:45 pm


Previous

Return to Arduino

Who is online

Users browsing this forum: No registered users and 11 guests

Stuff to buy from the Adafruit store and links to product documentation!


New Products [102]

Raspberry Pi[80]
 
FLORA[23]
 
Bunnie Studios[9]
 
FPGA[1]
 
mbed[11]
Arduino[60]
 
NETduino[14]
 
BeagleBone[24]
 
Android[6]
 
XBee[10]
More Dev Boards[30]


 
BoArduino[8]
 
SpokePOV[4]
 
TV-B-Gone[4]
 
MiniPOV[3]
 
SIM reader[3]
 
Microtouch[5]
 
Clocks & Watches[18]
 
Drawdio[4]
 
Brain Machine[1]
 
Game of Life[2]
 
MintyBoost[2]
More DIY Kits[16]


 
MaKey MaKey[3]
 
Tweet-a-Watt[5]
 
Young Engineers[33]
 
Discover Electronics[2]
 
Snap Circuits[4]
 
littleBits[3]
 
Project packs[8]


 
Breakout Boards[33]
LCDs & Displays[48]
Components & Parts[69]
Batteries & Power[49]
EL Wire/Tape/Panel[52]
LEDs[108]
 
Wireless[14]
Cables[60]
 
Lasers[6]
Sensors/Parts[145]
 
Enclosures/Cases[11]
 
Solar[11]
 
RFID / NFC[13]
Prototyping[69]
 
iDevices[13]
Tools[71]
 
Wearables[39]
 
CNC[37]
 
Robotics[29]
 
3D printing[1]
 
Materials[24]


 
Stickers[41]
 
Skill badges[55]
 
Books[25]
 
Circuit Playground[7]
 
Gift Certificates[4]