Added class for message passing

This commit is contained in:
Pieter Kokx 2024-11-19 11:23:58 +01:00
parent a6c483c0b4
commit 6f70a56c90
No known key found for this signature in database
GPG Key ID: BD73BAB527D54451
6 changed files with 99 additions and 59 deletions

View File

@ -136,38 +136,16 @@ void Duco::stop_waiting(uint8_t message_id) {
}
}
void Duco::send(uint8_t function, std::vector<uint8_t> message, DucoDevice *device) {
std::vector<uint8_t> data;
uint8_t message_id = this->next_id_();
data.push_back(message.size() + 2);
data.push_back(function);
data.push_back(message_id);
data.insert(data.end(), message.begin(), message.end());
send_raw(data);
this->waiting_for_response[message_id] = device;
}
// Helper function for lambdas
// Send raw command. Except CRC everything must be contained in payload
void Duco::send_raw(const std::vector<uint8_t> &payload) {
if (payload.empty()) {
return;
}
auto crc = crc16(payload.data(), payload.size());
void Duco::send(DucoMessage message, DucoDevice *device) {
message.id = this->next_id_();
this->write_byte(0xAA);
this->write_byte(0x55);
this->write_array(payload);
this->write_byte(crc & 0xFF);
this->write_byte((crc >> 8) & 0xFF);
this->write_array(message.get_message());
this->flush();
ESP_LOGD(TAG, "DUCO write: %s", format_hex_pretty(payload).c_str());
last_send_ = millis();
this->waiting_for_response[message.id] = device;
ESP_LOGD(TAG, "Duco message sent: %s", message.to_string().c_str());
}
void Duco::debug_hex(std::vector<uint8_t> bytes, uint8_t separator) {
@ -233,8 +211,10 @@ void DucoDiscovery::loop() {
if (!waiting_for_response_) {
ESP_LOGD(TAG, "Discover next node (%d = 0x%02x)", next_node_, next_node_);
// request the next node
std::vector<uint8_t> message = {0x01, next_node_};
this->parent_->send(0x0c, message, this);
DucoMessage message;
message.function = 0x0c;
message.data = {0x01, next_node_};
this->parent_->send(message, this);
waiting_for_response_ = true;
}

View File

@ -12,6 +12,59 @@ namespace duco {
class DucoDevice;
class DucoMessage {
public:
DucoMessage() {}
uint8_t function;
uint8_t id;
std::vector<uint8_t> data;
uint16_t crc;
std::vector<uint8_t> get_message() {
std::vector<uint8_t> message;
message.push_back(data.size() + 2);
message.push_back(function);
message.push_back(id);
message.insert(message.end(), data.begin(), data.end());
auto crc = crc16(message.data(), message.size());
message.push_back(crc & 0xFF);
message.push_back((crc >> 8) & 0xFF);
return message;
}
std::string to_string() {
std::string res;
char buf[5];
size_t len = data.size();
sprintf(buf, "%02X", len + 2);
res += buf;
res += " ";
sprintf(buf, "%02X", function);
res += buf;
res += " ";
sprintf(buf, "%02X", id);
res += buf;
res += " ";
for (size_t i = 0; i < len; i++) {
res += " ";
sprintf(buf, "%02X", data[i]);
res += buf;
}
return res;
}
};
class Duco : public uart::UARTDevice, public Component {
public:
Duco() { this->last_id_ = 10; };
@ -24,8 +77,7 @@ class Duco : public uart::UARTDevice, public Component {
float get_setup_priority() const override;
void send(uint8_t function, std::vector<uint8_t> message, DucoDevice *device);
void send_raw(const std::vector<uint8_t> &payload);
void send(DucoMessage message, DucoDevice *device);
void set_send_wait_time(uint16_t time_in_ms) { send_wait_time_ = time_in_ms; }
void set_disable_crc(bool disable_crc) { disable_crc_ = disable_crc; }

View File

@ -10,8 +10,10 @@ static const char *const TAG = "duco number";
void DucoComfortTemperature::setup() {}
void DucoComfortTemperature::update() {
std::vector<uint8_t> message = {0x00, 0x12, 0x0a};
this->parent_->send(0x24, message, this);
DucoMessage message;
message.function = 0x24;
message.data = {0x00, 0x12, 0x0a};
this->parent_->send(message, this);
}
float DucoComfortTemperature::get_setup_priority() const {
@ -31,8 +33,10 @@ void DucoComfortTemperature::receive_response(std::vector<uint8_t> message) {
void DucoComfortTemperature::control(float number) {
uint8_t temperature = number * 10;
std::vector<uint8_t> message = {0x01, 0x12, 0x0a, temperature, 0x00, 0x00, 0x00};
this->parent_->send(0x24, message, this);
DucoMessage message;
message.function = 0x24;
message.data = {0x01, 0x12, 0x0a, temperature, 0x00, 0x00, 0x00};
this->parent_->send(message, this);
}
} // namespace duco

View File

@ -40,12 +40,10 @@ const uint8_t DucoSelect::MODE_CODE_MAN3x3 = 0xc6;
void DucoSelect::setup() {}
void DucoSelect::update() {
// ask for current mode
ESP_LOGD(TAG, "Ask for current mode");
// ask for information from node 1
std::vector<uint8_t> message = {0x02, 0x01};
this->parent_->send(0x0c, message, this);
DucoMessage message;
message.function = 0x0c;
message.data = {0x02, 0x01};
this->parent_->send(message, this);
}
float DucoSelect::get_setup_priority() const {
@ -152,10 +150,10 @@ void DucoSelect::receive_response(std::vector<uint8_t> message) {
}
void DucoSelect::control(const std::string &value) {
ESP_LOGD(TAG, "TODO: Set value %s", value.c_str());
std::vector<uint8_t> message = {0x04, 0x01, string_to_code(value)};
this->parent_->send(0x0c, message, this);
DucoMessage message;
message.function = 0x0c;
message.data = {0x04, 0x01, string_to_code(value)};
this->parent_->send(message, this);
}
} // namespace duco

View File

@ -10,11 +10,10 @@ static const char *const TAG = "duco sensor";
void DucoCo2Sensor::setup() {}
void DucoCo2Sensor::update() {
// ask for current mode
ESP_LOGD(TAG, "CO2: Get sensor information");
std::vector<uint8_t> message = {0x01, address_, 0x00, 0x49, 0x04};
this->parent_->send(0x10, message, this);
DucoMessage message;
message.function = 0x10;
message.data = {0x01, address_, 0x00, 0x49, 0x04};
this->parent_->send(message, this);
}
float DucoCo2Sensor::get_setup_priority() const {
@ -36,8 +35,10 @@ void DucoCo2Sensor::set_address(uint8_t address) { this->address_ = address; }
void DucoFilterRemainingSensor::setup() {}
void DucoFilterRemainingSensor::update() {
std::vector<uint8_t> message = {0x00, 0x30, 0x09};
this->parent_->send(0x24, message, this);
DucoMessage message;
message.function = 0x24;
message.data = {0x00, 0x30, 0x09};
this->parent_->send(message, this);
}
float DucoFilterRemainingSensor::get_setup_priority() const {
@ -57,8 +58,10 @@ void DucoFilterRemainingSensor::receive_response(std::vector<uint8_t> message) {
void DucoFlowLevelSensor::setup() {}
void DucoFlowLevelSensor::update() {
std::vector<uint8_t> message = {0x02, 0x01};
this->parent_->send(0x0c, message, this);
DucoMessage message;
message.function = 0x0c;
message.data = {0x02, 0x01};
this->parent_->send(message, this);
}
float DucoFlowLevelSensor::get_setup_priority() const {
@ -78,8 +81,10 @@ void DucoFlowLevelSensor::receive_response(std::vector<uint8_t> message) {
void DucoStateTimeRemainingSensor::setup() {}
void DucoStateTimeRemainingSensor::update() {
std::vector<uint8_t> message = {0x02, 0x01};
this->parent_->send(0x0c, message, this);
DucoMessage message;
message.function = 0x0c;
message.data = {0x02, 0x01};
this->parent_->send(message, this);
}
float DucoStateTimeRemainingSensor::get_setup_priority() const {

View File

@ -10,9 +10,10 @@ static const char *const TAG = "duco sensor";
void DucoSerial::setup() {}
void DucoSerial::update() {
// ask for serial
std::vector<uint8_t> message = {0x01, 0x01, 0x00, 0x1a, 0x10};
this->parent_->send(0x10, message, this);
DucoMessage message;
message.function = 0x10;
message.data = {0x01, 0x01, 0x00, 0x1a, 0x10};
this->parent_->send(message, this);
}
float DucoSerial::get_setup_priority() const {