ESPHome 2026.11.0-dev
Loading...
Searching...
No Matches
es7243.cpp
Go to the documentation of this file.
1#include "es7243.h"
2
3#ifdef USE_ESP32
4
5#include "esphome/core/hal.h"
6#include "esphome/core/log.h"
7
8#include <driver/gpio.h>
9
10#include <cmath>
11
12namespace esphome::es7243 {
13
14ESPHOME_LOG_TAG(TAG, "es7243");
15
16// Register map from the ES7243 datasheet
17static constexpr uint8_t REG_MODE_CONFIG = 0x00;
18static constexpr uint8_t REG_SDP_FORMAT = 0x01;
19static constexpr uint8_t REG_MUTE_CONTROL = 0x05;
20static constexpr uint8_t REG_STATE_CONTROL = 0x06;
21static constexpr uint8_t REG_GAIN = 0x08; // ANACTRL1
22static constexpr uint8_t MCLK_PULSES = 20;
23
24struct GainEntry {
25 float db;
26 uint8_t reg;
27};
28// Register 0x08 values for each gain, from the ESP-ADF es7243 driver
29static constexpr GainEntry GAIN_TABLE[] = {
30 {1.0f, 0x11}, {3.5f, 0x13}, {18.0f, 0x21}, {20.5f, 0x23},
31 {22.5f, 0x06}, {24.5f, 0x41}, {25.0f, 0x07}, {27.0f, 0x43},
32};
33static constexpr uint8_t GAIN_COUNT = sizeof(GAIN_TABLE) / sizeof(GAIN_TABLE[0]);
34
35// The table entry nearest the requested gain; values outside the table snap to its ends
36static uint8_t nearest_gain_index(float gain_db) {
37 uint8_t best = 0;
38 for (uint8_t i = 1; i < GAIN_COUNT; i++) {
39 if (std::fabs(gain_db - GAIN_TABLE[i].db) < std::fabs(gain_db - GAIN_TABLE[best].db))
40 best = i;
41 }
42 return best;
43}
44
46 // The chip ignores I2C until it has seen MCLK, so pulse the pin before the I2S peripheral takes it over
47 const gpio_num_t mclk = this->i2s_->get_pin_config().mclk;
48 gpio_reset_pin(mclk);
49 gpio_set_direction(mclk, GPIO_MODE_OUTPUT);
50 for (uint8_t i = 0; i < MCLK_PULSES; i++) {
51 gpio_set_level(mclk, 0);
52 delay(1);
53 gpio_set_level(mclk, 1);
54 delay(1);
55 }
56
57 // The ESP-ADF sequence: mute while the format and gain are set, then unmute
58 const bool ok = this->write_byte(REG_MODE_CONFIG, 0x01) && this->write_byte(REG_STATE_CONTROL, 0x00) &&
59 this->write_byte(REG_MUTE_CONTROL, 0x1B) && this->write_byte(REG_SDP_FORMAT, 0x0C) &&
60 this->write_mic_gain_() && this->write_byte(REG_MUTE_CONTROL, 0x13);
61 if (!ok) {
62 this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
63 return;
64 }
65 this->setup_complete_ = true;
66}
67
69 ESP_LOGCONFIG(TAG,
70 "ES7243 audio ADC:\n"
71 " Mic gain: %.1f dB",
72 this->mic_gain());
73 LOG_I2C_DEVICE(this);
74}
75
76float ES7243::mic_gain() { return GAIN_TABLE[this->gain_index_].db; }
77
78bool ES7243::set_mic_gain(float mic_gain) {
79 this->gain_index_ = nearest_gain_index(mic_gain);
80 if (!this->setup_complete_)
81 return true;
82 return this->status_comm_result(this->write_mic_gain_());
83}
84
85bool ES7243::write_mic_gain_() { return this->write_byte(REG_GAIN, GAIN_TABLE[this->gain_index_].reg); }
86
87} // namespace esphome::es7243
88
89#endif // USE_ESP32
void mark_failed()
Mark this component as failed.
bool status_comm_result(bool ok)
Clears the warning when ok, else sets it with message (default "Communication failed"); returns ok.
void dump_config() override
Definition es7243.cpp:68
const i2s_audio::I2SAudioComponent * i2s_
Definition es7243.h:29
float mic_gain() override
Definition es7243.cpp:76
void setup() override
Definition es7243.cpp:45
bool set_mic_gain(float mic_gain) override
Definition es7243.cpp:78
bool write_byte(uint8_t a_register, uint8_t data) const
Definition i2c.h:312
I2CRegister reg(uint8_t a_register)
calls the I2CRegister constructor
Definition i2c.h:164
i2s_std_gpio_config_t get_pin_config() const
Definition i2s_audio.h:89
ESPHOME_LOG_TAG(TAG, "es7243")
void HOT delay(uint32_t ms)
Definition hal.cpp:85