diff --git a/README.md b/README.md index 5257b8d..77b42b7 100644 --- a/README.md +++ b/README.md @@ -29,3 +29,7 @@ The `values` property is a convenience function that provides a tuple of human-r * `temperature`: the temperature in hundredths of a degree celsius. For example, the value 2534 indicates a temperature of 25.34 degrees. * `pressure`: the atmospheric pressure. This 32-bit value consists of 24 bits indicating the integer value, and 8 bits indicating the fractional value. To get a value in Pascals, divide the return value by 256. For example, a value of 24674867 indicates 96386.2Pa, or 963.862hPa. * `humidity`: the relative humidity. This 32-bit value consists of 22 bits indicating the integer value, and 10 bits indicating the fractional value. To get a value in %RH, divide the return value by 1024. For example, a value of 47445 indicates 46.333%RH. + +The BME280 constructor takes an optional `address` argument. BME280 devices are +on I2C addresses 0x76 or 0x77. If you do not provide an address the driver will +scan for a device and use it, raising an exception if no device is found. diff --git a/bme280.py b/bme280.py index 856f967..759824c 100644 --- a/bme280.py +++ b/bme280.py @@ -37,8 +37,8 @@ from ustruct import unpack, unpack_from from array import array from micropython import const -# BME280 default address. -BME280_I2CADDR = const(0x76) +# BME280 default addresses. +BME280_I2CADDRS = (0x76, 0x77) # Operating Modes BME280_OSAMPLE_1 = const(1) @@ -55,23 +55,29 @@ class BME280: def __init__(self, mode=BME280_OSAMPLE_1, - address=BME280_I2CADDR, + address=None, i2c=None): # Check that mode is valid. - if mode not in range(1,6): + if mode < BME280_OSAMPLE_1 or mode > BME280_OSAMPLE_16: raise ValueError( 'Unexpected mode value {0}. Set mode to one of ' 'BME280_OSAMPLE_1, BME280_OSAMPLE_2, BME280_OSAMPLE_4, ' 'BME280_OSAMPLE_8 or BME280_OSAMPLE_16'.format(mode)) self._mode = mode - self.address = address if i2c is None: raise ValueError('An I2C object is required.') + if address is not None: + self.address = address + else: + addr = [a for a in i2c.scan() if a in BME280_I2CADDRS] + if len(addr) == 0: + raise RuntimeError('No BME280 found.') + self.address = addr[0] # 1st device found self.i2c = i2c # load calibration data - dig_88_a1 = self.i2c.readfrom_mem(self.address, 0x88, 26) - dig_e1_e7 = self.i2c.readfrom_mem(self.address, 0xE1, 7) + dig_88_a1 = i2c.readfrom_mem(self.address, 0x88, 26) + dig_e1_e7 = i2c.readfrom_mem(self.address, 0xE1, 7) self.dig_T1, self.dig_T2, self.dig_T3, self.dig_P1, \ self.dig_P2, self.dig_P3, self.dig_P4, self.dig_P5, \ self.dig_P6, self.dig_P7, self.dig_P8, self.dig_P9, \ @@ -86,7 +92,7 @@ class BME280: self.dig_H6 = unpack_from("