ESPHome 2025.9.0-dev
Loading...
Searching...
No Matches
hmc5883l.cpp
Go to the documentation of this file.
1#include "hmc5883l.h"
2#include "esphome/core/log.h"
4
5namespace esphome {
6namespace hmc5883l {
7
8static const char *const TAG = "hmc5883l";
9static const uint8_t HMC5883L_ADDRESS = 0x1E;
10static const uint8_t HMC5883L_REGISTER_CONFIG_A = 0x00;
11static const uint8_t HMC5883L_REGISTER_CONFIG_B = 0x01;
12static const uint8_t HMC5883L_REGISTER_MODE = 0x02;
13static const uint8_t HMC5883L_REGISTER_DATA_X_MSB = 0x03;
14static const uint8_t HMC5883L_REGISTER_DATA_X_LSB = 0x04;
15static const uint8_t HMC5883L_REGISTER_DATA_Z_MSB = 0x05;
16static const uint8_t HMC5883L_REGISTER_DATA_Z_LSB = 0x06;
17static const uint8_t HMC5883L_REGISTER_DATA_Y_MSB = 0x07;
18static const uint8_t HMC5883L_REGISTER_DATA_Y_LSB = 0x08;
19static const uint8_t HMC5883L_REGISTER_STATUS = 0x09;
20static const uint8_t HMC5883L_REGISTER_IDENTIFICATION_A = 0x0A;
21static const uint8_t HMC5883L_REGISTER_IDENTIFICATION_B = 0x0B;
22static const uint8_t HMC5883L_REGISTER_IDENTIFICATION_C = 0x0C;
23
25 uint8_t id[3];
26 if (!this->read_byte(HMC5883L_REGISTER_IDENTIFICATION_A, &id[0]) ||
27 !this->read_byte(HMC5883L_REGISTER_IDENTIFICATION_B, &id[1]) ||
28 !this->read_byte(HMC5883L_REGISTER_IDENTIFICATION_C, &id[2])) {
30 this->mark_failed();
31 return;
32 }
33
36 }
37
38 if (id[0] != 0x48 || id[1] != 0x34 || id[2] != 0x33) {
40 this->mark_failed();
41 return;
42 }
43
44 uint8_t config_a = 0;
45 config_a |= this->oversampling_ << 5;
46 config_a |= this->datarate_ << 2;
47 config_a |= 0b0 << 0; // Measurement Mode: Normal(high impedance on load)
48 if (!this->write_byte(HMC5883L_REGISTER_CONFIG_A, config_a)) {
50 this->mark_failed();
51 return;
52 }
53
54 uint8_t config_b = 0;
55 config_b |= this->range_ << 5;
56 if (!this->write_byte(HMC5883L_REGISTER_CONFIG_B, config_b)) {
58 this->mark_failed();
59 return;
60 }
61
62 uint8_t mode = 0;
63 // Continuous Measurement Mode
64 mode |= 0b00;
65 if (!this->write_byte(HMC5883L_REGISTER_MODE, mode)) {
67 this->mark_failed();
68 return;
69 }
70}
72 ESP_LOGCONFIG(TAG, "HMC5883L:");
73 LOG_I2C_DEVICE(this);
74 if (this->error_code_ == COMMUNICATION_FAILED) {
75 ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
76 } else if (this->error_code_ == ID_REGISTERS) {
77 ESP_LOGE(TAG, "The ID registers don't match - Is this really an HMC5883L?");
78 }
79 LOG_UPDATE_INTERVAL(this);
80
81 LOG_SENSOR(" ", "X Axis", this->x_sensor_);
82 LOG_SENSOR(" ", "Y Axis", this->y_sensor_);
83 LOG_SENSOR(" ", "Z Axis", this->z_sensor_);
84 LOG_SENSOR(" ", "Heading", this->heading_sensor_);
85}
88 uint16_t raw_x, raw_y, raw_z;
89 if (!this->read_byte_16(HMC5883L_REGISTER_DATA_X_MSB, &raw_x) ||
90 !this->read_byte_16(HMC5883L_REGISTER_DATA_Y_MSB, &raw_y) ||
91 !this->read_byte_16(HMC5883L_REGISTER_DATA_Z_MSB, &raw_z)) {
92 this->status_set_warning();
93 return;
94 }
95
96 float mg_per_bit;
97 switch (this->range_) {
99 mg_per_bit = 0.073f;
100 break;
102 mg_per_bit = 0.92f;
103 break;
105 mg_per_bit = 1.22f;
106 break;
108 mg_per_bit = 1.52f;
109 break;
111 mg_per_bit = 2.27f;
112 break;
114 mg_per_bit = 2.56f;
115 break;
117 mg_per_bit = 3.03f;
118 break;
120 mg_per_bit = 4.35f;
121 break;
122 default:
123 mg_per_bit = NAN;
124 }
125
126 // in µT
127 const float x = int16_t(raw_x) * mg_per_bit * 0.1f;
128 const float y = int16_t(raw_y) * mg_per_bit * 0.1f;
129 const float z = int16_t(raw_z) * mg_per_bit * 0.1f;
130
131 float heading = atan2f(0.0f - x, y) * 180.0f / M_PI;
132 ESP_LOGD(TAG, "Got x=%0.02fµT y=%0.02fµT z=%0.02fµT heading=%0.01f°", x, y, z, heading);
133
134 if (this->x_sensor_ != nullptr)
135 this->x_sensor_->publish_state(x);
136 if (this->y_sensor_ != nullptr)
137 this->y_sensor_->publish_state(y);
138 if (this->z_sensor_ != nullptr)
139 this->z_sensor_->publish_state(z);
140 if (this->heading_sensor_ != nullptr)
141 this->heading_sensor_->publish_state(heading);
142}
143
144} // namespace hmc5883l
145} // namespace esphome
BedjetMode mode
BedJet operating mode.
uint32_t get_loop_interval() const
virtual void mark_failed()
Mark this component as failed.
void status_set_warning(const char *message=nullptr)
void start()
Start running the loop continuously.
Definition helpers.cpp:564
virtual uint32_t get_update_interval() const
Get the update interval in ms of this sensor.
HighFrequencyLoopRequester high_freq_
Definition hmc5883l.h:66
HMC5883LOversampling oversampling_
Definition hmc5883l.h:54
float get_setup_priority() const override
Definition hmc5883l.cpp:86
enum esphome::hmc5883l::HMC5883LComponent::ErrorCode error_code_
bool write_byte(uint8_t a_register, uint8_t data, bool stop=true)
Definition i2c.h:266
bool read_byte_16(uint8_t a_register, uint16_t *data)
Definition i2c.h:250
bool read_byte(uint8_t a_register, uint8_t *data, bool stop=true)
Definition i2c.h:239
void publish_state(float state)
Publish a new state to the front-end.
Definition sensor.cpp:45
bool z
Definition msa3xx.h:1
const float DATA
For components that import data from directly connected sensors like DHT.
Definition component.cpp:50
Providing packet encoding functions for exchanging data with a remote host.
Definition a01nyub.cpp:7
Application App
Global storage of Application pointer - only one Application can exist.
uint16_t x
Definition tt21100.cpp:5
uint16_t y
Definition tt21100.cpp:6