@@ -42,6 +42,9 @@ class WipperSnapper_I2C_Driver_SCD4X : public WipperSnapper_I2C_Driver {
4242 : WipperSnapper_I2C_Driver(i2c, sensorAddress) {
4343 _i2c = i2c;
4444 _sensorAddress = sensorAddress;
45+ _lastRead = 0 ;
46+ _temperature = 20.0 ;
47+ _humidity = 50.0 ;
4548 }
4649
4750 /* ******************************************************************************/
@@ -55,38 +58,69 @@ class WipperSnapper_I2C_Driver_SCD4X : public WipperSnapper_I2C_Driver {
5558 _scd->begin (*_i2c, _sensorAddress);
5659
5760 // stop previously started measurement
58- if (_scd->stopPeriodicMeasurement ())
61+ if (_scd->stopPeriodicMeasurement () != 0 ) {
5962 return false ;
63+ }
6064
6165 // start measurements
62- if (_scd->startPeriodicMeasurement ())
66+ if (_scd->startPeriodicMeasurement () != 0 ) {
6367 return false ;
68+ }
6469
6570 return true ;
6671 }
6772
68- /* *******************************************************************************/
73+ /* ******************************************************************************/
74+ /* !
75+ @brief Checks if sensor was read within last 1s, or is the first read.
76+ @returns True if the sensor was recently read, False otherwise.
77+ */
78+ bool hasBeenReadInLastSecond () {
79+ return _lastRead != 0 && millis () - _lastRead < 1000 ;
80+ }
81+
82+ /* ******************************************************************************/
6983 /* !
70- @brief Attempts to read the SCD4x's sensor measurements
71- @returns True if the measurements were read without errors, False
72- if read errors occured or if sensor did not have data ready.
84+ @brief Checks if the sensor is ready to be read
85+ @returns True if the sensor is ready, False otherwise.
7386 */
74- /* *******************************************************************************/
75- bool readSensorMeasurements () {
76- uint16_t error;
87+ /* ******************************************************************************/
88+ bool isSensorReady () {
7789 bool isDataReady = false ;
78- delay (100 );
90+ uint16_t error = _scd->getDataReadyStatus (isDataReady);
91+ if (error != 0 || !isDataReady) {
92+ // failed, one more quick attempt
93+ delay (100 );
94+ error = _scd->getDataReadyStatus (isDataReady);
95+ if (error != 0 || !isDataReady) {
96+ return false ;
97+ }
98+ }
99+ return true ;
100+ }
79101
80- // Check if data is ready
81- error = _scd->getDataReadyStatus (isDataReady);
82- if (error || !isDataReady)
102+ /* ******************************************************************************/
103+ /* !
104+ @brief Reads the sensor.
105+ @returns True if the sensor was read successfully, False otherwise.
106+ */
107+ /* ******************************************************************************/
108+ bool readSensorData () {
109+ // dont read sensor more than once per second
110+ if (hasBeenReadInLastSecond ()) {
111+ return true ;
112+ }
113+
114+ if (!isSensorReady ()) {
83115 return false ;
116+ }
84117
85118 // Read SCD4x measurement
86- error = _scd->readMeasurement (_co2, _temperature, _humidity);
87- if (error || _co2 == 0 )
119+ uint16_t error = _scd->readMeasurement (_co2, _temperature, _humidity);
120+ if (error != 0 || _co2 == 0 ) {
88121 return false ;
89-
122+ }
123+ _lastRead = millis ();
90124 return true ;
91125 }
92126
@@ -101,8 +135,9 @@ class WipperSnapper_I2C_Driver_SCD4X : public WipperSnapper_I2C_Driver {
101135 /* ******************************************************************************/
102136 bool getEventAmbientTemp (sensors_event_t *tempEvent) {
103137 // read all sensor measurements
104- if (!readSensorMeasurements ())
138+ if (!readSensorData ()) {
105139 return false ;
140+ }
106141
107142 tempEvent->temperature = _temperature;
108143 return true ;
@@ -119,8 +154,9 @@ class WipperSnapper_I2C_Driver_SCD4X : public WipperSnapper_I2C_Driver {
119154 /* ******************************************************************************/
120155 bool getEventRelativeHumidity (sensors_event_t *humidEvent) {
121156 // read all sensor measurements
122- if (!readSensorMeasurements ())
157+ if (!readSensorData ()) {
123158 return false ;
159+ }
124160
125161 humidEvent->relative_humidity = _humidity;
126162 return true ;
@@ -137,18 +173,20 @@ class WipperSnapper_I2C_Driver_SCD4X : public WipperSnapper_I2C_Driver {
137173 /* ******************************************************************************/
138174 bool getEventCO2 (sensors_event_t *co2Event) {
139175 // read all sensor measurements
140- if (!readSensorMeasurements ())
176+ if (!readSensorData ()) {
141177 return false ;
178+ }
142179
143180 co2Event->CO2 = (float )_co2;
144181 return true ;
145182 }
146183
147184protected:
148- SensirionI2cScd4x *_scd; // /< SCD4x driver object
149- uint16_t _co2; // /< SCD4x co2 reading
150- float _temperature; // /< SCD4x temperature reading
151- float _humidity; // /< SCD4x humidity reading
185+ SensirionI2cScd4x *_scd = nullptr ; // /< SCD4x driver object
186+ uint16_t _co2 = 0 ; // /< SCD4x co2 reading
187+ float _temperature; // /< SCD4x temperature reading
188+ float _humidity; // /< SCD4x humidity reading
189+ ulong _lastRead; // /< Last time the sensor was read
152190};
153191
154- #endif // WipperSnapper_I2C_Driver_SCD4X
192+ #endif // WipperSnapper_I2C_Driver_SCD4X_H
0 commit comments