ESPHome 2025.10.0-dev
Loading...
Searching...
No Matches
veml3235.cpp
Go to the documentation of this file.
1#include "veml3235.h"
3#include "esphome/core/log.h"
4
5namespace esphome {
6namespace veml3235 {
7
8static const char *const TAG = "veml3235.sensor";
9
11 uint8_t device_id[] = {0, 0};
12 if (!this->refresh_config_reg()) {
13 ESP_LOGE(TAG, "Unable to write configuration");
14 this->mark_failed();
15 return;
16 }
17 if ((this->read_register(ID_REG, device_id, sizeof device_id) != i2c::ERROR_OK)) {
18 ESP_LOGE(TAG, "Unable to read ID");
19 this->mark_failed();
20 } else if (device_id[0] != DEVICE_ID) {
21 ESP_LOGE(TAG, "Incorrect device ID - expected 0x%.2x, read 0x%.2x", DEVICE_ID, device_id[0]);
22 this->mark_failed();
23 }
24}
25
27 uint16_t data = this->power_on_ || force_on ? 0 : SHUTDOWN_BITS;
28
29 data |= (uint16_t(this->integration_time_ << CONFIG_REG_IT_BIT));
30 data |= (uint16_t(this->digital_gain_ << CONFIG_REG_DG_BIT));
31 data |= (uint16_t(this->gain_ << CONFIG_REG_G_BIT));
32 data |= 0x1; // mandatory 1 here per RM
33
34 ESP_LOGVV(TAG, "Writing 0x%.4x to register 0x%.2x", data, CONFIG_REG);
35 return this->write_byte_16(CONFIG_REG, data);
36}
37
39 if (!this->power_on_) { // if off, turn on
40 if (!this->refresh_config_reg(true)) {
41 ESP_LOGW(TAG, "Turning on failed");
42 this->status_set_warning();
43 return NAN;
44 }
45 delay(4); // from RM: a wait time of 4 ms should be observed before the first measurement is picked up, to allow
46 // for a correct start of the signal processor and oscillator
47 }
48
49 uint8_t als_regs[] = {0, 0};
50 if ((this->read_register(ALS_REG, als_regs, sizeof als_regs) != i2c::ERROR_OK)) {
51 this->status_set_warning();
52 return NAN;
53 }
54
56
57 float als_raw_value_multiplier = LUX_MULTIPLIER_BASE;
58 uint16_t als_raw_value = encode_uint16(als_regs[1], als_regs[0]);
59 // determine multiplier value based on gains and integration time
61 als_raw_value_multiplier *= 2;
62 }
63 switch (this->gain_) {
65 als_raw_value_multiplier *= 4;
66 break;
68 als_raw_value_multiplier *= 2;
69 break;
70 default:
71 break;
72 }
73 switch (this->integration_time_) {
75 als_raw_value_multiplier *= 16;
76 break;
78 als_raw_value_multiplier *= 8;
79 break;
81 als_raw_value_multiplier *= 4;
82 break;
84 als_raw_value_multiplier *= 2;
85 break;
86 default:
87 break;
88 }
89 // finally, determine and return the actual lux value
90 float lx = float(als_raw_value) * als_raw_value_multiplier;
91 ESP_LOGVV(TAG, "'%s': ALS raw = %u, multiplier = %.5f", this->get_name().c_str(), als_raw_value,
92 als_raw_value_multiplier);
93 ESP_LOGD(TAG, "'%s': Illuminance = %.4flx", this->get_name().c_str(), lx);
94
95 if (!this->power_on_) { // turn off if required
96 if (!this->refresh_config_reg()) {
97 ESP_LOGW(TAG, "Turning off failed");
98 this->status_set_warning();
99 }
100 }
101
102 if (this->auto_gain_) {
103 this->adjust_gain_(als_raw_value);
104 }
105
106 return lx;
107}
108
109void VEML3235Sensor::adjust_gain_(const uint16_t als_raw_value) {
110 if ((als_raw_value > UINT16_MAX * this->auto_gain_threshold_low_) &&
111 (als_raw_value < UINT16_MAX * this->auto_gain_threshold_high_)) {
112 return;
113 }
114
115 if (als_raw_value >= UINT16_MAX * 0.9) { // over-saturated, reset all gains and start over
117 this->gain_ = VEML3235_GAIN_1X;
119 this->refresh_config_reg();
120 return;
121 }
122
123 if (this->gain_ != VEML3235_GAIN_4X) { // increase gain if possible
124 switch (this->gain_) {
125 case VEML3235_GAIN_1X:
126 this->gain_ = VEML3235_GAIN_2X;
127 break;
128 case VEML3235_GAIN_2X:
129 this->gain_ = VEML3235_GAIN_4X;
130 break;
131 default:
132 break;
133 }
134 this->refresh_config_reg();
135 return;
136 }
137 // gain is maxed out; reset it and try to increase digital gain
138 if (this->digital_gain_ != VEML3235_DIGITAL_GAIN_2X) { // increase digital gain if possible
140 this->gain_ = VEML3235_GAIN_1X;
141 this->refresh_config_reg();
142 return;
143 }
144 // digital gain is maxed out; reset it and try to increase integration time
145 if (this->integration_time_ != VEML3235_INTEGRATION_TIME_800MS) { // increase integration time if possible
146 switch (this->integration_time_) {
149 break;
152 break;
155 break;
158 break;
159 default:
160 break;
161 }
163 this->gain_ = VEML3235_GAIN_1X;
164 this->refresh_config_reg();
165 return;
166 }
167}
168
170 uint8_t digital_gain = 1;
171 uint8_t gain = 1;
172 uint16_t integration_time = 0;
173
175 digital_gain = 2;
176 }
177 switch (this->gain_) {
178 case VEML3235_GAIN_2X:
179 gain = 2;
180 break;
181 case VEML3235_GAIN_4X:
182 gain = 4;
183 break;
184 default:
185 break;
186 }
187 switch (this->integration_time_) {
189 integration_time = 50;
190 break;
192 integration_time = 100;
193 break;
195 integration_time = 200;
196 break;
198 integration_time = 400;
199 break;
201 integration_time = 800;
202 break;
203 default:
204 break;
205 }
206
207 LOG_SENSOR("", "VEML3235", this);
208 LOG_I2C_DEVICE(this);
209 if (this->is_failed()) {
210 ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
211 }
212 LOG_UPDATE_INTERVAL(this);
213 ESP_LOGCONFIG(TAG, " Auto-gain enabled: %s", YESNO(this->auto_gain_));
214 if (this->auto_gain_) {
215 ESP_LOGCONFIG(TAG,
216 " Auto-gain upper threshold: %f%%\n"
217 " Auto-gain lower threshold: %f%%\n"
218 " Values below will be used as initial values only",
219 this->auto_gain_threshold_high_ * 100.0, this->auto_gain_threshold_low_ * 100.0);
220 }
221 ESP_LOGCONFIG(TAG,
222 " Digital gain: %uX\n"
223 " Gain: %uX\n"
224 " Integration time: %ums",
226}
227
228} // namespace veml3235
229} // namespace esphome
virtual void mark_failed()
Mark this component as failed.
bool is_failed() const
void status_set_warning(const char *message=nullptr)
void status_clear_warning()
const StringRef & get_name() const
ErrorCode read_register(uint8_t a_register, uint8_t *data, size_t len)
reads an array of bytes from a specific register in the I²C device
Definition i2c.cpp:32
bool write_byte_16(uint8_t a_register, uint16_t data) const
Definition i2c.h:268
VEML3235ComponentIntegrationTime integration_time_
Definition veml3235.h:104
VEML3235ComponentGain gain()
Definition veml3235.h:88
void adjust_gain_(uint16_t als_raw_value)
Definition veml3235.cpp:109
VEML3235ComponentIntegrationTime integration_time()
Definition veml3235.h:89
VEML3235ComponentGain gain_
Definition veml3235.h:103
VEML3235ComponentDigitalGain digital_gain()
Definition veml3235.h:87
VEML3235ComponentDigitalGain digital_gain_
Definition veml3235.h:102
bool refresh_config_reg(bool force_on=false)
Definition veml3235.cpp:26
@ ERROR_OK
No error found during execution of method.
Definition i2c_bus.h:33
@ VEML3235_INTEGRATION_TIME_100MS
Definition veml3235.h:40
@ VEML3235_INTEGRATION_TIME_200MS
Definition veml3235.h:41
@ VEML3235_INTEGRATION_TIME_50MS
Definition veml3235.h:39
@ VEML3235_INTEGRATION_TIME_800MS
Definition veml3235.h:43
@ VEML3235_INTEGRATION_TIME_400MS
Definition veml3235.h:42
Providing packet encoding functions for exchanging data with a remote host.
Definition a01nyub.cpp:7
constexpr uint16_t encode_uint16(uint8_t msb, uint8_t lsb)
Encode a 16-bit value given the most and least significant byte.
Definition helpers.h:185
void IRAM_ATTR HOT delay(uint32_t ms)
Definition core.cpp:29