@@ -155,7 +155,10 @@ def temp_f(self):
155155
156156class Bmx280Spi :
157157 ''' Class to represent a BME280 or BMP280 sensor connected via an SPI bus '''
158- def __init__ (self , spiBus :int , cs_pin :int , cs_chip = None , set_spi_hz = True , logger = None ):
158+ def __init__ (self , spiBus :int , cs_pin :int , cs_chip = None , set_spi_hz = True , logger = None ,
159+ temp_enable = True , pressure_enable = True , humidity_enable = True , filter = 0 ,
160+ temp_oversample = 1 , pressure_oversample = 1 , humidity_oversample = 1 ,
161+ mode = MODE_FORCED , sleep_duration = 0 ):
159162 self ._lock = Lock ()
160163 self ._log_extra = f"SPI{ spiBus } .{ cs_pin } "
161164 self ._logger = logger if logger is not None else logging_handler .create_logger ('DEBUG' if DEBUG else 'INFO' )
@@ -224,6 +227,57 @@ def __init__(self, spiBus:int, cs_pin:int, cs_chip=None, set_spi_hz=True, logger
224227 ]
225228 self ._logger .debug (f"{ self .info_str } : Humidity Trim: { self ._trim_humid } " )
226229
230+ # init the sensor
231+ self .init (temp_enable = temp_enable , pressure_enable = pressure_enable , humidity_enable = humidity_enable ,
232+ temp_oversample = temp_oversample , pressure_oversample = pressure_oversample ,
233+ humidity_oversample = humidity_oversample , mode = mode , sleep_duration = sleep_duration , filter = filter )
234+
235+ def init (self , temp_enable = True , pressure_enable = True , humidity_enable = True , filter = 0 ,
236+ temp_oversample = 1 , pressure_oversample = 1 , humidity_oversample = 1 ,
237+ mode = MODE_FORCED , sleep_duration = 0 ) -> bool :
238+ ''' Initialize the sensor with the bulk settings
239+ Parameters:
240+ temp_enable (bool:True) - Enables the temperature sensor
241+ humidity_enable (bool:True) - Enables the humidity sensor (if available)
242+ pressure_enable (bool:True) - Enables the pressure sensor
243+ filter (int:0) - Enables the filter (averages readings to reduce fluctuations)
244+ Supports 0, 2, 4, 8 and 16. Formula is data_filtered = (previous_data * (filter - 1) + new_data) / filter
245+ temp_oversample (int:1) - Sets the oversampling rate for temp sensor (0,1,2,4,8) (0 disables the sensor)
246+ humidity_oversample (int:1) - Sets the oversampling rate for humidity sensor (0,1,2,4,8) (0 disables the sensor)
247+ pressure_oversample (int:1) - Sets the oversampling rate for pressure sensor (0,1,2,4,8) (0 disables the sensor)
248+ mode (int:1) - MODE_STANDBY = 0, MODE_FORCED = 1, MODE_NORMAL = 3
249+
250+ Returns:
251+ True - Settings were successful
252+ False - An error occured
253+ '''
254+ if not self .set_filter (filter ):
255+ return False
256+ if not self .set_sleep_duration_value (sleep_duration ):
257+ return False
258+ if not self .set_power_mode (mode ):
259+ return False
260+ if temp_enable :
261+ if not self .set_temp_oversample (temp_oversample if temp_oversample >= 1 else 1 ):
262+ return False
263+ else :
264+ if not self .set_temp_oversample (0 ):
265+ return False
266+ if pressure_enable :
267+ if not self .set_pressure_oversample (pressure_oversample if pressure_oversample >= 1 else 1 ):
268+ return False
269+ else :
270+ if not self .set_pressure_oversample (0 ):
271+ return False
272+ if self .model == 'BME280' :
273+ if humidity_enable :
274+ if not self .set_humidity_oversample (humidity_oversample if humidity_oversample >= 1 else 1 ):
275+ return False
276+ else :
277+ if not self .set_humidity_oversample (0 ):
278+ return False
279+ return True
280+
227281 def _read_reg (self , reg :int , count = 1 ) -> int :
228282 ''' Read a register and return the value '''
229283 with self ._lock :
@@ -234,19 +288,20 @@ def _read_reg(self, reg:int, count=1) -> int:
234288 self ._logger .debug (f"{ self .info_str } : Read Register: { reg } , value: { value } " )
235289 return value [0 ] if isinstance (value , list ) and len (value ) == 1 else value
236290
237- def _write_single_reg (self , reg :int , value :int , retries = WRITE_RETRY , retry_delay = WRITE_RETRY_DELAY ) -> bool :
291+ def _write_single_reg (self , reg :int , value :int , retries = WRITE_RETRY , retry_delay = WRITE_RETRY_DELAY , check_reply = True ) -> bool :
238292 '''Write a single register. Returns True/False if successful (tested by reading back from the sensor) '''
239293 for x in range (retries ):
240294 with self ._lock :
241295 self ._logger .debug (f"{ self .info_str } : Writing Register: { reg } , value: { value } " )
242296 self ._cs .low ()
243297 self ._spi .xfer ([reg & ~ WRITE_MASK , value ])
244298 self ._cs .high ()
245- updated_value = self ._read_reg (reg )
246- if value == updated_value :
247- return True
248- self ._logger .warning (f"{ self .info_str } : Write error to reg { reg } . Sending { value } , device returned { updated_value } . Retry { x + 1 } /{ retries } after { retry_delay } sec" )
249- sleep (retry_delay )
299+ if check_reply :
300+ updated_value = self ._read_reg (reg )
301+ if value == updated_value :
302+ return True
303+ self ._logger .warning (f"{ self .info_str } : Write error to reg { reg } . Sending { value } , device returned { updated_value } . Retry { x + 1 } /{ retries } after { retry_delay } sec" )
304+ sleep (retry_delay )
250305
251306 def get_filter (self ) -> int :
252307 ''' Read the filter coefficient from the sensor '''
@@ -318,7 +373,7 @@ def set_power_mode(self, value) -> bool:
318373 press_ovsmpl = ctrl_meas & REG_CTRL_MEAS_PRESS_OVERSMPL
319374 temp_ovsmpl = ctrl_meas & REG_CTRL_MEAS_TEMP_OVERSMPL
320375 self ._logger .debug (f"{ self .info_str } : Setting Power Mode to: { value } . Existing: { (ctrl_meas & REG_CTRL_MEAS_POWER ) >> get_trailing_bits (REG_CTRL_MEAS_POWER )} " )
321- return self ._write_single_reg (REG_CTRL_MEAS , temp_ovsmpl + press_ovsmpl + set_bits ( MODE_VALUES . index ( value ), REG_CTRL_MEAS_POWER ) )
376+ return self ._write_single_reg (REG_CTRL_MEAS , temp_ovsmpl + press_ovsmpl + ( value if value in MODE_VALUES else 1 ), check_reply = False if value == MODE_FORCED else True )
322377
323378 def set_temp_oversample (self , value ) -> bool :
324379 ''' Write the oversample rate for the temp sensor. Values 0,1,2,4,8,16 supported. Returns True/False if successful '''
@@ -375,7 +430,7 @@ def update_readings(self, timeout=2):
375430 If in standby - set to force and get reading
376431 If in normal - collect the last readings from the register
377432 Returns an instance of Bmx280Readings containing the readings '''
378- if self .get_power_mode () == MODE_FORCED :
433+ if self .get_power_mode () == MODE_STANDBY :
379434 # set to forced and wait for the sensor to complete
380435 cancel_time = time () + timeout
381436 self .set_power_mode (MODE_FORCED )
0 commit comments