0

I've connected my ADS1115 to an Arduino Uno as in the diagram (Vdd - 5V, Gnd - Gnd, SDA/SCL - SDA/SCL), all powered from the USB on a PC, with A0-3 unconnected, and am getting readings of around 3000 (i.e. 3000/65535 on 5V supply = 0.23V) from all four analog pins. Then if I connect them to 3.3V output on the arduino they give me only 17625 (i.e. 1.34V) i.e. about 40% of the full range I expected. If I try with a seperate 5V supply, it's still the same problem. Why is this?

P.S. sorry the code format below isn't very good, but basically it reads the four pins by
int16_t V1 = ads.readADC_SingleEnded(PIN).

enter image description here

#define THERMISTORPIN1 0
#define THERMISTORPIN2 1
#define SHELLPTPIN 2
#define SPAREPIN 3
#include < Wire.h >
#include < Adafruit_ADS1015.h >

Adafruit_ADS1115 ads(0x48);  //16 bit ADC add-on for arduino for better temperature resolution
float Voltage = 0.0;

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

void loop(void)
{
    int16_t V1;
    int16_t V2;
    int16_t V3;
    int16_t V4;
    long cumV1;
    long cumV2;
    long cumV3;
    long cumV4;
    float avgV1;
    float avgV2;
    float avgV3;
    float avgV4;

    //take readings of voltages between resistor and thermsitor
    int i=0;

    while(i<6) {
        V1 = ads.readADC_SingleEnded(THERMISTORPIN1); //5 readings to allow the arduino capacitors to equalize with the pin voltage, to increase accuracy
        V2 = ads.readADC_SingleEnded(THERMISTORPIN2);
        V3 = ads.readADC_SingleEnded(SHELLPTPIN);
        V4 = ads.readADC_SingleEnded(SPAREPIN);
        i++;
        delay(10);
    }

    while(6<=i && i<16) {
        cumV1+= ads.readADC_SingleEnded(THERMISTORPIN1);  //multiple measurements from which to take an average, to increase precision
        cumV2+= ads.readADC_SingleEnded(THERMISTORPIN2);
        cumV3+= ads.readADC_SingleEnded(SHELLPTPIN);
        cumV4+= ads.readADC_SingleEnded(SPAREPIN);
        i++;
        delay(10);
    }

    avgV1=cumV1/10;
    avgV2=cumV2/10;
    avgV3=cumV3/10;
    avgV4=cumV4/10;

    //print out information to serial monitor on laptop
    Serial.print(V1);
    Serial.print(" ");
    Serial.print(V2);
    Serial.print(" ");
    Serial.print(V3);
    Serial.print(" ");
    Serial.println(V4);
    Serial.print(" ");
    Serial.print(avgV1);
    Serial.print(" ");
    Serial.print(avgV2);
    Serial.print(" ");
    Serial.print(avgV3);
    Serial.print(" ");
    Serial.println(avgV4);
    //Serial.println();
    delay(1000);
}
1
  • first off, single ended readings are only 15 bit. secondly, providing 3.3v will limit the measurement to 3.3v; 66% of 5v. – dandavis Feb 15 '18 at 12:34
1

Your readings are correct because you have the default gain set. You have incorrectly assumed that you can convert the ADC reading from your 16-bit ADC to Volts by dividing by 2^16 - 1. Your ADC has gain settings to have more accurate readings for certain voltage intervals. If we look at the example sketch, we see

 void setup(void) 
{
  Serial.begin(9600);
  Serial.println("Hello!");

  Serial.println("Getting single-ended readings from AIN0..3");
  Serial.println("ADC Range: +/- 6.144V (1 bit = 3mV/ADS1015, 0.1875mV/ADS1115)");

  // The ADC input range (or gain) can be changed via the following
  // functions, but be careful never to exceed VDD +0.3V max, or to
  // exceed the upper and lower limits if you adjust the input range!
  // Setting these values incorrectly may destroy your ADC!
  //                                                                ADS1015  ADS1115
  //                                                                -------  -------
  // ads.setGain(GAIN_TWOTHIRDS);  // 2/3x gain +/- 6.144V  1 bit = 3mV      0.1875mV (default)
  // ads.setGain(GAIN_ONE);        // 1x gain   +/- 4.096V  1 bit = 2mV      0.125mV
  // ads.setGain(GAIN_TWO);        // 2x gain   +/- 2.048V  1 bit = 1mV      0.0625mV
  // ads.setGain(GAIN_FOUR);       // 4x gain   +/- 1.024V  1 bit = 0.5mV    0.03125mV
  // ads.setGain(GAIN_EIGHT);      // 8x gain   +/- 0.512V  1 bit = 0.25mV   0.015625mV
  // ads.setGain(GAIN_SIXTEEN);    // 16x gain  +/- 0.256V  1 bit = 0.125mV  0.0078125mV

  ads.begin();
}

Your ADC has a default gain of 2/3, or 0.1875mV per count. You say when you connect 3.3V to the pin, you get a reading of 17625. Thus we have

17625 * 0.1875 / 1000.0 [V]
= 3.3046875 [V]

Which is a correct reading. A reading on a floating pin (nothing attached) is irrelevant. Use the correct factors from above to convert your read ADC value to voltage.

Side note: In line

avgV1=cumV1/10;

You have the float avgV1 on the left and cumV1 (a long) divided by 10 on the right; this will do a integer division. Make sure to divide by 10.0f if you want a floating point average.

Side note 2:

These factors do make sense. If you apply positive 6.144V on the 2/3rd gain setting, you will read the maximum positive value of a int16_t, i.e. 2^15-1 = 32767 (solve above formula for the count). If you apply -6.144V, you get -32768; thus the full 16-bit number space is used. On differnt gain settings it analogous.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.