Skip to content

Commit 20df1f2

Browse files
committed
major changes to just ADS1115
1 parent 69e7ef6 commit 20df1f2

File tree

3 files changed

+353
-0
lines changed

3 files changed

+353
-0
lines changed

ADS1115/ADS1115.py

Lines changed: 177 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,177 @@
1+
#!/usr/bin/python3
2+
3+
import time
4+
import smbus
5+
from I2C import Adafruit_I2C
6+
7+
# ===========================================================================
8+
# ADS1115 Class
9+
# ===========================================================================
10+
class ADS1115:
11+
i2c = None
12+
13+
# IC Identifiers
14+
__IC_ADS1115 = 0x01
15+
16+
# Config Register
17+
__ADS1115_REG_CONFIG_DR_8SPS = 0x0000 # 8 samples per second
18+
__ADS1115_REG_CONFIG_DR_16SPS = 0x0020 # 16 samples per second
19+
__ADS1115_REG_CONFIG_DR_32SPS = 0x0040 # 32 samples per second
20+
__ADS1115_REG_CONFIG_DR_64SPS = 0x0060 # 64 samples per second
21+
__ADS1115_REG_CONFIG_DR_128SPS = 0x0080 # 128 samples per second
22+
__ADS1115_REG_CONFIG_DR_250SPS = 0x00A0 # 250 samples per second (default)
23+
__ADS1115_REG_CONFIG_DR_475SPS = 0x00C0 # 475 samples per second
24+
__ADS1115_REG_CONFIG_DR_860SPS = 0x00E0 # 860 samples per second
25+
26+
__ADS1015_REG_CONFIG_CQUE_MASK = 0x0003
27+
__ADS1015_REG_CONFIG_CQUE_1CONV = 0x0000 # Assert ALERT/RDY after one conversions
28+
__ADS1015_REG_CONFIG_CQUE_2CONV = 0x0001 # Assert ALERT/RDY after two conversions
29+
__ADS1015_REG_CONFIG_CQUE_4CONV = 0x0002 # Assert ALERT/RDY after four conversions
30+
__ADS1015_REG_CONFIG_CQUE_NONE = 0x0003 # Disable the comparator and put ALERT/RDY in high state (default)
31+
32+
__ADS1015_REG_CONFIG_CMODE_MASK = 0x0010
33+
__ADS1015_REG_CONFIG_CMODE_TRAD = 0x0000 # Traditional comparator with hysteresis (default)
34+
__ADS1015_REG_CONFIG_CMODE_WINDOW = 0x0010 # Window comparator
35+
36+
__ADS1015_REG_CONFIG_CPOL_MASK = 0x0008
37+
__ADS1015_REG_CONFIG_CPOL_ACTVLOW = 0x0000 # ALERT/RDY pin is low when active (default)
38+
__ADS1015_REG_CONFIG_CPOL_ACTVHI = 0x0008 # ALERT/RDY pin is high when active
39+
40+
__ADS1015_REG_CONFIG_CLAT_MASK = 0x0004 # Determines if ALERT/RDY pin latches once asserted
41+
__ADS1015_REG_CONFIG_CLAT_NONLAT = 0x0000 # Non-latching comparator (default)
42+
__ADS1015_REG_CONFIG_CLAT_LATCH = 0x0004 # Latching comparator
43+
44+
__ADS1015_REG_CONFIG_MODE_MASK = 0x0100
45+
__ADS1015_REG_CONFIG_MODE_CONTIN = 0x0000 # Continuous conversion mode
46+
__ADS1015_REG_CONFIG_MODE_SINGLE = 0x0100 # Power-down single-shot mode (default)
47+
48+
__ADS1015_REG_CONFIG_PGA_MASK = 0x0E00
49+
__ADS1015_REG_CONFIG_PGA_6_144V = 0x0000 # +/-6.144V range
50+
__ADS1015_REG_CONFIG_PGA_4_096V = 0x0200 # +/-4.096V range
51+
__ADS1015_REG_CONFIG_PGA_2_048V = 0x0400 # +/-2.048V range (default)
52+
__ADS1015_REG_CONFIG_PGA_1_024V = 0x0600 # +/-1.024V range
53+
__ADS1015_REG_CONFIG_PGA_0_512V = 0x0800 # +/-0.512V range
54+
__ADS1015_REG_CONFIG_PGA_0_256V = 0x0A00 # +/-0.256V range
55+
56+
__ADS1015_REG_CONFIG_MUX_MASK = 0x7000
57+
__ADS1015_REG_CONFIG_MUX_DIFF_0_1 = 0x0000 # Differential P = AIN0, N = AIN1 (default)
58+
__ADS1015_REG_CONFIG_MUX_DIFF_0_3 = 0x1000 # Differential P = AIN0, N = AIN3
59+
__ADS1015_REG_CONFIG_MUX_DIFF_1_3 = 0x2000 # Differential P = AIN1, N = AIN3
60+
__ADS1015_REG_CONFIG_MUX_DIFF_2_3 = 0x3000 # Differential P = AIN2, N = AIN3
61+
__ADS1015_REG_CONFIG_MUX_SINGLE_0 = 0x4000 # Single-ended AIN0
62+
__ADS1015_REG_CONFIG_MUX_SINGLE_1 = 0x5000 # Single-ended AIN1
63+
__ADS1015_REG_CONFIG_MUX_SINGLE_2 = 0x6000 # Single-ended AIN2
64+
__ADS1015_REG_CONFIG_MUX_SINGLE_3 = 0x7000 # Single-ended AIN3
65+
66+
# Config Register
67+
__ADS1015_REG_CONFIG_OS_MASK = 0x8000
68+
__ADS1015_REG_CONFIG_OS_SINGLE = 0x8000 # Write: Set to start a single-conversion
69+
__ADS1015_REG_CONFIG_OS_BUSY = 0x0000 # Read: Bit = 0 when conversion is in progress
70+
__ADS1015_REG_CONFIG_OS_NOTBUSY = 0x8000 # Read: Bit = 1 when device is not performing a conversion
71+
72+
# Pointer Register
73+
__ADS1015_REG_POINTER_MASK = 0x03
74+
__ADS1015_REG_POINTER_CONVERT = 0x00
75+
__ADS1015_REG_POINTER_CONFIG = 0x01
76+
__ADS1015_REG_POINTER_LOWTHRESH = 0x02
77+
__ADS1015_REG_POINTER_HITHRESH = 0x03
78+
79+
# Dictionaries with the sampling speed values
80+
# These simplify and clean the code (avoid the abuse of if/elif/else clauses)
81+
spsADS1115 = {
82+
8:__ADS1115_REG_CONFIG_DR_8SPS,
83+
16:__ADS1115_REG_CONFIG_DR_16SPS,
84+
32:__ADS1115_REG_CONFIG_DR_32SPS,
85+
64:__ADS1115_REG_CONFIG_DR_64SPS,
86+
128:__ADS1115_REG_CONFIG_DR_128SPS,
87+
250:__ADS1115_REG_CONFIG_DR_250SPS,
88+
475:__ADS1115_REG_CONFIG_DR_475SPS,
89+
860:__ADS1115_REG_CONFIG_DR_860SPS
90+
}
91+
92+
# Dictionariy with the programable gains
93+
pgaADS1x15 = {
94+
6144:__ADS1015_REG_CONFIG_PGA_6_144V,
95+
4096:__ADS1015_REG_CONFIG_PGA_4_096V,
96+
2048:__ADS1015_REG_CONFIG_PGA_2_048V,
97+
1024:__ADS1015_REG_CONFIG_PGA_1_024V,
98+
512:__ADS1015_REG_CONFIG_PGA_0_512V,
99+
256:__ADS1015_REG_CONFIG_PGA_0_256V
100+
}
101+
102+
# Constructor
103+
def __init__(self, address=0x48, ic=__IC_ADS1115, debug=False):
104+
self.i2c = Adafruit_I2C(address)
105+
self.address = address
106+
self.debug = debug
107+
108+
# Make sure the IC specified is valid
109+
if (ic > self.__IC_ADS1115):
110+
return -1
111+
else:
112+
self.ic = ic
113+
114+
# Set pga value, so that getLastConversionResult() can use it,
115+
# any function that accepts a pga value must update this.
116+
self.pga = 6144
117+
118+
def readADCSingleEnded(self, channel=0, pga=6144, sps=250):
119+
'''
120+
Gets a single-ended ADC reading from the specified channel in mV.
121+
The sample rate for this mode (single-shot) can be used to lower the noise
122+
(low sps) or to lower the power consumption (high sps) by duty cycling,
123+
see datasheet page 14 for more info.
124+
The pga must be given in mV, see page 13 for the supported values.
125+
'''
126+
127+
# With invalid channel return -1
128+
if (channel > 3):
129+
return -1
130+
131+
# Disable comparator, Non-latching, Alert/Rdy active low
132+
# traditional comparator, single-shot mode
133+
config = self.__ADS1015_REG_CONFIG_CQUE_NONE | \
134+
self.__ADS1015_REG_CONFIG_CLAT_NONLAT | \
135+
self.__ADS1015_REG_CONFIG_CPOL_ACTVLOW | \
136+
self.__ADS1015_REG_CONFIG_CMODE_TRAD | \
137+
self.__ADS1015_REG_CONFIG_MODE_SINGLE
138+
139+
# Set sample per seconds, defaults to 250sps
140+
config |= self.spsADS1115.setdefault(sps, self.__ADS1115_REG_CONFIG_DR_250SPS)
141+
142+
# Set PGA/voltage range, defaults to +-6.144V
143+
config |= self.pgaADS1x15.setdefault(pga, self.__ADS1015_REG_CONFIG_PGA_6_144V)
144+
self.pga = pga
145+
146+
# Set the channel to be converted
147+
if channel == 3:
148+
config |= self.__ADS1015_REG_CONFIG_MUX_SINGLE_3
149+
elif channel == 2:
150+
config |= self.__ADS1015_REG_CONFIG_MUX_SINGLE_2
151+
elif channel == 1:
152+
config |= self.__ADS1015_REG_CONFIG_MUX_SINGLE_1
153+
else:
154+
config |= self.__ADS1015_REG_CONFIG_MUX_SINGLE_0
155+
156+
# Set 'start single-conversion' bit
157+
config |= self.__ADS1015_REG_CONFIG_OS_SINGLE
158+
159+
# Write config register to the ADC
160+
bytes = [(config >> 8) & 0xFF, config & 0xFF]
161+
self.i2c.writeList(self.__ADS1015_REG_POINTER_CONFIG, bytes)
162+
163+
# Wait for the ADC conversion to complete
164+
# The minimum delay depends on the sps: delay >= 1/sps
165+
# We add 0.1ms to be sure
166+
delay = 1.0/sps+0.0001
167+
time.sleep(delay)
168+
169+
# Read the conversion results
170+
result = self.i2c.readList(self.__ADS1015_REG_POINTER_CONVERT, 2)
171+
# Return a mV value for the ADS1115
172+
# (Take signed values into account as well)
173+
val = (result[0] << 8) | (result[1])
174+
if val > 0x7FFF:
175+
return (val - 0xFFFF)*pga/32768.0
176+
else:
177+
return ( (result[0] << 8) | (result[1]) )*pga/32768.0

ADS1115/I2C.py

Lines changed: 156 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,156 @@
1+
#!/usr/bin/python3
2+
import re
3+
import smbus
4+
5+
# ===========================================================================
6+
# Adafruit_I2C Class
7+
# ===========================================================================
8+
9+
class Adafruit_I2C(object):
10+
11+
@staticmethod
12+
def getPiRevision():
13+
"Gets the version number of the Raspberry Pi board"
14+
# Revision list available at: http://elinux.org/RPi_HardwareHistory#Board_Revision_History
15+
try:
16+
with open('/proc/cpuinfo', 'r') as infile:
17+
for line in infile:
18+
# Match a line of the form "Revision : 0002" while ignoring extra
19+
# info in front of the revsion (like 1000 when the Pi was over-volted).
20+
match = re.match('Revision\s+:\s+.*(\w{4})$', line)
21+
if match and match.group(1) in ['0000', '0002', '0003']:
22+
# Return revision 1 if revision ends with 0000, 0002 or 0003.
23+
return 1
24+
elif match:
25+
# Assume revision 2 if revision ends with any other 4 chars.
26+
return 2
27+
# Couldn't find the revision, assume revision 0 like older code for compatibility.
28+
return 0
29+
except:
30+
return 0
31+
32+
@staticmethod
33+
def getPiI2CBusNumber():
34+
# Gets the I2C bus number /dev/i2c#
35+
return 1 if Adafruit_I2C.getPiRevision() > 1 else 0
36+
37+
def __init__(self, address, busnum=-1, debug=False):
38+
self.address = address
39+
# By default, the correct I2C bus is auto-detected using /proc/cpuinfo
40+
# Alternatively, you can hard-code the bus version below:
41+
# self.bus = smbus.SMBus(0); # Force I2C0 (early 256MB Pi's)
42+
# self.bus = smbus.SMBus(1); # Force I2C1 (512MB Pi's)
43+
self.bus = smbus.SMBus(busnum if busnum >= 0 else Adafruit_I2C.getPiI2CBusNumber())
44+
self.debug = debug
45+
46+
def reverseByteOrder(self, data):
47+
''' Reverses the byte order of an int (16-bit) or long (32-bit) value '''
48+
byteCount = len(hex(data)[2:].replace('L','')[::2])
49+
val = 0
50+
for i in range(byteCount):
51+
val = (val << 8) | (data & 0xff)
52+
data >>= 8
53+
return val
54+
55+
def errMsg(self):
56+
print ("Error accessing 0x%02X: Check your I2C address" % self.address)
57+
return -1
58+
59+
def write8(self, reg, value):
60+
"Writes an 8-bit value to the specified register/address"
61+
try:
62+
self.bus.write_byte_data(self.address, reg, value)
63+
if self.debug:
64+
print ("I2C: Wrote 0x%02X to register 0x%02X" % (value, reg))
65+
except IOError:
66+
return self.errMsg()
67+
68+
def write16(self, reg, value):
69+
"Writes a 16-bit value to the specified register/address pair"
70+
try:
71+
self.bus.write_word_data(self.address, reg, value)
72+
if self.debug:
73+
print ("I2C: Wrote 0x%02X to register pair 0x%02X,0x%02X" % (value, reg, reg+1))
74+
except IOError:
75+
return self.errMsg()
76+
77+
def writeRaw8(self, value):
78+
"Writes an 8-bit value on the bus"
79+
try:
80+
self.bus.write_byte(self.address, value)
81+
if self.debug:
82+
print ("I2C: Wrote 0x%02X" % value)
83+
except IOError:
84+
return self.errMsg()
85+
86+
def writeList(self, reg, list):
87+
"Writes an array of bytes using I2C format"
88+
try:
89+
if self.debug:
90+
print ("I2C: Writing list to register 0x%02X:" % reg)
91+
print (list)
92+
self.bus.write_i2c_block_data(self.address, reg, list)
93+
except IOError:
94+
return self.errMsg()
95+
96+
def readList(self, reg, length):
97+
"Read a list of bytes from the I2C device"
98+
try:
99+
results = self.bus.read_i2c_block_data(self.address, reg, length)
100+
if self.debug:
101+
print ("I2C: Device 0x%02X returned the following from reg 0x%02X" % (self.address, reg))
102+
print (results)
103+
return results
104+
except IOError:
105+
return self.errMsg()
106+
107+
def readU8(self, reg):
108+
"Read an unsigned byte from the I2C device"
109+
try:
110+
result = self.bus.read_byte_data(self.address, reg)
111+
if self.debug:
112+
print ("I2C: Device 0x%02X returned 0x%02X from reg 0x%02X" % (self.address, result & 0xFF, reg))
113+
return (result)
114+
except IOError:
115+
return self.errMsg()
116+
117+
def readS8(self, reg):
118+
"Reads a signed byte from the I2C device"
119+
try:
120+
result = self.bus.read_byte_data(self.address, reg)
121+
if result > 127: result -= 256
122+
if self.debug:
123+
print ("I2C: Device 0x%02X returned 0x%02X from reg 0x%02X" % (self.address, result & 0xFF, reg))
124+
return result
125+
except IOError:
126+
return self.errMsg()
127+
128+
def readU16(self, reg, little_endian=True):
129+
"Reads an unsigned 16-bit value from the I2C device"
130+
try:
131+
result = self.bus.read_word_data(self.address,reg)
132+
# Swap bytes if using big endian because read_word_data assumes little
133+
# endian on ARM (little endian) systems.
134+
if not little_endian:
135+
result = ((result << 8) & 0xFF00) + (result >> 8)
136+
if (self.debug):
137+
print ("I2C: Device 0x%02X returned 0x%04X from reg 0x%02X" % (self.address, result & 0xFFFF, reg))
138+
return result
139+
except IOError:
140+
return self.errMsg()
141+
142+
def readS16(self, reg, little_endian=True):
143+
"Reads a signed 16-bit value from the I2C device"
144+
try:
145+
result = self.readU16(reg,little_endian)
146+
if result > 32767: result -= 65536
147+
return result
148+
except IOError:
149+
return self.errMsg()
150+
151+
if __name__ == '__main__':
152+
try:
153+
bus = Adafruit_I2C(address=0)
154+
print ("Default I2C bus is accessible")
155+
except:
156+
print ("Error accessing default I2C bus")

ADS1115/ads1x15_ex_singleended.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
#!/usr/bin/python3
2+
3+
from ADS1115 import ADS1115
4+
5+
ADS1115 = 0x01 # 16-bit ADC
6+
7+
# Select the gain
8+
gain = 6144 # +/- 6.144V
9+
10+
# Select the sample rate
11+
sps = 250 # 250 samples per second
12+
13+
# Initialise the ADC using the default mode (use default I2C address)
14+
# Set this to ADS1015 or ADS1115 depending on the ADC you are using!
15+
adc = ADS1115(ic=ADS1115)
16+
17+
# Read channel 0 in single-ended mode using the settings above
18+
volts = adc.readADCSingleEnded(0, gain, sps) / 1000
19+
20+
print ("0".format(volts))

0 commit comments

Comments
 (0)