From e393e68799d310efcfe10648b4d519a9658b337b Mon Sep 17 00:00:00 2001 From: Geoff Davis Date: Sat, 21 Jan 2023 10:22:04 -0800 Subject: [PATCH 1/6] Cast pointers to void* before comparision --- components/mitsubishi_heatpump/espmhp.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/components/mitsubishi_heatpump/espmhp.cpp b/components/mitsubishi_heatpump/espmhp.cpp index 02223a1..04af44f 100644 --- a/components/mitsubishi_heatpump/espmhp.cpp +++ b/components/mitsubishi_heatpump/espmhp.cpp @@ -451,7 +451,7 @@ void MitsubishiHeatPump::setup() { "hw_serial(%p) is &Serial(%p)? %s", this->get_hw_serial_(), &Serial, - YESNO(this->get_hw_serial_() == &Serial) + YESNO((void *)this->get_hw_serial_() == (void *)&Serial) ); ESP_LOGCONFIG(TAG, "Calling hp->connect(%p)", this->get_hw_serial_()); From bcba670a096821602ddb78bbab96729b452a39b5 Mon Sep 17 00:00:00 2001 From: Geoff Davis Date: Sat, 21 Jan 2023 11:03:04 -0800 Subject: [PATCH 2/6] Clarify ESP32 vs ESP8266 in docs --- README.md | 95 ++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 94 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 98e74dd..b71deec 100644 --- a/README.md +++ b/README.md @@ -112,6 +112,8 @@ climate: update_interval: 500ms ``` +#### ESP8266 platforms + On ESP8266 you'll need to disable logging to serial because it conflicts with the heatpump UART: @@ -120,9 +122,13 @@ logger: baud_rate: 0 ``` +#### ESP32 platforms + On ESP32 you can change `hardware_uart` to `UART1` or `UART2` and keep logging enabled on the main serial port. +#### UART Notes + *Note:* this component DOES NOT use the ESPHome `uart` component, as it requires direct access to a hardware UART via the Arduino `HardwareSerial` class. The Mitsubishi Heatpump units use an atypical serial port setting ("even @@ -131,13 +137,15 @@ software serial libraries, including the one in ESPHome. There's currently no way to guarantee access to a hardware UART nor retrieve the `HardwareSerial` handle from the `uart` component within the ESPHome framework. -# Example configuration +# Example configurations Below is an example configuration which will include wireless strength indicators and permit over the air updates. You'll need to create a `secrets.yaml` file inside of your `esphome` directory with entries for the various items prefixed with `!secret`. +## ESP8266 Example Configuration + ```yaml substitutions: name: hptest @@ -227,6 +235,91 @@ climate: hardware_uart: UART0 ``` +## ESP32 Example Configuration + +```yaml +substitutions: + name: hptest + friendly_name: Test Heatpump + + +esphome: + name: ${name} + +esp32: + board: lolin_s2_mini + variant: ESP32S2 + framework: + type: arduino + version: 2.0.3 + platform_version: 5.0.0 + +wifi: + ssid: !secret wifi_ssid + password: !secret wifi_password + + # Enable fallback hotspot (captive portal) in case wifi connection fails + ap: + ssid: "${friendly_name} Fallback Hotspot" + password: !secret fallback_password + +captive_portal: + +# Enable logging +logger: + +# Enable Home Assistant API +api: + +ota: + +# Enable Web server. +web_server: + port: 80 + + # Sync time with Home Assistant. +time: + - platform: homeassistant + id: homeassistant_time + +# Text sensors with general information. +text_sensor: + # Expose ESPHome version as sensor. + - platform: version + name: ${name} ESPHome Version + # Expose WiFi information as sensors. + - platform: wifi_info + ip_address: + name: ${name} IP + ssid: + name: ${name} SSID + bssid: + name: ${name} BSSID + +# Sensors with general information. +sensor: + # Uptime sensor. + - platform: uptime + name: ${name} Uptime + + # WiFi Signal sensor. + - platform: wifi_signal + name: ${name} WiFi Signal + update_interval: 60s + +external_components: + - source: github://geoffdavis/esphome-mitsubishiheatpump + +climate: + - platform: mitsubishi_heatpump + name: "${friendly_name}" + + # ESP32 only - change UART0 to UART1 or UART2 and remove the + # logging:baud_rate above to allow the built-in UART0 to function for + # logging. + hardware_uart: UART1 +``` + # Advanced configuration Some models of heat pump require different baud rates or don't support all From 1066ab6f1522742d0490801cb15ad7425e51906f Mon Sep 17 00:00:00 2001 From: Paul Nicholls Date: Sat, 11 Feb 2023 22:35:37 +1300 Subject: [PATCH 3/6] Make UART pins configurable (for ESP32) Adds optional configuration for the UART RX and TX pins on platforms which support assigning arbitrary pins to hardware UART(s), i.e. ESP32. --- README.md | 6 ++++++ components/mitsubishi_heatpump/climate.py | 10 ++++++++++ components/mitsubishi_heatpump/espmhp.cpp | 11 +++++++++-- components/mitsubishi_heatpump/espmhp.h | 8 ++++++++ 4 files changed, 33 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index b71deec..89b21ce 100644 --- a/README.md +++ b/README.md @@ -332,6 +332,8 @@ climate: name: "My heat pump" hardware_uart: UART2 baud_rate: 9600 + rx_pin: 9 + tx_pin: 10 supports: mode: [HEAT_COOL, COOL, HEAT, FAN_ONLY] fan_mode: [AUTO, LOW, MEDIUM, HIGH] @@ -350,6 +352,10 @@ climate: * *baud\_rate* (_Optional_): Serial BAUD rate used to communicate with the HeatPump. Most systems use the default value of `4800` baud, but some use `9600`. Default: `4800` +* *rx\_pin* (_Optional_): pin number to use as RX for the specified hardware + UART (ESP32 only - ESP8266 hardware UART's pins aren't configurable). +* *tx\_pin* (_Optional_): pin number to use as TX for the specified hardware + UART (ESP32 only - ESP8266 hardware UART's pins aren't configurable). * *update\_interval* (_Optional_, range: 0ms to 9000ms): How often this component polls the heatpump hardware, in milliseconds. Maximum usable value is 9 seconds due to underlying issues with the HeatPump library. Default: 500ms diff --git a/components/mitsubishi_heatpump/climate.py b/components/mitsubishi_heatpump/climate.py index 93c4e5f..5fd7f31 100644 --- a/components/mitsubishi_heatpump/climate.py +++ b/components/mitsubishi_heatpump/climate.py @@ -6,6 +6,8 @@ from esphome.const import ( CONF_ID, CONF_HARDWARE_UART, CONF_BAUD_RATE, + CONF_RX_PIN, + CONF_TX_PIN, CONF_UPDATE_INTERVAL, CONF_MODE, CONF_FAN_MODE, @@ -41,6 +43,8 @@ CONFIG_SCHEMA = climate.CLIMATE_SCHEMA.extend( cv.GenerateID(): cv.declare_id(MitsubishiHeatPump), cv.Optional(CONF_HARDWARE_UART, default="UART0"): valid_uart, cv.Optional(CONF_BAUD_RATE): cv.positive_int, + cv.Optional(CONF_RX_PIN): cv.positive_int, + cv.Optional(CONF_TX_PIN): cv.positive_int, # If polling interval is greater than 9 seconds, the HeatPump library # reconnects, but doesn't then follow up with our data request. cv.Optional(CONF_UPDATE_INTERVAL, default="500ms"): cv.All( @@ -69,6 +73,12 @@ def to_code(config): if CONF_BAUD_RATE in config: cg.add(var.set_baud_rate(config[CONF_BAUD_RATE])) + if CONF_RX_PIN in config: + cg.add(var.set_rx_pin(config[CONF_RX_PIN])) + + if CONF_TX_PIN in config: + cg.add(var.set_tx_pin(config[CONF_TX_PIN])) + supports = config[CONF_SUPPORTS] traits = var.config_traits() diff --git a/components/mitsubishi_heatpump/espmhp.cpp b/components/mitsubishi_heatpump/espmhp.cpp index 04af44f..f69e4e8 100644 --- a/components/mitsubishi_heatpump/espmhp.cpp +++ b/components/mitsubishi_heatpump/espmhp.cpp @@ -68,6 +68,14 @@ void MitsubishiHeatPump::set_baud_rate(int baud) { this->baud_ = baud; } +void MitsubishiHeatPump::set_rx_pin(int rx_pin) { + this->rx_pin_ = rx_pin; +} + +void MitsubishiHeatPump::set_tx_pin(int tx_pin) { + this->tx_pin_ = tx_pin; +} + /** * Get our supported traits. * @@ -455,8 +463,7 @@ void MitsubishiHeatPump::setup() { ); ESP_LOGCONFIG(TAG, "Calling hp->connect(%p)", this->get_hw_serial_()); - - if (hp->connect(this->get_hw_serial_(), this->baud_, -1, -1)) { + if (hp->connect(this->get_hw_serial_(), this->baud_, this->rx_pin_, this->tx_pin_)) { hp->sync(); } else { diff --git a/components/mitsubishi_heatpump/espmhp.h b/components/mitsubishi_heatpump/espmhp.h index 7cb3a27..5cd0877 100644 --- a/components/mitsubishi_heatpump/espmhp.h +++ b/components/mitsubishi_heatpump/espmhp.h @@ -66,6 +66,12 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { // Set the baud rate. Must be called before setup() to have any effect. void set_baud_rate(int); + // Set the RX pin. Must be called before setup() to have any effect. + void set_rx_pin(int); + + // Set the TX pin. Must be called before setup() to have any effect. + void set_tx_pin(int); + // print the current configuration void dump_config() override; @@ -133,6 +139,8 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { // Retrieve the HardwareSerial pointer from friend and subclasses. HardwareSerial *hw_serial_; int baud_ = 0; + int rx_pin_ = -1; + int tx_pin_ = -1; }; #endif From 50bb5b9c07659f21e0897f43ad1bb28f6919c5a4 Mon Sep 17 00:00:00 2001 From: David McClosky Date: Fri, 17 Feb 2023 17:25:07 -0500 Subject: [PATCH 4/6] README.md: Minor markdown formatting/quoting Without the quoting, I get config parsing errors for swing_mode. --- README.md | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 98e74dd..0c6c3d2 100644 --- a/README.md +++ b/README.md @@ -240,9 +240,10 @@ climate: hardware_uart: UART2 baud_rate: 9600 supports: - mode: [HEAT_COOL, COOL, HEAT, FAN_ONLY] - fan_mode: [AUTO, LOW, MEDIUM, HIGH] - swing_mode: [OFF, VERTICAL] + mode: ["HEAT_COOL", "COOL", "HEAT", "FAN_ONLY"] + fan_mode: ["AUTO", "LOW", "MEDIUM", "HIGH"] + swing_mode: ["OFF", "VERTICAL"] + visual: min_temperature: 16 max_temperature: 31 @@ -260,14 +261,13 @@ climate: * *update\_interval* (_Optional_, range: 0ms to 9000ms): How often this component polls the heatpump hardware, in milliseconds. Maximum usable value is 9 seconds due to underlying issues with the HeatPump library. Default: 500ms -* *supports* (_Optional_): Supported features for the device. ** *mode* - (_Optional_, list): Supported climate modes for the HeatPump. Default: - `['HEAT_COOL', 'COOL', 'HEAT', 'DRY', 'FAN_ONLY']` - ** *fan_mode* (_Optional_, list): - Supported fan speeds for the HeatPump. Default: `['AUTO', 'DIFFUSE', 'LOW', - 'MEDIUM', 'MIDDLE', 'HIGH']` ** *swing_mode* (_Optional_, list): Supported - fan swing modes. Most Mitsubishi units only support the default. Default: - `['OFF', 'VERTICAL']` +* *supports* (_Optional_): Supported features for the device. + * *mode* (_Optional_, list): Supported climate modes for the HeatPump. Default: + `['HEAT_COOL', 'COOL', 'HEAT', 'DRY', 'FAN_ONLY']` + * *fan_mode* (_Optional_, list): Supported fan speeds for the HeatPump. + Default: `['AUTO', 'DIFFUSE', 'LOW', 'MEDIUM', 'MIDDLE', 'HIGH']` + * *swing_mode* (_Optional_, list): Supported fan swing modes. Most Mitsubishi + units only support the default. Default: `['OFF', 'VERTICAL']` ## Other configuration From 6e00fa62b582ae64a6c3a443e0ae2a36675f525e Mon Sep 17 00:00:00 2001 From: Jon Maucher Date: Thu, 11 May 2023 10:34:41 -0400 Subject: [PATCH 5/6] Using explicit namespaces in header --- components/mitsubishi_heatpump/espmhp.cpp | 5 ++++ components/mitsubishi_heatpump/espmhp.h | 32 ++++++++++------------- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/components/mitsubishi_heatpump/espmhp.cpp b/components/mitsubishi_heatpump/espmhp.cpp index 02223a1..6978644 100644 --- a/components/mitsubishi_heatpump/espmhp.cpp +++ b/components/mitsubishi_heatpump/espmhp.cpp @@ -53,6 +53,11 @@ void MitsubishiHeatPump::check_logger_conflict_() { #endif } +void MitsubishiHeatPump::banner() { + ESP_LOGI(TAG, "ESPHome MitsubishiHeatPump version %s", + ESPMHP_VERSION); +} + void MitsubishiHeatPump::update() { // This will be called every "update_interval" milliseconds. //this->dump_config(); diff --git a/components/mitsubishi_heatpump/espmhp.h b/components/mitsubishi_heatpump/espmhp.h index 7cb3a27..7d59f7d 100644 --- a/components/mitsubishi_heatpump/espmhp.h +++ b/components/mitsubishi_heatpump/espmhp.h @@ -21,7 +21,6 @@ #include "esphome/core/preferences.h" #include "HeatPump.h" -using namespace esphome; #ifndef ESPMHP_H #define ESPMHP_H @@ -41,7 +40,7 @@ static const uint8_t ESPMHP_MAX_TEMPERATURE = 31; // degrees C, static const float ESPMHP_TEMPERATURE_STEP = 0.5; // temperature setting step, // in degrees C -class MitsubishiHeatPump : public PollingComponent, public climate::Climate { +class MitsubishiHeatPump : public esphome::PollingComponent, public esphome::climate::Climate { public: @@ -58,10 +57,7 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { ); // Print a banner with library information. - void banner() { - ESP_LOGI(TAG, "ESPHome MitsubishiHeatPump version %s", - ESPMHP_VERSION); - } + void banner(); // Set the baud rate. Must be called before setup() to have any effect. void set_baud_rate(int); @@ -82,16 +78,16 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { void update() override; // Configure the climate object with traits that we support. - climate::ClimateTraits traits() override; + esphome::climate::ClimateTraits traits() override; // Get a mutable reference to the traits that we support. - climate::ClimateTraits& config_traits(); + esphome::climate::ClimateTraits& config_traits(); // Debugging function to print the object's state. void dump_state(); // Handle a request from the user to change settings. - void control(const climate::ClimateCall &call) override; + void control(const esphome::climate::ClimateCall &call) override; // Use the temperature from an external sensor. Use // set_remote_temp(0) to switch back to the internal sensor. @@ -102,7 +98,7 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { HeatPump* hp; // The ClimateTraits supported by this HeatPump. - climate::ClimateTraits traits_; + esphome::climate::ClimateTraits traits_; // Allow the HeatPump class to use get_hw_serial_ friend class HeatPump; @@ -118,16 +114,16 @@ class MitsubishiHeatPump : public PollingComponent, public climate::Climate { // various prefs to save mode-specific temperatures, akin to how the IR // remote works. - ESPPreferenceObject cool_storage; - ESPPreferenceObject heat_storage; - ESPPreferenceObject auto_storage; + esphome::ESPPreferenceObject cool_storage; + esphome::ESPPreferenceObject heat_storage; + esphome::ESPPreferenceObject auto_storage; - optional cool_setpoint; - optional heat_setpoint; - optional auto_setpoint; + esphome::optional cool_setpoint; + esphome::optional heat_setpoint; + esphome::optional auto_setpoint; - static void save(float value, ESPPreferenceObject& storage); - static optional load(ESPPreferenceObject& storage); + static void save(float value, esphome::ESPPreferenceObject& storage); + static esphome::optional load(esphome::ESPPreferenceObject& storage); private: // Retrieve the HardwareSerial pointer from friend and subclasses. From 87d0f5af1e220e72633c02476ef70f7a7d9fe471 Mon Sep 17 00:00:00 2001 From: TheDK Date: Fri, 9 Jun 2023 17:10:17 +0200 Subject: [PATCH 6/6] Update README.md Add info to avoid boot loop on ESP32 --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 98e74dd..718c474 100644 --- a/README.md +++ b/README.md @@ -224,7 +224,9 @@ climate: # ESP32 only - change UART0 to UART1 or UART2 and remove the # logging:baud_rate above to allow the built-in UART0 to function for # logging. + # For ESP32 specifying baud_rate is mandatory, otherwise a boot loop occurs! hardware_uart: UART0 + baud_rate: 9600 ``` # Advanced configuration