ESPHome 2025.6.3
Loading...
Searching...
No Matches
my9231.cpp
Go to the documentation of this file.
1#include "my9231.h"
3#include "esphome/core/log.h"
4
5namespace esphome {
6namespace my9231 {
7
8static const char *const TAG = "my9231.output";
9
10// One-shot select (frame cycle repeat mode / frame cycle One-shot mode)
11static const uint8_t MY9231_CMD_ONE_SHOT_DISABLE = 0x0 << 6;
12static const uint8_t MY9231_CMD_ONE_SHOT_ENFORCE = 0x1 << 6;
13// Reaction time of Iout
14static const uint8_t MY9231_CMD_REACTION_FAST = 0x0 << 5;
15static const uint8_t MY9231_CMD_REACTION_SLOW = 0x1 << 5;
16// Grayscale resolution select
17static const uint8_t MY9231_CMD_BIT_WIDTH_16 = 0x0 << 3;
18static const uint8_t MY9231_CMD_BIT_WIDTH_14 = 0x1 << 3;
19static const uint8_t MY9231_CMD_BIT_WIDTH_12 = 0x2 << 3;
20static const uint8_t MY9231_CMD_BIT_WIDTH_8 = 0x3 << 3;
21// Internal oscillator freq. select (divider)
22static const uint8_t MY9231_CMD_FREQUENCY_DIVIDE_1 = 0x0 << 1;
23static const uint8_t MY9231_CMD_FREQUENCY_DIVIDE_4 = 0x1 << 1;
24static const uint8_t MY9231_CMD_FREQUENCY_DIVIDE_16 = 0x2 << 1;
25static const uint8_t MY9231_CMD_FREQUENCY_DIVIDE_64 = 0x3 << 1;
26// Output waveform
27static const uint8_t MY9231_CMD_SCATTER_APDM = 0x0 << 0;
28static const uint8_t MY9231_CMD_SCATTER_PWM = 0x1 << 0;
29
31 ESP_LOGCONFIG(TAG, "Running setup");
32 this->pin_di_->setup();
33 this->pin_di_->digital_write(false);
34 this->pin_dcki_->setup();
35 this->pin_dcki_->digital_write(false);
36 this->pwm_amounts_.resize(this->num_channels_, 0);
37 uint8_t command = 0;
38 if (this->bit_depth_ <= 8) {
39 this->bit_depth_ = 8;
40 command |= MY9231_CMD_BIT_WIDTH_8;
41 } else if (this->bit_depth_ <= 12) {
42 this->bit_depth_ = 12;
43 command |= MY9231_CMD_BIT_WIDTH_12;
44 } else if (this->bit_depth_ <= 14) {
45 this->bit_depth_ = 14;
46 command |= MY9231_CMD_BIT_WIDTH_14;
47 } else {
48 this->bit_depth_ = 16;
49 command |= MY9231_CMD_BIT_WIDTH_16;
50 }
51 command |=
52 MY9231_CMD_SCATTER_APDM | MY9231_CMD_FREQUENCY_DIVIDE_1 | MY9231_CMD_REACTION_FAST | MY9231_CMD_ONE_SHOT_DISABLE;
53 ESP_LOGV(TAG, " Command: 0x%02X", command);
54
55 {
56 InterruptLock lock;
57 this->send_dcki_pulses_(32 * this->num_chips_);
58 this->init_chips_(command);
59 }
60 ESP_LOGV(TAG, " Chips initialized.");
61}
63 ESP_LOGCONFIG(TAG, "MY9231:");
64 LOG_PIN(" DI Pin: ", this->pin_di_);
65 LOG_PIN(" DCKI Pin: ", this->pin_dcki_);
66 ESP_LOGCONFIG(TAG,
67 " Total number of channels: %u\n"
68 " Number of chips: %u\n"
69 " Bit depth: %u",
70 this->num_channels_, this->num_chips_, this->bit_depth_);
71}
73 if (!this->update_)
74 return;
75
76 {
77 InterruptLock lock;
78 for (auto pwm_amount : this->pwm_amounts_) {
79 this->write_word_(pwm_amount, this->bit_depth_);
80 }
81 // Send 8 DI pulses. After 8 falling edges, the duty data are store.
82 this->send_di_pulses_(8);
83 }
84 this->update_ = false;
85}
86void MY9231OutputComponent::set_channel_value_(uint8_t channel, uint16_t value) {
87 ESP_LOGV(TAG, "set channels %u to %u", channel, value);
88 uint8_t index = this->num_channels_ - channel - 1;
89 if (this->pwm_amounts_[index] != value) {
90 this->update_ = true;
91 }
92 this->pwm_amounts_[index] = value;
93}
95 // Send 12 DI pulse. After 6 falling edges, the duty data are stored
96 // and after 12 rising edges the command mode is activated.
97 this->send_di_pulses_(12);
99 for (uint8_t i = 0; i < this->num_chips_; i++) {
100 this->write_word_(command, 8);
101 }
102 // Send 16 DI pulse. After 14 falling edges, the command data are
103 // stored and after 16 falling edges the duty mode is activated.
104 this->send_di_pulses_(16);
106}
107void MY9231OutputComponent::write_word_(uint16_t value, uint8_t bits) {
108 for (uint8_t i = bits; i > 0; i--) {
109 this->pin_di_->digital_write(value & (1 << (i - 1)));
111 }
112}
115 for (uint8_t i = 0; i < count; i++) {
116 this->pin_di_->digital_write(true);
117 this->pin_di_->digital_write(false);
118 }
119}
122 for (uint8_t i = 0; i < count; i++) {
123 this->pin_dcki_->digital_write(true);
124 this->pin_dcki_->digital_write(false);
125 }
126}
127
128} // namespace my9231
129} // namespace esphome
virtual void setup()=0
virtual void digital_write(bool value)=0
virtual bool digital_read()=0
Helper class to disable interrupts.
Definition helpers.h:615
std::vector< uint16_t > pwm_amounts_
Definition my9231.h:59
void setup() override
Setup the MY9231.
Definition my9231.cpp:30
void set_channel_value_(uint8_t channel, uint16_t value)
Definition my9231.cpp:86
void loop() override
Send new values if they were updated.
Definition my9231.cpp:72
void send_di_pulses_(uint8_t count)
Definition my9231.cpp:113
void write_word_(uint16_t value, uint8_t bits)
Definition my9231.cpp:107
void send_dcki_pulses_(uint8_t count)
Definition my9231.cpp:120
void init_chips_(uint8_t command)
Definition my9231.cpp:94
Providing packet encoding functions for exchanging data with a remote host.
Definition a01nyub.cpp:7
void IRAM_ATTR HOT delayMicroseconds(uint32_t us)
Definition core.cpp:31