mirror of
https://github.com/esphome/esphome.git
synced 2026-10-22 05:46:12 +00:00
Merge remote-tracking branch 'origin/dev' into in-range-test-coverage
This commit is contained in:
@@ -395,6 +395,8 @@ jobs:
|
||||
- common
|
||||
- determine-jobs
|
||||
if: needs.determine-jobs.outputs.integration-tests == 'true'
|
||||
# A hung test is failed by pytest's --timeout below; this bounds the rest
|
||||
timeout-minutes: 60
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
@@ -471,7 +473,8 @@ jobs:
|
||||
exit 1
|
||||
fi
|
||||
echo "Bucket ${{ matrix.bucket.name }}: running ${#test_files[@]} integration tests"
|
||||
pytest -vv --no-cov --tb=native --durations=30 -n auto --dist worksteal \
|
||||
# A hung test fails after 30 min: the 15 min shared build lock wait plus a cold compile
|
||||
pytest -vv --no-cov --tb=native --durations=30 -n auto --dist worksteal --timeout=1800 \
|
||||
--junitxml=junit-integration.xml "${test_files[@]}"
|
||||
- name: Upload test artifacts
|
||||
# Tests that compare rendered output write the image they actually got here, so a
|
||||
|
||||
@@ -27,7 +27,7 @@ jobs:
|
||||
days-before-close: 7
|
||||
stale-label: stale
|
||||
exempt-label: not-stale
|
||||
conflict-label: needs-rebase
|
||||
conflict-label: has-conflicts
|
||||
ignored-users: esphbot,codecov-commenter
|
||||
stale-pr-message: >
|
||||
There hasn't been any activity on this pull request recently. This
|
||||
|
||||
@@ -225,6 +225,15 @@ file does, and it is the authority when they disagree. The most useful starting
|
||||
stays inside the `#ifdef`.
|
||||
* **Failures after `setup()`:** `mark_failed()` is for `setup()` only. A runtime read or write failure
|
||||
sets `status_set_warning()` and the next success clears it; writes skip work when `is_failed()`.
|
||||
* **`dump_config()` already prints the failure reason:** for a failed component, core prints
|
||||
`<component> is marked FAILED: <reason>` right after the component's `dump_config()`, using the reason
|
||||
passed to `mark_failed()`. So `dump_config()` never checks `is_failed()` to log a failure, and no
|
||||
`error_code_` member exists only to pick that message. Pass the reason where setup fails instead:
|
||||
`this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL))` for a failed bus transfer, a short specific reason
|
||||
otherwise (`LOG_STR("Wrong chip ID")`). Core also logs it at that moment, so no `ESP_LOGE` repeats it
|
||||
before `mark_failed()`; keep a separate line only when it prints a value read at run time, such as the
|
||||
chip ID that did not match. Only the first reason is kept, so do not call `status_set_error()` before
|
||||
`mark_failed()` and do not mark the component failed again after a helper already did.
|
||||
* **Fixed platform facts compile to nothing:** gate on `#ifdef USE_ESP8266` and friends, not on a
|
||||
runtime check of something the build already knows.
|
||||
* **Logging string literals:** wrap literals passed as `%s` arguments in `LOG_STR_LITERAL()` so they
|
||||
|
||||
+8
-1
@@ -157,6 +157,9 @@ esphome/components/delonghi/* @grob6000
|
||||
esphome/components/dew_point/* @CFlix
|
||||
esphome/components/dfplayer/* @glmnet
|
||||
esphome/components/dfrobot_sen0395/* @niklasweber
|
||||
esphome/components/dfrobot_sen0465_base/* @tzabbi
|
||||
esphome/components/dfrobot_sen0465_i2c/* @tzabbi
|
||||
esphome/components/dfrobot_sen0465_uart/* @tzabbi
|
||||
esphome/components/dfrobot_sen0609/* @remcom
|
||||
esphome/components/dht/* @OttoWinter
|
||||
esphome/components/display_menu_base/* @numo68
|
||||
@@ -252,6 +255,7 @@ esphome/components/haier/text_sensor/* @paveldn
|
||||
esphome/components/haier_tundra/* @fauxpark
|
||||
esphome/components/haier_tundra/button/* @fauxpark
|
||||
esphome/components/haier_tundra/switch/* @fauxpark
|
||||
esphome/components/haier_water_heater/* @TheLexus
|
||||
esphome/components/havells_solar/* @sourabhjaiswal
|
||||
esphome/components/hbridge/fan/* @WeekendWarrior
|
||||
esphome/components/hbridge/light/* @DotNetDann
|
||||
@@ -390,6 +394,7 @@ esphome/components/micro_wake_word/* @jesserockz @kahrendt
|
||||
esphome/components/micronova/* @edenhaus @jorre05
|
||||
esphome/components/microphone/* @jesserockz @kahrendt
|
||||
esphome/components/mics_4514/* @jesserockz
|
||||
esphome/components/mics_5524/* @nliaudat
|
||||
esphome/components/midea/* @dudanov
|
||||
esphome/components/midea_ir/* @dudanov
|
||||
esphome/components/midea_portasplit/* @Fexiven
|
||||
@@ -507,6 +512,7 @@ esphome/components/rp2040_pwm/* @jesserockz
|
||||
esphome/components/rp2_ble_tracker/* @bdraco
|
||||
esphome/components/rpi_dpi_rgb/* @clydebarrow
|
||||
esphome/components/rtl87xx/* @kuba2k2
|
||||
esphome/components/rtsp_server/* @max246
|
||||
esphome/components/rtttl/* @glmnet @ximex
|
||||
esphome/components/runtime_image/* @clydebarrow @guillempages @kahrendt
|
||||
esphome/components/runtime_stats/* @bdraco
|
||||
@@ -682,7 +688,7 @@ esphome/components/version/* @esphome/core
|
||||
esphome/components/voice_assistant/* @jesserockz @kahrendt
|
||||
esphome/components/wake_on_lan/* @clydebarrow @willwill2will54
|
||||
esphome/components/watchdog/* @oarcher
|
||||
esphome/components/water_heater/* @dhoeben
|
||||
esphome/components/water_heater/* @esphome/core
|
||||
esphome/components/waveshare_epaper/* @clydebarrow
|
||||
esphome/components/waveshare_io_ch32v003/* @latonita
|
||||
esphome/components/web_server/ota/* @esphome/core
|
||||
@@ -721,6 +727,7 @@ esphome/components/xl9535/* @mreditor97
|
||||
esphome/components/xpt2046/touchscreen/* @nielsnl68 @numo68
|
||||
esphome/components/xxtea/* @clydebarrow
|
||||
esphome/components/zephyr/* @tomaszduda23
|
||||
esphome/components/zephyr_coredump/* @tomaszduda23
|
||||
esphome/components/zephyr_mcumgr/ota/* @tomaszduda23
|
||||
esphome/components/zephyr_pwm/* @wiomoc
|
||||
esphome/components/zhlt01/* @cfeenstra1024
|
||||
|
||||
+1
-1
@@ -22,7 +22,7 @@ RUN \
|
||||
-r /requirements.txt
|
||||
|
||||
# Install the ESPHome Device Builder dashboard.
|
||||
RUN uv pip install --no-cache-dir esphome-device-builder==1.23.1
|
||||
RUN uv pip install --no-cache-dir esphome-device-builder==1.24.0
|
||||
|
||||
RUN \
|
||||
platformio settings set enable_telemetry No \
|
||||
|
||||
+126
-3
@@ -14,6 +14,7 @@ from esphome.const import (
|
||||
CONF_COUNT,
|
||||
CONF_ELSE,
|
||||
CONF_ID,
|
||||
CONF_IF,
|
||||
CONF_THEN,
|
||||
CONF_TIME,
|
||||
CONF_TIMEOUT,
|
||||
@@ -34,6 +35,9 @@ from esphome.schema_extractors import SCHEMA_EXTRACT, schema_extractor
|
||||
from esphome.types import ConfigType, SafeExpType
|
||||
from esphome.util import Registry
|
||||
|
||||
CONF_CHOOSE = "choose"
|
||||
CONF_CHOICE_ID = "choice_id"
|
||||
|
||||
|
||||
def progmem_bytes(name: str, data: bytes | list[int]) -> MockObj:
|
||||
"""Shared PROGMEM table for constant bytes; equal payloads share one, empty is nullptr."""
|
||||
@@ -840,10 +844,39 @@ async def delay_action_to_code(
|
||||
return var
|
||||
|
||||
|
||||
def _wrap_bare_if_condition(value: Any) -> Any:
|
||||
"""Allow a single condition directly under `if:` in place of `condition: {...}`."""
|
||||
if not isinstance(value, dict):
|
||||
return value
|
||||
# `any` and `all` are also registered conditions, but here they are the if action's own keys
|
||||
bare = [
|
||||
key
|
||||
for key in value
|
||||
if key in CONDITION_REGISTRY and key not in (CONF_ANY, CONF_ALL)
|
||||
]
|
||||
if not bare:
|
||||
return value
|
||||
if len(bare) > 1:
|
||||
raise cv.Invalid(
|
||||
f"Only one condition may be given directly under 'if', found {', '.join(bare)}. "
|
||||
f"Use '{CONF_CONDITION}', '{CONF_ALL}' or '{CONF_ANY}' to combine conditions"
|
||||
)
|
||||
if other := [k for k in (CONF_CONDITION, CONF_ANY, CONF_ALL) if k in value]:
|
||||
raise cv.Invalid(
|
||||
f"'{bare[0]}' given directly under 'if' cannot be used with '{other[0]}'. "
|
||||
f"Move it into '{other[0]}'"
|
||||
)
|
||||
key = bare[0]
|
||||
result = {k: v for k, v in value.items() if k != key}
|
||||
result[CONF_CONDITION] = {key: value[key]}
|
||||
return result
|
||||
|
||||
|
||||
@register_action(
|
||||
"if",
|
||||
IfAction,
|
||||
cv.All(
|
||||
_wrap_bare_if_condition,
|
||||
{
|
||||
cv.Exclusive(
|
||||
CONF_CONDITION, CONF_CONDITION
|
||||
@@ -870,14 +903,104 @@ async def if_action_to_code(
|
||||
cond_conf = next(el for el in config if el in (CONF_ANY, CONF_ALL, CONF_CONDITION))
|
||||
condition = await build_condition(config[cond_conf], template_arg, args)
|
||||
var = cg.new_Pvariable(action_id, if_template_arg, condition)
|
||||
then_actions = else_actions = None
|
||||
if CONF_THEN in config:
|
||||
for action in await build_action_list(config[CONF_THEN], template_arg, args):
|
||||
then_actions = await build_action_list(config[CONF_THEN], template_arg, args)
|
||||
if has_else:
|
||||
else_actions = await build_action_list(config[CONF_ELSE], template_arg, args)
|
||||
_add_if_branches(var, then_actions, else_actions)
|
||||
return var
|
||||
|
||||
|
||||
def _add_if_branches(
|
||||
var: MockObj,
|
||||
then_actions: list[MockObj] | None,
|
||||
else_actions: list[MockObj] | None,
|
||||
) -> None:
|
||||
"""Add the branches of an IfAction one action at a time; None leaves a branch out."""
|
||||
if then_actions is not None:
|
||||
for action in then_actions:
|
||||
cg.add(var.add_then_action(action))
|
||||
cg.add(var.finish_then())
|
||||
if has_else:
|
||||
for action in await build_action_list(config[CONF_ELSE], template_arg, args):
|
||||
if else_actions is not None:
|
||||
for action in else_actions:
|
||||
cg.add(var.add_else_action(action))
|
||||
cg.add(var.finish_else())
|
||||
|
||||
|
||||
def _validate_choice(choice: ConfigType) -> ConfigType:
|
||||
"""A choice is either `if` with `then`, or `else` on its own."""
|
||||
if CONF_ELSE in choice:
|
||||
for key in (CONF_IF, CONF_THEN):
|
||||
if key in choice:
|
||||
raise cv.Invalid(f"'{key}' cannot be used with 'else'", path=[key])
|
||||
return choice
|
||||
for key in (CONF_IF, CONF_THEN):
|
||||
if key not in choice:
|
||||
raise cv.Invalid(f"'{key}' is required", path=[key])
|
||||
return choice
|
||||
|
||||
|
||||
def _validate_choose_else(choices: list[ConfigType]) -> list[ConfigType]:
|
||||
"""`else` may only be the last choice, and not the only one."""
|
||||
for index, choice in enumerate(choices[:-1]):
|
||||
if CONF_ELSE in choice:
|
||||
raise cv.Invalid(
|
||||
"Only the last choice may be 'else'", path=[index, CONF_ELSE]
|
||||
)
|
||||
if len(choices) == 1 and CONF_ELSE in choices[0]:
|
||||
raise cv.Invalid(
|
||||
"At least one choice must have 'if' and 'then'", path=[0, CONF_ELSE]
|
||||
)
|
||||
return choices
|
||||
|
||||
|
||||
@register_action(
|
||||
CONF_CHOOSE,
|
||||
IfAction,
|
||||
cv.All(
|
||||
cv.ensure_list(
|
||||
cv.All(
|
||||
cv.Schema(
|
||||
{
|
||||
cv.GenerateID(CONF_CHOICE_ID): cv.declare_id(IfAction),
|
||||
cv.Optional(CONF_IF): validate_potentially_and_condition,
|
||||
cv.Optional(CONF_THEN): validate_action_list,
|
||||
cv.Optional(CONF_ELSE): validate_action_list,
|
||||
}
|
||||
),
|
||||
_validate_choice,
|
||||
)
|
||||
),
|
||||
cv.Length(min=1),
|
||||
_validate_choose_else,
|
||||
),
|
||||
synchronous=True,
|
||||
)
|
||||
async def choose_action_to_code(
|
||||
config: list[ConfigType],
|
||||
action_id: ID,
|
||||
template_arg: cg.TemplateArguments,
|
||||
args: TemplateArgsType,
|
||||
) -> MockObj:
|
||||
# Built as a chain of if/else actions: each choice's else branch holds the next choice,
|
||||
# and the last choice's else branch holds the `else` actions, if any.
|
||||
else_actions: list[MockObj] | None = None
|
||||
if CONF_ELSE in config[-1]:
|
||||
else_actions = await build_action_list(
|
||||
config[-1][CONF_ELSE], template_arg, args
|
||||
)
|
||||
config = config[:-1]
|
||||
var: MockObj | None = None
|
||||
for index in reversed(range(len(config))):
|
||||
choice = config[index]
|
||||
if_template_arg = cg.TemplateArguments(else_actions is not None, *template_arg)
|
||||
condition = await build_condition(choice[CONF_IF], template_arg, args)
|
||||
choice_id = action_id if index == 0 else choice[CONF_CHOICE_ID]
|
||||
var = cg.new_Pvariable(choice_id, if_template_arg, condition)
|
||||
then_actions = await build_action_list(choice[CONF_THEN], template_arg, args)
|
||||
_add_if_branches(var, then_actions, else_actions)
|
||||
else_actions = [var]
|
||||
return var
|
||||
|
||||
|
||||
|
||||
@@ -58,6 +58,7 @@ from esphome.cpp_helpers import ( # noqa: F401
|
||||
extract_registry_entry_config,
|
||||
get_slot_count,
|
||||
gpio_pin_expression,
|
||||
new_bus_component,
|
||||
past_safe_mode,
|
||||
register_component,
|
||||
register_parented,
|
||||
|
||||
@@ -19,11 +19,7 @@ AbsoluteHumidityComponent = absolute_humidity_ns.class_(
|
||||
SaturationVaporPressureEquation = absolute_humidity_ns.enum(
|
||||
"SaturationVaporPressureEquation"
|
||||
)
|
||||
EQUATION = {
|
||||
"BUCK": SaturationVaporPressureEquation.BUCK,
|
||||
"TETENS": SaturationVaporPressureEquation.TETENS,
|
||||
"WOBUS": SaturationVaporPressureEquation.WOBUS,
|
||||
}
|
||||
EQUATION = SaturationVaporPressureEquation.options("BUCK", "TETENS", "WOBUS")
|
||||
|
||||
CONFIG_SCHEMA = (
|
||||
sensor.sensor_schema(
|
||||
|
||||
@@ -14,11 +14,9 @@ ac_dimmer_ns = cg.esphome_ns.namespace("ac_dimmer")
|
||||
AcDimmer = ac_dimmer_ns.class_("AcDimmer", output.FloatOutput, cg.Component)
|
||||
|
||||
DimMethod = ac_dimmer_ns.enum("DimMethod")
|
||||
DIM_METHODS = {
|
||||
"LEADING_PULSE": DimMethod.DIM_METHOD_LEADING_PULSE,
|
||||
"LEADING": DimMethod.DIM_METHOD_LEADING,
|
||||
"TRAILING": DimMethod.DIM_METHOD_TRAILING,
|
||||
}
|
||||
DIM_METHODS = DimMethod.options(
|
||||
"LEADING_PULSE", "LEADING", "TRAILING", prefix="DIM_METHOD_"
|
||||
)
|
||||
|
||||
ZC_INTERRUPT_TYPES = {
|
||||
"RISING": gpio_ns.INTERRUPT_RISING_EDGE,
|
||||
|
||||
@@ -46,11 +46,7 @@ ATTENUATION_MODES = {
|
||||
|
||||
sampling_mode = adc_ns.enum("SamplingMode", is_class=True)
|
||||
|
||||
SAMPLING_MODES = {
|
||||
"avg": sampling_mode.AVG,
|
||||
"min": sampling_mode.MIN,
|
||||
"max": sampling_mode.MAX,
|
||||
}
|
||||
SAMPLING_MODES = sampling_mode.options("avg", "min", "max")
|
||||
|
||||
adc_unit_t = cg.global_ns.enum("adc_unit_t", is_class=True)
|
||||
|
||||
|
||||
@@ -11,12 +11,6 @@
|
||||
|
||||
namespace esphome::ade7880 {
|
||||
|
||||
// adapted from https://stackoverflow.com/a/55912127/1886371
|
||||
template<size_t Bits, typename T> inline T sign_extend(const T &v) noexcept {
|
||||
using S = struct { signed Val : Bits; };
|
||||
return reinterpret_cast<const S *>(&v)->Val;
|
||||
}
|
||||
|
||||
// Register types
|
||||
// unsigned 8-bit (uint8_t)
|
||||
// signed 10-bit - 16-bit ZP on wire (int16_t, needs sign extension)
|
||||
@@ -49,7 +43,7 @@ uint16_t ADE7880::read_u16_register16_(uint16_t a_register) {
|
||||
|
||||
int32_t ADE7880::read_s24zp_register16_(uint16_t a_register) {
|
||||
// s24zp means 24 bit signed value in the lower 24 bits of a 32-bit register
|
||||
int32_t in;
|
||||
uint32_t in;
|
||||
this->read_register16(a_register, reinterpret_cast<uint8_t *>(&in), sizeof(in));
|
||||
return sign_extend<24>(convert_big_endian(in));
|
||||
}
|
||||
|
||||
@@ -282,9 +282,7 @@ async def power_channel(config: ConfigType) -> MockObj:
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
if irq0_pin := config.get(CONF_IRQ0_PIN):
|
||||
pin = await cg.gpio_pin_expression(irq0_pin)
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import esphome.codegen as cg
|
||||
from esphome.components import i2c
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import CONF_ID
|
||||
from esphome.types import ConfigType
|
||||
|
||||
DEPENDENCIES = ["i2c"]
|
||||
@@ -27,8 +26,6 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_continuous_mode(config[CONF_CONTINUOUS_MODE]))
|
||||
|
||||
@@ -11,7 +11,7 @@ static const uint8_t ADS1115_REGISTER_CONFIG = 0x01;
|
||||
void ADS1115Component::setup() {
|
||||
uint16_t value;
|
||||
if (!this->read_byte_16(ADS1115_REGISTER_CONVERSION, &value)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -58,7 +58,7 @@ void ADS1115Component::setup() {
|
||||
config |= 0b0000000000000011;
|
||||
|
||||
if (!this->write_byte_16(ADS1115_REGISTER_CONFIG, config)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
this->prev_config_ = config;
|
||||
@@ -66,9 +66,6 @@ void ADS1115Component::setup() {
|
||||
void ADS1115Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "ADS1115:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
float ADS1115Component::request_measurement(ADS1115Multiplexer multiplexer, ADS1115Gain gain,
|
||||
ADS1115Resolution resolution, ADS1115Samplerate samplerate) {
|
||||
|
||||
@@ -4,7 +4,6 @@ from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_ADDRESS,
|
||||
CONF_ID,
|
||||
CONF_MODE,
|
||||
CONF_TVOC,
|
||||
CONF_VALUE,
|
||||
@@ -58,9 +57,7 @@ FINAL_VALIDATE_SCHEMA = i2c.final_validate_device_schema("ags10", max_frequency=
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_TVOC, var.set_tvoc)
|
||||
@@ -84,11 +81,9 @@ automation.register_apply_action(
|
||||
)
|
||||
|
||||
AGS10SetZeroPointActionMode = ags10_ns.enum("AGS10SetZeroPointActionMode")
|
||||
AGS10_SET_ZERO_POINT_ACTION_MODE = {
|
||||
"FACTORY_DEFAULT": AGS10SetZeroPointActionMode.FACTORY_DEFAULT,
|
||||
"CURRENT_VALUE": AGS10SetZeroPointActionMode.CURRENT_VALUE,
|
||||
"CUSTOM_VALUE": AGS10SetZeroPointActionMode.CUSTOM_VALUE,
|
||||
}
|
||||
AGS10_SET_ZERO_POINT_ACTION_MODE = AGS10SetZeroPointActionMode.options(
|
||||
"FACTORY_DEFAULT", "CURRENT_VALUE", "CUSTOM_VALUE"
|
||||
)
|
||||
|
||||
AGS10_SET_ZERO_POINT_SCHEMA = cv.Schema(
|
||||
{
|
||||
|
||||
@@ -52,8 +52,7 @@ void AHT10Component::setup() {
|
||||
break;
|
||||
}
|
||||
if (error_code != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
uint8_t cal_attempts = 0;
|
||||
@@ -61,20 +60,17 @@ void AHT10Component::setup() {
|
||||
while (data & AHT10_STATUS_BUSY) {
|
||||
delay(AHT10_DEFAULT_DELAY);
|
||||
if (this->read(&data, 1) != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
++cal_attempts;
|
||||
if (cal_attempts > AHT10_INIT_ATTEMPTS) {
|
||||
ESP_LOGE(TAG, "Initialization timed out");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Initialization timed out"));
|
||||
return;
|
||||
}
|
||||
}
|
||||
if ((data & 0x68) != 0x08) { // Bit[6:5] = 0b00, NORMAL mode and Bit[3] = 0b1, CALIBRATED
|
||||
ESP_LOGE(TAG, "Initialization failed");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Initialization failed"));
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -152,9 +148,6 @@ void AHT10Component::update() {
|
||||
void AHT10Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "AHT10:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_SENSOR(" ", "Temperature", this->temperature_sensor_);
|
||||
LOG_SENSOR(" ", "Humidity", this->humidity_sensor_);
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_HUMIDITY,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
CONF_VARIANT,
|
||||
DEVICE_CLASS_HUMIDITY,
|
||||
@@ -20,10 +19,7 @@ aht10_ns = cg.esphome_ns.namespace("aht10")
|
||||
AHT10Component = aht10_ns.class_("AHT10Component", cg.PollingComponent, i2c.I2CDevice)
|
||||
|
||||
AHT10Variant = aht10_ns.enum("AHT10Variant")
|
||||
AHT10_VARIANTS = {
|
||||
"AHT10": AHT10Variant.AHT10,
|
||||
"AHT20": AHT10Variant.AHT20,
|
||||
}
|
||||
AHT10_VARIANTS = AHT10Variant.options("AHT10", "AHT20")
|
||||
|
||||
CONFIG_SCHEMA = (
|
||||
cv.Schema(
|
||||
@@ -52,9 +48,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
cg.add(var.set_variant(config[CONF_VARIANT]))
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
|
||||
@@ -10,8 +10,7 @@ ESPHOME_LOG_TAG(TAG, "aic3204");
|
||||
|
||||
#define ERROR_CHECK(err, msg) \
|
||||
if (!(err)) { \
|
||||
ESP_LOGE(TAG, msg); \
|
||||
this->mark_failed(); \
|
||||
this->mark_failed(LOG_STR(msg)); \
|
||||
return; \
|
||||
}
|
||||
|
||||
@@ -108,10 +107,6 @@ void AIC3204::setup() {
|
||||
void AIC3204::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "AIC3204:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
bool AIC3204::set_mute_off() {
|
||||
|
||||
@@ -3,7 +3,7 @@ import esphome.codegen as cg
|
||||
from esphome.components import i2c
|
||||
from esphome.components.audio_dac import AudioDac
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import CONF_ID, CONF_MODE
|
||||
from esphome.const import CONF_MODE
|
||||
from esphome.types import ConfigType
|
||||
|
||||
CODEOWNERS = ["@kbx81"]
|
||||
@@ -41,6 +41,4 @@ automation.register_apply_action(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
await i2c.new_i2c_component(config)
|
||||
|
||||
@@ -29,10 +29,7 @@ AirthingsWavePlus = airthings_wave_plus_ns.class_(
|
||||
|
||||
CONF_DEVICE_TYPE = "device_type"
|
||||
WaveDeviceType = airthings_wave_plus_ns.enum("WaveDeviceType")
|
||||
DEVICE_TYPES = {
|
||||
"WAVE_PLUS": WaveDeviceType.WAVE_PLUS,
|
||||
"WAVE_GEN2": WaveDeviceType.WAVE_GEN2,
|
||||
}
|
||||
DEVICE_TYPES = WaveDeviceType.options("WAVE_PLUS", "WAVE_GEN2")
|
||||
|
||||
|
||||
def validate_wave_gen2_config(config: ConfigType) -> ConfigType:
|
||||
|
||||
@@ -42,21 +42,18 @@ bool AM2315C::reset_register_(uint8_t reg) {
|
||||
data[2] = 0;
|
||||
ESP_LOGD(TAG, "Reset register: 0x%02x", reg);
|
||||
if (this->write(data, 3) != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, "Write failed!");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return false;
|
||||
}
|
||||
delay(5);
|
||||
if (this->read(data, 3) != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, "Read failed!");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return false;
|
||||
}
|
||||
delay(10);
|
||||
data[0] = 0xB0 | reg;
|
||||
if (this->write(data, 3) != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, "Write failed!");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return false;
|
||||
}
|
||||
delay(5);
|
||||
@@ -76,8 +73,7 @@ void AM2315C::setup() {
|
||||
// get status
|
||||
uint8_t status = 0;
|
||||
if (this->read(&status, 1) != i2c::ERROR_OK) {
|
||||
ESP_LOGE(TAG, "Read failed!");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -86,18 +82,9 @@ void AM2315C::setup() {
|
||||
// never required during testing
|
||||
if ((status & 0x18) != 0x18) {
|
||||
ESP_LOGD(TAG, "Resetting AM2315C registers");
|
||||
if (!this->reset_register_(0x1B)) {
|
||||
this->mark_failed();
|
||||
// reset_register_() marks the component failed with its own reason
|
||||
if (!this->reset_register_(0x1B) || !this->reset_register_(0x1C) || !this->reset_register_(0x1E))
|
||||
return;
|
||||
}
|
||||
if (!this->reset_register_(0x1C)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
}
|
||||
if (!this->reset_register_(0x1E)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -168,9 +155,6 @@ void AM2315C::update() {
|
||||
void AM2315C::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "AM2315C:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_SENSOR(" ", "Temperature", this->temperature_sensor_);
|
||||
LOG_SENSOR(" ", "Humidity", this->humidity_sensor_);
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_HUMIDITY,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
DEVICE_CLASS_HUMIDITY,
|
||||
DEVICE_CLASS_TEMPERATURE,
|
||||
@@ -42,9 +41,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_TEMPERATURE, var.set_temperature_sensor)
|
||||
|
||||
@@ -37,16 +37,13 @@ void AM2320Component::setup() {
|
||||
data[0] = 0;
|
||||
data[1] = 4;
|
||||
if (!this->read_data_(data)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
}
|
||||
void AM2320Component::dump_config() {
|
||||
ESP_LOGD(TAG, "AM2320:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_SENSOR(" ", "Temperature", this->temperature_sensor_);
|
||||
LOG_SENSOR(" ", "Humidity", this->humidity_sensor_);
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_HUMIDITY,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
DEVICE_CLASS_HUMIDITY,
|
||||
DEVICE_CLASS_TEMPERATURE,
|
||||
@@ -44,9 +43,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_TEMPERATURE, var.set_temperature_sensor)
|
||||
|
||||
@@ -5,8 +5,8 @@
|
||||
namespace esphome::animation {
|
||||
|
||||
Animation::Animation(const uint8_t *data_start, int width, int height, uint32_t animation_frame_count,
|
||||
image::ImageType type, image::Transparency transparent)
|
||||
: Image(data_start, width, height, type, transparent),
|
||||
image::ImageType type, image::Transparency transparent, bool big_endian)
|
||||
: Image(data_start, width, height, type, transparent, big_endian),
|
||||
animation_data_start_(data_start),
|
||||
current_frame_(0),
|
||||
animation_frame_count_(animation_frame_count),
|
||||
|
||||
@@ -6,7 +6,7 @@ namespace esphome::animation {
|
||||
class Animation final : public image::Image {
|
||||
public:
|
||||
Animation(const uint8_t *data_start, int width, int height, uint32_t animation_frame_count, image::ImageType type,
|
||||
image::Transparency transparent);
|
||||
image::Transparency transparent, bool big_endian = false);
|
||||
|
||||
uint32_t get_animation_frame_count() const;
|
||||
int get_current_frame() const;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
from esphome import automation
|
||||
import esphome.codegen as cg
|
||||
from esphome.components.const import CONF_LOOP
|
||||
from esphome.components.const import CONF_BYTE_ORDER, CONF_LOOP
|
||||
from esphome.components.file import image as file_image
|
||||
from esphome.components.file.image import image_schema, write_image
|
||||
from esphome.components.image import Image_, validate_settings
|
||||
@@ -90,6 +90,7 @@ async def setup_animation(config: ConfigType) -> None:
|
||||
frame_count,
|
||||
image_type,
|
||||
trans_value,
|
||||
config.get(CONF_BYTE_ORDER) == "BIG_ENDIAN",
|
||||
)
|
||||
if loop_config := config.get(CONF_LOOP):
|
||||
start = loop_config[CONF_START_FRAME]
|
||||
|
||||
@@ -28,15 +28,6 @@ static constexpr uint32_t APC1_NO_DATA_TIMEOUT_MS = 15000;
|
||||
// Drop a partial frame when the bytes stop mid-way
|
||||
static constexpr uint32_t APC1_RX_IDLE_TIMEOUT_MS = 200;
|
||||
|
||||
// Frames and commands end with the 16-bit sum of every byte before it
|
||||
static uint16_t apc1_checksum(const uint8_t *data, size_t len) {
|
||||
uint16_t sum = 0;
|
||||
for (size_t i = 0; i < len; i++) {
|
||||
sum += data[i];
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
void APC1Component::setup() {
|
||||
if (this->set_pin_ != nullptr) {
|
||||
this->set_pin_->setup();
|
||||
@@ -157,7 +148,7 @@ void APC1Component::loop() {
|
||||
|
||||
void APC1Component::parse_frame_(uint16_t total_len) {
|
||||
uint16_t expected_checksum = encode_uint16(this->rx_buffer_[total_len - 2], this->rx_buffer_[total_len - 1]);
|
||||
uint16_t calculated_checksum = apc1_checksum(this->rx_buffer_.data(), total_len - 2);
|
||||
uint16_t calculated_checksum = sum16_bytes(this->rx_buffer_.data(), total_len - 2);
|
||||
if (expected_checksum != calculated_checksum) {
|
||||
ESP_LOGW(TAG, "APC1 checksum mismatch: calculated 0x%04X != expected 0x%04X", calculated_checksum,
|
||||
expected_checksum);
|
||||
@@ -343,7 +334,7 @@ void APC1Component::send_command_(APC1Command cmd, uint16_t data) {
|
||||
0,
|
||||
0,
|
||||
};
|
||||
uint16_t checksum = apc1_checksum(buf.data(), 5);
|
||||
uint16_t checksum = sum16_bytes(buf.data(), 5);
|
||||
buf[5] = static_cast<uint8_t>((checksum >> 8) & 0xFF);
|
||||
buf[6] = static_cast<uint8_t>(checksum & 0xFF);
|
||||
this->write_array(buf);
|
||||
|
||||
@@ -32,40 +32,35 @@ void APCProteousCover::loop() {
|
||||
if (!this->read_byte(&data)) {
|
||||
continue;
|
||||
}
|
||||
if (data == '\r') {
|
||||
if (this->rx_len_ != 0) {
|
||||
this->rx_buffer_[this->rx_len_] = '\0';
|
||||
ESP_LOGVV(TAG, "rx: '%s'", this->rx_buffer_);
|
||||
this->parse_response_();
|
||||
this->rx_len_ = 0;
|
||||
}
|
||||
} else if (data != '\n') {
|
||||
if (this->rx_len_ >= MAX_RESPONSE_LEN) {
|
||||
ESP_LOGVV(TAG, "rx overflow, discarding");
|
||||
this->rx_len_ = 0;
|
||||
}
|
||||
this->rx_buffer_[this->rx_len_++] = static_cast<char>(data);
|
||||
const char *line = this->line_reader_.feed(data);
|
||||
if (this->line_reader_.overflowed()) {
|
||||
// Start over from this byte, so a frame right after unterminated noise is still read
|
||||
ESP_LOGVV(TAG, "rx overflow, discarding");
|
||||
this->line_reader_.restart_with(data);
|
||||
} else if (line != nullptr && line[0] != '\0') {
|
||||
ESP_LOGVV(TAG, "rx: '%s'", line);
|
||||
this->parse_response_(line);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void APCProteousCover::parse_response_() {
|
||||
void APCProteousCover::parse_response_(const char *line) {
|
||||
// Expected format: "?s=XX" or "?x=XX" where XX is a hex value
|
||||
if (this->rx_len_ < 4 || this->rx_buffer_[0] != '?' || this->rx_buffer_[2] != '=') {
|
||||
ESP_LOGV(TAG, "Invalid response: %s", this->rx_buffer_);
|
||||
if (line[0] != '?' || line[1] == '\0' || line[2] != '=' || line[3] == '\0') {
|
||||
ESP_LOGV(TAG, "Invalid response: %s", line);
|
||||
return;
|
||||
}
|
||||
|
||||
const char *hex_str = this->rx_buffer_ + 3;
|
||||
const char *hex_str = line + 3;
|
||||
char *end_ptr;
|
||||
uint8_t value = static_cast<uint8_t>(strtol(hex_str, &end_ptr, 16));
|
||||
if (end_ptr == hex_str) {
|
||||
ESP_LOGW(TAG, "Failed to parse hex value: %s", this->rx_buffer_);
|
||||
ESP_LOGW(TAG, "Failed to parse hex value: %s", line);
|
||||
return;
|
||||
}
|
||||
|
||||
bool state_changed = false;
|
||||
char type = this->rx_buffer_[1];
|
||||
char type = line[1];
|
||||
if (type == 's') {
|
||||
// bit 0 = operating, bit 1 = direction (0 = opening, 1 = closing)
|
||||
CoverOperation new_operation = COVER_OPERATION_IDLE;
|
||||
@@ -154,11 +149,10 @@ void APCProteousCover::update() {
|
||||
return;
|
||||
}
|
||||
// The line is idle, so anything left in the buffer is an unterminated echo
|
||||
if (this->rx_len_ != 0) {
|
||||
this->rx_buffer_[this->rx_len_] = '\0';
|
||||
ESP_LOGVV(TAG, "discarding stale rx '%s' before query", this->rx_buffer_);
|
||||
this->rx_len_ = 0;
|
||||
if (this->line_reader_.length() != 0) {
|
||||
ESP_LOGVV(TAG, "discarding stale rx '%s' before query", this->line_reader_.partial());
|
||||
}
|
||||
this->line_reader_.reset();
|
||||
|
||||
const char *query = this->query_s_next_ ? QUERY_S : QUERY_X;
|
||||
ESP_LOGVV(TAG, "tx: %s", query);
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "esphome/core/component.h"
|
||||
#include "esphome/core/line_reader.h"
|
||||
#include "esphome/components/uart/uart.h"
|
||||
#include "esphome/components/cover/cover.h"
|
||||
|
||||
@@ -17,7 +18,7 @@ class APCProteousCover : public cover::Cover, public PollingComponent, public ua
|
||||
|
||||
protected:
|
||||
void control(const cover::CoverCall &call) override;
|
||||
void parse_response_();
|
||||
void parse_response_(const char *line);
|
||||
void send_command_(const char *cmd);
|
||||
void write_command_(const char *cmd, uint32_t now);
|
||||
void stop_cmd_(uint32_t now);
|
||||
@@ -43,8 +44,7 @@ class APCProteousCover : public cover::Cover, public PollingComponent, public ua
|
||||
const char *pending_command_{nullptr};
|
||||
uint32_t pending_command_time_{0};
|
||||
uint32_t last_command_tx_{0};
|
||||
char rx_buffer_[MAX_RESPONSE_LEN + 1];
|
||||
uint8_t rx_len_{0};
|
||||
LineReader<MAX_RESPONSE_LEN + 1, '\r', '\n'> line_reader_;
|
||||
uint8_t command_retries_{0};
|
||||
bool query_s_next_{true};
|
||||
};
|
||||
|
||||
@@ -34,8 +34,7 @@ enum { // APDS9306 registers
|
||||
|
||||
#define APDS9306_ERROR_CHECK(func, error) \
|
||||
if (!(func)) { \
|
||||
ESP_LOGE(TAG, error); \
|
||||
this->mark_failed(); \
|
||||
this->mark_failed(LOG_STR(error)); \
|
||||
return; \
|
||||
}
|
||||
#define APDS9306_WARNING_CHECK(func, warning) \
|
||||
@@ -48,23 +47,14 @@ enum { // APDS9306 registers
|
||||
ESP_LOGV(TAG, "Writing 0x%02x to 0x%02x", value, reg); \
|
||||
if (!this->write_byte(reg, value)) { \
|
||||
ESP_LOGE(TAG, "Failed writing 0x%02x to 0x%02x", value, reg); \
|
||||
this->mark_failed(); \
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL)); \
|
||||
return; \
|
||||
}
|
||||
|
||||
void APDS9306::setup() {
|
||||
uint8_t id;
|
||||
if (!this->read_byte(APDS9306_PART_ID, &id)) { // Part ID register
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
// 0xB1 for APDS9306, 0xB3 for APDS9306-065; they differ only in bit 1
|
||||
if (!this->check_chip_id(this, APDS9306_PART_ID, 0xB1, 0xFD))
|
||||
return;
|
||||
}
|
||||
|
||||
if (id != 0xB1 && id != 0xB3) { // 0xB1 for APDS9306 0xB3 for APDS9306-065
|
||||
this->error_code_ = WRONG_ID;
|
||||
this->mark_failed();
|
||||
return;
|
||||
}
|
||||
|
||||
// ALS resolution and measurement, see datasheet or init.py for options
|
||||
uint8_t als_meas_rate = ((this->bit_width_ & 0x07) << 4) | (this->measurement_rate_ & 0x07);
|
||||
@@ -89,20 +79,6 @@ void APDS9306::dump_config() {
|
||||
LOG_SENSOR("", "APDS9306", this);
|
||||
LOG_I2C_DEVICE(this);
|
||||
|
||||
if (this->is_failed()) {
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case WRONG_ID:
|
||||
ESP_LOGE(TAG, "APDS9306 has invalid id!");
|
||||
break;
|
||||
default:
|
||||
ESP_LOGE(TAG, "Setting up APDS9306 registers failed!");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ESP_LOGCONFIG(TAG,
|
||||
" Gain: %u\n"
|
||||
" Measurement rate: %u\n"
|
||||
|
||||
@@ -50,12 +50,6 @@ class APDS9306 final : public sensor::Sensor, public PollingComponent, public i2
|
||||
void set_ambient_light_gain(AmbientLightGain gain) { this->gain_ = gain; }
|
||||
|
||||
protected:
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
COMMUNICATION_FAILED,
|
||||
WRONG_ID,
|
||||
} error_code_{NONE};
|
||||
|
||||
MeasurementBitWidth bit_width_;
|
||||
MeasurementRate measurement_rate_;
|
||||
AmbientLightGain gain_;
|
||||
|
||||
@@ -64,16 +64,8 @@ static constexpr uint16_t ALS_SATURATION = 1024 * (256 - APDS9930_ATIME_VALUE);
|
||||
bool APDS9930Component::write_reg_(uint8_t reg, uint8_t value) { return this->write_byte(reg | APDS9930_CMD, value); }
|
||||
|
||||
void APDS9930Component::setup() {
|
||||
uint8_t id;
|
||||
if (!this->read_byte(APDS9930_ID | APDS9930_CMD, &id)) {
|
||||
this->mark_failed(LOG_STR("Communication failed"));
|
||||
if (!this->check_chip_id(this, APDS9930_ID | APDS9930_CMD, APDS9930_CHIP_ID))
|
||||
return;
|
||||
}
|
||||
if (id != APDS9930_CHIP_ID) {
|
||||
ESP_LOGE(TAG, "Wrong ID 0x%02X (expected 0x%02X)", id, APDS9930_CHIP_ID);
|
||||
this->mark_failed(LOG_STR("Wrong chip ID"));
|
||||
return;
|
||||
}
|
||||
|
||||
const uint8_t control =
|
||||
(this->led_drive_ & 0b11) << CONTROL_PDRIVE_SHIFT | CONTROL_PDIODE_CH1 << CONTROL_PDIODE_SHIFT |
|
||||
|
||||
@@ -3,7 +3,6 @@ from esphome.components import i2c, sensor
|
||||
from esphome.components.const import UNIT_COUNTS
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_ID,
|
||||
CONF_ILLUMINANCE,
|
||||
DEVICE_CLASS_ILLUMINANCE,
|
||||
STATE_CLASS_MEASUREMENT,
|
||||
@@ -59,9 +58,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
cg.add(var.set_led_drive(config[CONF_LED_DRIVE]))
|
||||
cg.add(var.set_proximity_gain(config[CONF_PROXIMITY_GAIN]))
|
||||
cg.add(var.set_ambient_gain(config[CONF_AMBIENT_LIGHT_GAIN]))
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import esphome.codegen as cg
|
||||
from esphome.components import i2c
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import CONF_ID
|
||||
from esphome.types import ConfigType
|
||||
|
||||
DEPENDENCIES = ["i2c"]
|
||||
@@ -60,9 +59,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
cg.add(var.set_led_drive(config[CONF_LED_DRIVE]))
|
||||
cg.add(var.set_proximity_gain(config[CONF_PROXIMITY_GAIN]))
|
||||
cg.add(var.set_ambient_gain(config[CONF_AMBIENT_LIGHT_GAIN]))
|
||||
|
||||
@@ -8,7 +8,7 @@ ESPHOME_LOG_TAG(TAG, "apds9960");
|
||||
|
||||
#define APDS9960_ERROR_CHECK(func) \
|
||||
if (!(func)) { \
|
||||
this->mark_failed(); \
|
||||
this->mark_failed(LOG_STR("Setting up APDS9960 registers failed")); \
|
||||
return; \
|
||||
}
|
||||
#define APDS9960_WRITE_BYTE(reg, value) APDS9960_ERROR_CHECK(this->write_byte(reg, value));
|
||||
@@ -16,14 +16,12 @@ ESPHOME_LOG_TAG(TAG, "apds9960");
|
||||
void APDS9960::setup() {
|
||||
uint8_t id;
|
||||
if (!this->read_byte(0x92, &id)) { // ID register
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
if (id != 0xAB && id != 0x9C && id != 0xA8 && id != 0x9E) { // APDS9960 all should have one of these IDs
|
||||
this->error_code_ = WRONG_ID;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("APDS9960 has invalid id"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -135,20 +133,6 @@ void APDS9960::dump_config() {
|
||||
LOG_SENSOR(" ", "Clear channel", this->clear_sensor_);
|
||||
LOG_SENSOR(" ", "Proximity", this->proximity_sensor_);
|
||||
#endif
|
||||
|
||||
if (this->is_failed()) {
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case WRONG_ID:
|
||||
ESP_LOGE(TAG, "APDS9960 has invalid id!");
|
||||
break;
|
||||
default:
|
||||
ESP_LOGE(TAG, "Setting up APDS9960 registers failed!");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#define APDS9960_WARNING_CHECK(func, warning) \
|
||||
|
||||
@@ -58,11 +58,6 @@ class APDS9960 final : public PollingComponent, public i2c::I2CDevice {
|
||||
uint8_t gesture_gain_;
|
||||
uint8_t gesture_wait_time_;
|
||||
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
COMMUNICATION_FAILED,
|
||||
WRONG_ID,
|
||||
} error_code_{NONE};
|
||||
bool gesture_up_started_{false};
|
||||
bool gesture_down_started_{false};
|
||||
bool gesture_left_started_{false};
|
||||
|
||||
@@ -65,6 +65,9 @@ void APIServer::socket_failed_(const LogString *msg) {
|
||||
}
|
||||
|
||||
void APIServer::setup() {
|
||||
#if defined(USE_API_HOMEASSISTANT_STATES) && defined(HOMEASSISTANT_STATE_SUBSCRIPTION_COUNT)
|
||||
this->state_subs_.reserve(HOMEASSISTANT_STATE_SUBSCRIPTION_COUNT);
|
||||
#endif
|
||||
#ifdef USE_API_NOISE
|
||||
// Always reserve the slot: flash preferences are positional on esp8266, so
|
||||
// a yaml key build must keep the layout of a runtime key build
|
||||
|
||||
@@ -9,7 +9,6 @@ from esphome.const import (
|
||||
CONF_DIR_PIN,
|
||||
CONF_DIRECTION,
|
||||
CONF_HYSTERESIS,
|
||||
CONF_ID,
|
||||
CONF_POWER_MODE,
|
||||
CONF_RANGE,
|
||||
CONF_WATCHDOG,
|
||||
@@ -209,9 +208,7 @@ CONFIG_SCHEMA = cv.All(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_direction(config[CONF_DIRECTION]))
|
||||
cg.add(var.set_watchdog(config[CONF_WATCHDOG]))
|
||||
|
||||
@@ -23,7 +23,7 @@ static const uint8_t REGISTER_MAGNITUDE = 0x1B; // 16 bytes / R
|
||||
|
||||
void AS5600Component::setup() {
|
||||
if (!this->read_byte(REGISTER_STATUS).has_value()) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -54,7 +54,7 @@ void AS5600Component::setup() {
|
||||
|
||||
// write config to config register
|
||||
if (!this->write_byte_16(REGISTER_CONF, config)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -87,10 +87,8 @@ void AS5600Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "AS5600:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
if (this->is_failed())
|
||||
return;
|
||||
}
|
||||
|
||||
ESP_LOGCONFIG(TAG,
|
||||
" Watchdog: %d\n"
|
||||
|
||||
@@ -30,10 +30,7 @@ CONF_END_POSITION = "end_position"
|
||||
CONF_OUT_OF_RANGE_MODE = "out_of_range_mode"
|
||||
|
||||
OutOfRangeMode = as5600_ns.enum("OutRangeMode")
|
||||
OUT_OF_RANGE_MODES = {
|
||||
"MIN_MAX": OutOfRangeMode.OUT_RANGE_MODE_MIN_MAX,
|
||||
"NAN": OutOfRangeMode.OUT_RANGE_MODE_NAN,
|
||||
}
|
||||
OUT_OF_RANGE_MODES = OutOfRangeMode.options("MIN_MAX", "NAN", prefix="OUT_RANGE_MODE_")
|
||||
|
||||
|
||||
CONF_AS5600_ID = "as5600_id"
|
||||
|
||||
@@ -9,19 +9,12 @@ ESPHOME_LOG_TAG(TAG, "as7341");
|
||||
void AS7341Component::setup() {
|
||||
LOG_I2C_DEVICE(this);
|
||||
|
||||
// Verify device ID
|
||||
uint8_t id;
|
||||
this->read_byte(AS7341_ID, &id);
|
||||
ESP_LOGCONFIG(TAG, " Read ID: 0x%X", id);
|
||||
if ((id & 0xFC) != (AS7341_CHIP_ID << 2)) {
|
||||
this->mark_failed();
|
||||
if (!this->check_chip_id(this, AS7341_ID, AS7341_CHIP_ID << 2, 0xFC))
|
||||
return;
|
||||
}
|
||||
|
||||
// Power on (enter IDLE state)
|
||||
if (!this->enable_power(true)) {
|
||||
ESP_LOGE(TAG, " Power on failed!");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Power on failed"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -35,9 +28,6 @@ void AS7341Component::setup() {
|
||||
void AS7341Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "AS7341:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
ESP_LOGCONFIG(TAG,
|
||||
" Gain: %u\n"
|
||||
|
||||
@@ -5,7 +5,6 @@ import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_CLEAR,
|
||||
CONF_GAIN,
|
||||
CONF_ID,
|
||||
DEVICE_CLASS_EMPTY,
|
||||
ICON_BRIGHTNESS_5,
|
||||
STATE_CLASS_MEASUREMENT,
|
||||
@@ -97,9 +96,7 @@ SENSORS = {
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_gain(config[CONF_GAIN]))
|
||||
cg.add(var.set_atime(config[CONF_ATIME]))
|
||||
|
||||
@@ -5,7 +5,6 @@ from esphome.const import (
|
||||
CONF_CALIBRATION,
|
||||
CONF_GAIN,
|
||||
CONF_GLASS_ATTENUATION_FACTOR,
|
||||
CONF_ID,
|
||||
CONF_TYPE,
|
||||
CONF_UPDATE_INTERVAL,
|
||||
)
|
||||
@@ -55,12 +54,9 @@ GAINS_41 = {
|
||||
GAINS_43 = {**GAINS_41, "X1024": Gain.GAIN_1024X, "X2048": Gain.GAIN_2048X}
|
||||
|
||||
Normalization = as734x_ns.enum("Normalization", True)
|
||||
NORMALIZATIONS = {
|
||||
"NONE": Normalization.NORMALIZATION_NONE,
|
||||
"ALL": Normalization.NORMALIZATION_ALL,
|
||||
"BANDS": Normalization.NORMALIZATION_BANDS,
|
||||
"CLEAR": Normalization.NORMALIZATION_CLEAR,
|
||||
}
|
||||
NORMALIZATIONS = Normalization.options(
|
||||
"NONE", "ALL", "BANDS", "CLEAR", prefix="NORMALIZATION_"
|
||||
)
|
||||
|
||||
# Per-channel correction for the golden device, measured by the manufacturer.
|
||||
DEFAULT_CHANNEL_CORRECTION_43 = [
|
||||
@@ -169,9 +165,7 @@ def _per_band(
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
chip = config[CONF_TYPE]
|
||||
cg.add_define("USE_AS7341" if chip == "AS7341" else "USE_AS7343")
|
||||
var = cg.new_Pvariable(config[CONF_ID], cg.RawExpression(f"&as734x::{chip}_CHIP"))
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config, cg.RawExpression(f"&as734x::{chip}_CHIP"))
|
||||
cg.add(var.set_gain(config[CONF_GAIN]))
|
||||
cg.add(var.set_atime(config[CONF_ATIME]))
|
||||
cg.add(var.set_astep(config[CONF_ASTEP]))
|
||||
|
||||
@@ -355,9 +355,6 @@ void AS734XComponent::dump_config() {
|
||||
#ifdef USE_AS734X_RGB
|
||||
LOG_TEXT_SENSOR(" ", "RGB hex", this->rgb_hex_sensor_);
|
||||
#endif
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
void AS734XComponent::enable_led(bool enable) {
|
||||
|
||||
@@ -73,9 +73,7 @@ CONFIG_SCHEMA = cv.All(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
await i2c.new_i2c_component(config)
|
||||
|
||||
|
||||
# Actions
|
||||
@@ -93,7 +91,7 @@ def _megahertz(value: float) -> int:
|
||||
|
||||
|
||||
def _microamps(value: float) -> int:
|
||||
return int(value * 1000000)
|
||||
return round(value * 1000000)
|
||||
|
||||
|
||||
RADAR_SETTINGS_SCHEMA = cv.Schema(
|
||||
|
||||
@@ -52,7 +52,7 @@ void ATM90E26Component::setup() {
|
||||
uint16_t read = this->read16_(ATM90E26_REGISTER_LASTDATA);
|
||||
if (read != 0x0030) {
|
||||
ESP_LOGW(TAG, "Could not initialize ATM90E26 IC, check SPI settings: %d", read);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
// TODO: 100 * <nominal voltage, e.g. 230> * sqrt(2) * <fraction of nominal, e.g. 0.9> / (4 * gain_voltage/32768)
|
||||
@@ -120,21 +120,18 @@ void ATM90E26Component::setup() {
|
||||
|
||||
ESP_LOGW(TAG, "Could not initialize ATM90E26 IC: CS1 was incorrect, expected: 0x%04X",
|
||||
this->read16_(ATM90E26_REGISTER_CS1));
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Checksum mismatch"));
|
||||
}
|
||||
if (sys_status & 0x3000) { // Checksum 2 Error
|
||||
ESP_LOGW(TAG, "Could not initialize ATM90E26 IC: CS2 was incorrect, expected: 0x%04X",
|
||||
this->read16_(ATM90E26_REGISTER_CS2));
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Checksum mismatch"));
|
||||
}
|
||||
}
|
||||
|
||||
void ATM90E26Component::dump_config() {
|
||||
ESP_LOGCONFIG("", "ATM90E26:");
|
||||
LOG_PIN(" CS Pin: ", this->cs_);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
LOG_SENSOR(" ", "Voltage A", this->voltage_sensor_);
|
||||
LOG_SENSOR(" ", "Current A", this->current_sensor_);
|
||||
|
||||
@@ -168,7 +168,7 @@ void ATM90E32Component::setup() {
|
||||
this->write16_(ATM90E32_REGISTER_CFGREGACCEN, 0x55AA); // enable register config access
|
||||
if (!this->validate_spi_read_(0x55AA, "setup()")) {
|
||||
ESP_LOGW(TAG, "Could not initialize ATM90E32 IC, check SPI settings");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -411,9 +411,6 @@ void ATM90E32Component::log_calibration_status_() {
|
||||
void ATM90E32Component::dump_config() {
|
||||
ESP_LOGCONFIG("", "ATM90E32:");
|
||||
LOG_PIN(" CS Pin: ", this->cs_);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
LOG_SENSOR(" ", "Voltage A", this->phase_[PHASEA].voltage_sensor_);
|
||||
LOG_SENSOR(" ", "Current A", this->phase_[PHASEA].current_sensor_);
|
||||
|
||||
@@ -27,13 +27,7 @@ audio_ns = cg.esphome_ns.namespace("audio")
|
||||
|
||||
AudioFile = audio_ns.struct("AudioFile")
|
||||
AudioFileType = audio_ns.enum("AudioFileType", is_class=True)
|
||||
AUDIO_FILE_TYPE_ENUM = {
|
||||
"NONE": AudioFileType.NONE,
|
||||
"WAV": AudioFileType.WAV,
|
||||
"MP3": AudioFileType.MP3,
|
||||
"FLAC": AudioFileType.FLAC,
|
||||
"OPUS": AudioFileType.OPUS,
|
||||
}
|
||||
AUDIO_FILE_TYPE_ENUM = AudioFileType.options("NONE", "WAV", "MP3", "FLAC", "OPUS")
|
||||
|
||||
MEMORY_PSRAM = "psram"
|
||||
MEMORY_INTERNAL = "internal"
|
||||
|
||||
@@ -12,14 +12,10 @@ DEPENDENCIES = ["bedjet"]
|
||||
BedJetClimate = bedjet_ns.class_("BedJetClimate", climate.Climate, cg.PollingComponent)
|
||||
BedjetHeatMode = bedjet_ns.enum("BedjetHeatMode")
|
||||
BedjetTemperatureSource = bedjet_ns.enum("BedjetTemperatureSource")
|
||||
BEDJET_HEAT_MODES = {
|
||||
"heat": BedjetHeatMode.HEAT_MODE_HEAT,
|
||||
"extended": BedjetHeatMode.HEAT_MODE_EXTENDED,
|
||||
}
|
||||
BEDJET_TEMPERATURE_SOURCES = {
|
||||
"outlet": BedjetTemperatureSource.TEMPERATURE_SOURCE_OUTLET,
|
||||
"ambient": BedjetTemperatureSource.TEMPERATURE_SOURCE_AMBIENT,
|
||||
}
|
||||
BEDJET_HEAT_MODES = BedjetHeatMode.options("heat", "extended", prefix="HEAT_MODE_")
|
||||
BEDJET_TEMPERATURE_SOURCES = BedjetTemperatureSource.options(
|
||||
"outlet", "ambient", prefix="TEMPERATURE_SOURCE_"
|
||||
)
|
||||
|
||||
CONFIG_SCHEMA = (
|
||||
climate.climate_schema(BedJetClimate)
|
||||
|
||||
@@ -6,7 +6,6 @@ import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_GAIN,
|
||||
CONF_GLASS_ATTENUATION_FACTOR,
|
||||
CONF_ID,
|
||||
CONF_INTEGRATION_TIME,
|
||||
)
|
||||
from esphome.types import ConfigType
|
||||
@@ -25,11 +24,7 @@ BH1745Component = bh1745_ns.class_(
|
||||
)
|
||||
|
||||
AdcGain = bh1745_ns.enum("AdcGain", is_class=True)
|
||||
ADC_GAINS = {
|
||||
"1X": AdcGain.ADC_GAIN_1X,
|
||||
"2X": AdcGain.ADC_GAIN_2X,
|
||||
"16X": AdcGain.ADC_GAIN_16X,
|
||||
}
|
||||
ADC_GAINS = AdcGain.options("1X", "2X", "16X", prefix="ADC_GAIN_")
|
||||
|
||||
MeasurementTime = bh1745_ns.enum("MeasurementTime", is_class=True)
|
||||
MEASUREMENT_TIMES = {
|
||||
@@ -66,9 +61,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_adc_gain(config[CONF_GAIN]))
|
||||
cg.add(var.set_measurement_time(config[CONF_INTEGRATION_TIME]))
|
||||
|
||||
@@ -63,15 +63,8 @@ static float calculate_cct(uint16_t red, uint16_t green, uint16_t blue, bool low
|
||||
}
|
||||
|
||||
void BH1745Component::setup() {
|
||||
uint8_t manufacturer_id;
|
||||
if (!this->read_byte(REG_MANUFACTURER_ID, &manufacturer_id)) {
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
if (!this->check_chip_id(this, REG_MANUFACTURER_ID, MANUFACTURER_ID))
|
||||
return;
|
||||
}
|
||||
if (manufacturer_id != MANUFACTURER_ID) {
|
||||
this->mark_failed(LOG_STR("Wrong manufacturer ID"));
|
||||
return;
|
||||
}
|
||||
uint8_t system_control;
|
||||
if (!this->read_byte(REG_SYSTEM_CONTROL, &system_control) ||
|
||||
(system_control & SYSTEM_CONTROL_PART_ID_MASK) != PART_ID) {
|
||||
|
||||
@@ -65,7 +65,7 @@ MTreg:
|
||||
void BH1750Sensor::setup() {
|
||||
uint8_t turn_on = BH1750_COMMAND_POWER_ON;
|
||||
if (this->write(&turn_on, 1) != i2c::ERROR_OK) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
this->state_ = IDLE;
|
||||
@@ -74,9 +74,6 @@ void BH1750Sensor::setup() {
|
||||
void BH1750Sensor::dump_config() {
|
||||
LOG_SENSOR("", "BH1750", this);
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL_FOR, this->get_name().c_str());
|
||||
}
|
||||
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
}
|
||||
|
||||
@@ -35,10 +35,9 @@ CONF_ENERGY_TOTAL = "energy_total"
|
||||
bl0939_ns = cg.esphome_ns.namespace("bl0939")
|
||||
BL0939 = bl0939_ns.class_("BL0939", cg.PollingComponent, uart.UARTDevice)
|
||||
BL0939Mode = bl0939_ns.enum("BL0939Mode", is_class=True)
|
||||
MODE_OPTIONS = {
|
||||
"direct": BL0939Mode.BL0939_MODE_DIRECT,
|
||||
"current_transformer": BL0939Mode.BL0939_MODE_CURRENT_TRANSFORMER,
|
||||
}
|
||||
MODE_OPTIONS = BL0939Mode.options(
|
||||
"direct", "current_transformer", prefix="BL0939_MODE_"
|
||||
)
|
||||
# Must match the mode_ member initializer in bl0939.h; set_mode() is skipped
|
||||
# when the config already equals it.
|
||||
DEFAULT_MODE = "direct"
|
||||
|
||||
@@ -62,7 +62,8 @@ void BluedroidGattClient::loop() {
|
||||
auto ret = esp_ble_gattc_app_register(this->app_id);
|
||||
if (ret) {
|
||||
ESP_LOGE(TAG, "gattc app register failed: app_id=%d code=%d", this->app_id, ret);
|
||||
this->mark_failed();
|
||||
this->mark_failed(
|
||||
LOG_STR("Registration failed; if the error was ESP_GATT_NO_RESOURCES, reduce the connection slots"));
|
||||
}
|
||||
// Do not wait for REG_EVT; connect() rejects until it lands.
|
||||
this->set_idle_();
|
||||
@@ -108,12 +109,7 @@ void BluedroidGattClient::ble_before_disabled_event_handler() {
|
||||
this->enable_loop();
|
||||
}
|
||||
|
||||
void BluedroidGattClient::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "Bluedroid GATT client %d", this->connection_index_);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, " Registration failed; if the error was ESP_GATT_NO_RESOURCES, reduce the connection slots");
|
||||
}
|
||||
}
|
||||
void BluedroidGattClient::dump_config() { ESP_LOGCONFIG(TAG, "Bluedroid GATT client %d", this->connection_index_); }
|
||||
|
||||
// ---- contract ops ----
|
||||
|
||||
@@ -680,7 +676,8 @@ bool BluedroidGattClient::gattc_event_handler(esp_gattc_cb_event_t event, esp_ga
|
||||
this->gattc_if_ = esp_gattc_if;
|
||||
} else {
|
||||
ESP_LOGE(TAG, "[%d] gattc app registration failed, status=%d", this->connection_index_, param->reg.status);
|
||||
this->mark_failed();
|
||||
this->mark_failed(
|
||||
LOG_STR("Registration failed; if the error was ESP_GATT_NO_RESOURCES, reduce the connection slots"));
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -76,16 +76,14 @@ void RP2GattClient::setup() {
|
||||
// Pre-create every pool entry so the packet handlers' allocate() calls are
|
||||
// always a free-list pop -- the IRQ path must never reach malloc().
|
||||
if (!this->event_pool_.warm() || !this->notify_pool_.warm()) {
|
||||
ESP_LOGE(TAG, "GATT event pool warm-up failed");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("GATT event pool warm-up failed"));
|
||||
return;
|
||||
}
|
||||
|
||||
// Register this engine for IRQ-context event routing.
|
||||
if (instance_count >= ESPHOME_BLE_GATT_CLIENT_COUNT) {
|
||||
// Cannot happen with codegen-sized storage; refuse loudly if it ever does.
|
||||
ESP_LOGE(TAG, "GATT client registry full");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("GATT client registry full"));
|
||||
return;
|
||||
}
|
||||
{
|
||||
|
||||
@@ -21,7 +21,7 @@ static constexpr uint32_t MAX_TIMER_DURATION_S = 255 * 60;
|
||||
|
||||
void BM8563::setup() {
|
||||
if (!this->write_byte_16(CONTROL_STATUS_1_REG, 0)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -31,9 +31,6 @@ void BM8563::update() { this->read_time(); }
|
||||
void BM8563::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BM8563:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
void BM8563::start_timer(uint32_t duration_s) {
|
||||
|
||||
@@ -2,7 +2,7 @@ from esphome import automation
|
||||
import esphome.codegen as cg
|
||||
from esphome.components import i2c, time
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import CONF_DURATION, CONF_ID
|
||||
from esphome.const import CONF_DURATION
|
||||
from esphome.types import ConfigType
|
||||
|
||||
DEPENDENCIES = ["i2c"]
|
||||
@@ -50,7 +50,5 @@ automation.register_apply_action(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
await time.register_time(var, config)
|
||||
|
||||
@@ -24,23 +24,14 @@ DOMAIN = "bme280_base"
|
||||
|
||||
bme280_ns = cg.esphome_ns.namespace("bme280_base")
|
||||
BME280Oversampling = bme280_ns.enum("BME280Oversampling")
|
||||
OVERSAMPLING_OPTIONS = {
|
||||
"NONE": BME280Oversampling.BME280_OVERSAMPLING_NONE,
|
||||
"1X": BME280Oversampling.BME280_OVERSAMPLING_1X,
|
||||
"2X": BME280Oversampling.BME280_OVERSAMPLING_2X,
|
||||
"4X": BME280Oversampling.BME280_OVERSAMPLING_4X,
|
||||
"8X": BME280Oversampling.BME280_OVERSAMPLING_8X,
|
||||
"16X": BME280Oversampling.BME280_OVERSAMPLING_16X,
|
||||
}
|
||||
OVERSAMPLING_OPTIONS = BME280Oversampling.options(
|
||||
"NONE", "1X", "2X", "4X", "8X", "16X", prefix="BME280_OVERSAMPLING_"
|
||||
)
|
||||
|
||||
BME280IIRFilter = bme280_ns.enum("BME280IIRFilter")
|
||||
IIR_FILTER_OPTIONS = {
|
||||
"OFF": BME280IIRFilter.BME280_IIR_FILTER_OFF,
|
||||
"2X": BME280IIRFilter.BME280_IIR_FILTER_2X,
|
||||
"4X": BME280IIRFilter.BME280_IIR_FILTER_4X,
|
||||
"8X": BME280IIRFilter.BME280_IIR_FILTER_8X,
|
||||
"16X": BME280IIRFilter.BME280_IIR_FILTER_16X,
|
||||
}
|
||||
IIR_FILTER_OPTIONS = BME280IIRFilter.options(
|
||||
"OFF", "2X", "4X", "8X", "16X", prefix="BME280_IIR_FILTER_"
|
||||
)
|
||||
|
||||
CONFIG_SCHEMA_BASE = cv.Schema(
|
||||
{
|
||||
|
||||
@@ -3,12 +3,11 @@
|
||||
|
||||
#include "bme280_base.h"
|
||||
#include "esphome/core/hal.h"
|
||||
#include "esphome/core/helpers.h"
|
||||
#include "esphome/core/log.h"
|
||||
#include <esphome/components/sensor/sensor.h>
|
||||
#include <esphome/core/component.h>
|
||||
|
||||
#define BME280_ERROR_WRONG_CHIP_ID "Wrong chip ID or no response"
|
||||
|
||||
namespace esphome::bme280_base {
|
||||
|
||||
ESPHOME_LOG_TAG(TAG, "bme280.sensor");
|
||||
@@ -100,13 +99,11 @@ void BME280Component::setup() {
|
||||
}
|
||||
|
||||
if (!this->read_byte(BME280_REGISTER_CHIPID, &chip_id)) {
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
if (chip_id != 0x60) {
|
||||
this->error_code_ = WRONG_CHIP_ID;
|
||||
this->mark_failed(LOG_STR(BME280_ERROR_WRONG_CHIP_ID));
|
||||
this->mark_failed(LOG_STR("Wrong chip ID or no response"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -148,11 +145,10 @@ void BME280Component::setup() {
|
||||
this->calibration_.h1 = read_u8_(BME280_REGISTER_DIG_H1);
|
||||
this->calibration_.h2 = read_s16_le_(BME280_REGISTER_DIG_H2);
|
||||
this->calibration_.h3 = read_u8_(BME280_REGISTER_DIG_H3);
|
||||
// h4 and h5 are signed 12-bit values; shift left then arithmetic right shift to sign-extend
|
||||
int16_t h4_raw = read_u8_(BME280_REGISTER_DIG_H4) << 4 | (read_u8_(BME280_REGISTER_DIG_H4 + 1) & 0x0F);
|
||||
this->calibration_.h4 = static_cast<int16_t>(h4_raw << 4) >> 4;
|
||||
int16_t h5_raw = read_u8_(BME280_REGISTER_DIG_H5 + 1) << 4 | (read_u8_(BME280_REGISTER_DIG_H5) >> 4);
|
||||
this->calibration_.h5 = static_cast<int16_t>(h5_raw << 4) >> 4;
|
||||
this->calibration_.h4 =
|
||||
sign_extend<12>(read_u8_(BME280_REGISTER_DIG_H4) << 4 | (read_u8_(BME280_REGISTER_DIG_H4 + 1) & 0x0F));
|
||||
this->calibration_.h5 =
|
||||
sign_extend<12>(read_u8_(BME280_REGISTER_DIG_H5 + 1) << 4 | (read_u8_(BME280_REGISTER_DIG_H5) >> 4));
|
||||
this->calibration_.h6 = read_u8_(BME280_REGISTER_DIG_H6);
|
||||
|
||||
uint8_t humid_control_val = 0;
|
||||
@@ -182,17 +178,6 @@ void BME280Component::setup() {
|
||||
}
|
||||
void BME280Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BME280:");
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case WRONG_CHIP_ID:
|
||||
ESP_LOGE(TAG, BME280_ERROR_WRONG_CHIP_ID);
|
||||
break;
|
||||
case NONE:
|
||||
default:
|
||||
break;
|
||||
}
|
||||
ESP_LOGCONFIG(TAG, " IIR Filter: %s", iir_filter_to_str(this->iir_filter_));
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
|
||||
|
||||
@@ -101,11 +101,6 @@ class BME280Component : public PollingComponent {
|
||||
sensor::Sensor *temperature_sensor_{nullptr};
|
||||
sensor::Sensor *pressure_sensor_{nullptr};
|
||||
sensor::Sensor *humidity_sensor_{nullptr};
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
COMMUNICATION_FAILED,
|
||||
WRONG_CHIP_ID,
|
||||
} error_code_{NONE};
|
||||
};
|
||||
|
||||
} // namespace esphome::bme280_base
|
||||
|
||||
@@ -72,22 +72,24 @@ constexpr float BME680_GAS_LOOKUP_TABLE_2[16] PROGMEM = {0.0, 0.0, 0.0, 0.0, 0.
|
||||
}
|
||||
|
||||
void BME680Component::setup() {
|
||||
if (!this->setup_registers_())
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
}
|
||||
|
||||
bool BME680Component::setup_registers_() {
|
||||
uint8_t chip_id;
|
||||
if (!this->read_byte(BME680_REGISTER_CHIPID, &chip_id) || chip_id != 0x61) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Read calibration
|
||||
uint8_t coeff1[25];
|
||||
if (!this->read_bytes(BME680_REGISTER_COEFF1, coeff1, 25)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
uint8_t coeff2[16];
|
||||
if (!this->read_bytes(BME680_REGISTER_COEFF2, coeff2, 16)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
this->calibration_.t1 = coeff2[9] << 8 | coeff2[8];
|
||||
@@ -119,20 +121,17 @@ void BME680Component::setup() {
|
||||
|
||||
uint8_t temp_var = 0;
|
||||
if (!this->read_byte(0x02, &temp_var)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
this->calibration_.res_heat_range = ((temp_var & 0x30) / 16);
|
||||
|
||||
if (!this->read_byte(0x00, &temp_var)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
this->calibration_.res_heat_val = (int8_t) temp_var;
|
||||
|
||||
if (!this->read_byte(0x04, &temp_var)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
this->calibration_.range_sw_err = ((int8_t) temp_var & (int8_t) 0xf0) / 16;
|
||||
|
||||
@@ -141,41 +140,35 @@ void BME680Component::setup() {
|
||||
// Config register
|
||||
uint8_t config_register;
|
||||
if (!this->read_byte(BME680_REGISTER_CONFIG, &config_register)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
config_register &= ~0b00011100;
|
||||
config_register |= (this->iir_filter_ & 0b111) << 2;
|
||||
if (!this->write_byte(BME680_REGISTER_CONFIG, config_register)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Humidity control register
|
||||
uint8_t hum_control;
|
||||
if (!this->read_byte(BME680_REGISTER_CONTROL_HUMIDITY, &hum_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
hum_control &= ~0b00000111;
|
||||
hum_control |= this->humidity_oversampling_ & 0b111;
|
||||
if (!this->write_byte(BME680_REGISTER_CONTROL_HUMIDITY, hum_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Gas 1 control register
|
||||
uint8_t gas1_control;
|
||||
if (!this->read_byte(BME680_REGISTER_CONTROL_GAS1, &gas1_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
gas1_control &= ~0b00011111;
|
||||
gas1_control |= 1 << 4;
|
||||
gas1_control |= 0; // profile 0
|
||||
if (!this->write_byte(BME680_REGISTER_CONTROL_GAS1, gas1_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
const bool heat_off = this->heater_temperature_ == 0 || this->heater_duration_ == 0;
|
||||
@@ -183,40 +176,34 @@ void BME680Component::setup() {
|
||||
// Gas 0 control register
|
||||
uint8_t gas0_control;
|
||||
if (!this->read_byte(BME680_REGISTER_CONTROL_GAS0, &gas0_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
gas0_control &= ~0b00001000;
|
||||
gas0_control |= heat_off << 3;
|
||||
if (!this->write_byte(BME680_REGISTER_CONTROL_GAS0, gas0_control)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!heat_off) {
|
||||
// Gas Heater Temperature
|
||||
uint8_t temperature = this->calc_heater_resistance_(this->heater_temperature_);
|
||||
if (!this->write_byte(BME680_REGISTER_HEATER_HEAT0, temperature)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Gas Heater Duration
|
||||
uint8_t duration = this->calc_heater_duration_(this->heater_duration_);
|
||||
|
||||
if (!this->write_byte(BME680_REGISTER_HEATER_WAIT0, duration)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void BME680Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BME680:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
ESP_LOGCONFIG(TAG, " IIR Filter: %s", iir_filter_to_str(this->iir_filter_));
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
|
||||
|
||||
@@ -101,6 +101,8 @@ class BME680Component final : public PollingComponent, public i2c::I2CDevice {
|
||||
void update() override;
|
||||
|
||||
protected:
|
||||
/// Configure the sensor registers; false on an I2C failure.
|
||||
bool setup_registers_();
|
||||
/// Calculate the heater resistance value to send to the BME680 register.
|
||||
uint8_t calc_heater_resistance_(uint16_t temperature);
|
||||
/// Calculate the heater duration value to send to the BME680 register.
|
||||
|
||||
@@ -7,7 +7,6 @@ from esphome.const import (
|
||||
CONF_GAS_RESISTANCE,
|
||||
CONF_HEATER,
|
||||
CONF_HUMIDITY,
|
||||
CONF_ID,
|
||||
CONF_IIR_FILTER,
|
||||
CONF_OVERSAMPLING,
|
||||
CONF_PRESSURE,
|
||||
@@ -28,26 +27,14 @@ DEPENDENCIES = ["i2c"]
|
||||
|
||||
bme680_ns = cg.esphome_ns.namespace("bme680")
|
||||
BME680Oversampling = bme680_ns.enum("BME680Oversampling")
|
||||
OVERSAMPLING_OPTIONS = {
|
||||
"NONE": BME680Oversampling.BME680_OVERSAMPLING_NONE,
|
||||
"1X": BME680Oversampling.BME680_OVERSAMPLING_1X,
|
||||
"2X": BME680Oversampling.BME680_OVERSAMPLING_2X,
|
||||
"4X": BME680Oversampling.BME680_OVERSAMPLING_4X,
|
||||
"8X": BME680Oversampling.BME680_OVERSAMPLING_8X,
|
||||
"16X": BME680Oversampling.BME680_OVERSAMPLING_16X,
|
||||
}
|
||||
OVERSAMPLING_OPTIONS = BME680Oversampling.options(
|
||||
"NONE", "1X", "2X", "4X", "8X", "16X", prefix="BME680_OVERSAMPLING_"
|
||||
)
|
||||
|
||||
BME680IIRFilter = bme680_ns.enum("BME680IIRFilter")
|
||||
IIR_FILTER_OPTIONS = {
|
||||
"OFF": BME680IIRFilter.BME680_IIR_FILTER_OFF,
|
||||
"1X": BME680IIRFilter.BME680_IIR_FILTER_1X,
|
||||
"3X": BME680IIRFilter.BME680_IIR_FILTER_3X,
|
||||
"7X": BME680IIRFilter.BME680_IIR_FILTER_7X,
|
||||
"15X": BME680IIRFilter.BME680_IIR_FILTER_15X,
|
||||
"31X": BME680IIRFilter.BME680_IIR_FILTER_31X,
|
||||
"63X": BME680IIRFilter.BME680_IIR_FILTER_63X,
|
||||
"127X": BME680IIRFilter.BME680_IIR_FILTER_127X,
|
||||
}
|
||||
IIR_FILTER_OPTIONS = BME680IIRFilter.options(
|
||||
"OFF", "1X", "3X", "7X", "15X", "31X", "63X", "127X", prefix="BME680_IIR_FILTER_"
|
||||
)
|
||||
|
||||
BME680Component = bme680_ns.class_(
|
||||
"BME680Component", cg.PollingComponent, i2c.I2CDevice
|
||||
@@ -127,9 +114,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
if await sensors(CONF_TEMPERATURE, var.set_temperature_sensor):
|
||||
|
||||
@@ -19,10 +19,7 @@ CONF_SUPPLY_VOLTAGE = "supply_voltage"
|
||||
bme680_bsec_ns = cg.esphome_ns.namespace("bme680_bsec")
|
||||
|
||||
IAQMode = bme680_bsec_ns.enum("IAQMode")
|
||||
IAQ_MODE_OPTIONS = {
|
||||
"STATIC": IAQMode.IAQ_MODE_STATIC,
|
||||
"MOBILE": IAQMode.IAQ_MODE_MOBILE,
|
||||
}
|
||||
IAQ_MODE_OPTIONS = IAQMode.options("STATIC", "MOBILE", prefix="IAQ_MODE_")
|
||||
|
||||
SupplyVoltage = bme680_bsec_ns.enum("SupplyVoltage")
|
||||
SUPPLY_VOLTAGE_OPTIONS = {
|
||||
@@ -31,10 +28,7 @@ SUPPLY_VOLTAGE_OPTIONS = {
|
||||
}
|
||||
|
||||
SampleRate = bme680_bsec_ns.enum("SampleRate")
|
||||
SAMPLE_RATE_OPTIONS = {
|
||||
"LP": SampleRate.SAMPLE_RATE_LP,
|
||||
"ULP": SampleRate.SAMPLE_RATE_ULP,
|
||||
}
|
||||
SAMPLE_RATE_OPTIONS = SampleRate.options("LP", "ULP", prefix="SAMPLE_RATE_")
|
||||
|
||||
BME680BSECComponent = bme680_bsec_ns.class_(
|
||||
"BME680BSECComponent", cg.Component, i2c.I2CDevice
|
||||
@@ -79,9 +73,7 @@ CONFIG_SCHEMA = cv.All(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_device_id(str(config[CONF_ID])))
|
||||
cg.add(var.set_temperature_offset(config[CONF_TEMPERATURE_OFFSET]))
|
||||
|
||||
@@ -36,28 +36,18 @@ BME68xBSEC2Component = bme68x_bsec2_ns.class_("BME68xBSEC2Component", cg.Compone
|
||||
MODEL_OPTIONS = ["bme680", "bme688"]
|
||||
|
||||
AlgorithmOutput = bme68x_bsec2_ns.enum("AlgorithmOutput")
|
||||
ALGORITHM_OUTPUT_OPTIONS = {
|
||||
"classification": AlgorithmOutput.ALGORITHM_OUTPUT_CLASSIFICATION,
|
||||
"regression": AlgorithmOutput.ALGORITHM_OUTPUT_REGRESSION,
|
||||
}
|
||||
ALGORITHM_OUTPUT_OPTIONS = AlgorithmOutput.options(
|
||||
"classification", "regression", prefix="ALGORITHM_OUTPUT_"
|
||||
)
|
||||
|
||||
OperatingAge = bme68x_bsec2_ns.enum("OperatingAge")
|
||||
OPERATING_AGE_OPTIONS = {
|
||||
"4d": OperatingAge.OPERATING_AGE_4D,
|
||||
"28d": OperatingAge.OPERATING_AGE_28D,
|
||||
}
|
||||
OPERATING_AGE_OPTIONS = OperatingAge.options("4d", "28d", prefix="OPERATING_AGE_")
|
||||
|
||||
SampleRate = bme68x_bsec2_ns.enum("SampleRate")
|
||||
SAMPLE_RATE_OPTIONS = {
|
||||
"LP": SampleRate.SAMPLE_RATE_LP,
|
||||
"ULP": SampleRate.SAMPLE_RATE_ULP,
|
||||
}
|
||||
SAMPLE_RATE_OPTIONS = SampleRate.options("LP", "ULP", prefix="SAMPLE_RATE_")
|
||||
|
||||
Voltage = bme68x_bsec2_ns.enum("Voltage")
|
||||
VOLTAGE_OPTIONS = {
|
||||
"1.8V": Voltage.VOLTAGE_1_8V,
|
||||
"3.3V": Voltage.VOLTAGE_3_3V,
|
||||
}
|
||||
VOLTAGE_OPTIONS = Voltage.options("1.8V", "3.3V", prefix="VOLTAGE_")
|
||||
|
||||
ALGORITHM_OUTPUT_FILE_NAME = {
|
||||
"classification": "sel",
|
||||
|
||||
@@ -117,18 +117,21 @@ const uint8_t BMI160_REGISTER_DATA_TEMP_MSB = 0x21;
|
||||
const float GRAVITY_EARTH = 9.80665f;
|
||||
|
||||
void BMI160Component::internal_setup_(int stage) {
|
||||
if (!this->setup_stage_(stage))
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
}
|
||||
|
||||
bool BMI160Component::setup_stage_(int stage) {
|
||||
switch (stage) {
|
||||
case 0:
|
||||
uint8_t chipid;
|
||||
if (!this->read_byte(BMI160_REGISTER_CHIPID, &chipid) || (chipid != 0b11010001)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
ESP_LOGV(TAG, " Bringing accelerometer out of sleep");
|
||||
if (!this->write_byte(BMI160_REGISTER_CMD, (uint8_t) Cmd::ACCL_SET_PMU_MODE | (uint8_t) AcclPmuMode::NORMAL)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
ESP_LOGV(TAG, " Waiting for accelerometer to wake up");
|
||||
// need to wait (max delay in datasheet) because we can't send commands while another is in progress
|
||||
@@ -139,8 +142,7 @@ void BMI160Component::internal_setup_(int stage) {
|
||||
case 1:
|
||||
ESP_LOGV(TAG, " Bringing gyroscope out of sleep");
|
||||
if (!this->write_byte(BMI160_REGISTER_CMD, (uint8_t) Cmd::GYRO_SET_PMU_MODE | (uint8_t) GyroPmuMode::NORMAL)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
ESP_LOGV(TAG, " Waiting for gyroscope to wake up");
|
||||
// wait between 51 & 81ms, doing 100 to be safe
|
||||
@@ -152,15 +154,13 @@ void BMI160Component::internal_setup_(int stage) {
|
||||
uint8_t gyro_config = (uint8_t) GyroBandwidth::OSR4 | (uint8_t) GyroOuputDataRate::HZ_25;
|
||||
ESP_LOGV(TAG, " Output gyro_config: 0b" BYTE_TO_BINARY_PATTERN, BYTE_TO_BINARY(gyro_config));
|
||||
if (!this->write_byte(BMI160_REGISTER_GYRO_CONFIG, gyro_config)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
ESP_LOGV(TAG, " Setting up Gyro Range");
|
||||
uint8_t gyro_range = (uint8_t) GyroRange::RANGE_2000_DPS;
|
||||
ESP_LOGV(TAG, " Output gyro_range: 0b" BYTE_TO_BINARY_PATTERN, BYTE_TO_BINARY(gyro_range));
|
||||
if (!this->write_byte(BMI160_REGISTER_GYRO_RANGE, gyro_range)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
ESP_LOGV(TAG, " Setting up Accel Config");
|
||||
@@ -168,28 +168,24 @@ void BMI160Component::internal_setup_(int stage) {
|
||||
(uint8_t) AcclFilterMode::PERF | (uint8_t) AcclBandwidth::RES_AVG16 | (uint8_t) AccelOutputDataRate::HZ_25;
|
||||
ESP_LOGV(TAG, " Output accel_config: 0b" BYTE_TO_BINARY_PATTERN, BYTE_TO_BINARY(accel_config));
|
||||
if (!this->write_byte(BMI160_REGISTER_ACCEL_CONFIG, accel_config)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
ESP_LOGV(TAG, " Setting up Accel Range");
|
||||
uint8_t accel_range = (uint8_t) AccelRange::RANGE_16G;
|
||||
ESP_LOGV(TAG, " Output accel_range: 0b" BYTE_TO_BINARY_PATTERN, BYTE_TO_BINARY(accel_range));
|
||||
if (!this->write_byte(BMI160_REGISTER_ACCEL_RANGE, accel_range)) {
|
||||
this->mark_failed();
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
this->setup_complete_ = true;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void BMI160Component::setup() { this->internal_setup_(0); }
|
||||
void BMI160Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BMI160:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
LOG_SENSOR(" ", "Acceleration X", this->accel_x_sensor_);
|
||||
LOG_SENSOR(" ", "Acceleration Y", this->accel_y_sensor_);
|
||||
|
||||
@@ -31,6 +31,8 @@ class BMI160Component final : public PollingComponent, public i2c::I2CDevice {
|
||||
sensor::Sensor *gyro_z_sensor_{nullptr};
|
||||
|
||||
void internal_setup_(int stage);
|
||||
/// Run one setup stage; false on an I2C failure.
|
||||
bool setup_stage_(int stage);
|
||||
bool setup_complete_{false};
|
||||
|
||||
/** reads `len` 16-bit little-endian integers from the given i2c register */
|
||||
|
||||
@@ -8,7 +8,6 @@ from esphome.const import (
|
||||
CONF_GYROSCOPE_X,
|
||||
CONF_GYROSCOPE_Y,
|
||||
CONF_GYROSCOPE_Z,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
DEVICE_CLASS_TEMPERATURE,
|
||||
ICON_ACCELERATION_X,
|
||||
@@ -84,9 +83,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_ACCELERATION_X, var.set_accel_x_sensor)
|
||||
|
||||
@@ -78,30 +78,19 @@ bool BMI270Component::load_config_file_() {
|
||||
void BMI270Component::setup() {
|
||||
MotionComponent::setup();
|
||||
// 1. Verify chip ID
|
||||
uint8_t chip_id = 0;
|
||||
if (!this->read_byte(BMI270_REG_CHIP_ID, &chip_id)) {
|
||||
ESP_LOGE(TAG, "Failed to read chip ID – check wiring / address");
|
||||
this->mark_failed();
|
||||
if (!this->check_chip_id(this, BMI270_REG_CHIP_ID, BMI270_CHIP_ID_VALUE))
|
||||
return;
|
||||
}
|
||||
if (chip_id != BMI270_CHIP_ID_VALUE) {
|
||||
ESP_LOGE(TAG, "Wrong chip ID: 0x%02X (expected 0x%02X)", chip_id, BMI270_CHIP_ID_VALUE);
|
||||
this->mark_failed();
|
||||
return;
|
||||
}
|
||||
ESP_LOGD(TAG, "Chip ID: 0x%02X", chip_id);
|
||||
|
||||
// 2. Soft-reset via CMD register (0x7E = 0xB6)
|
||||
if (!this->write_byte(BMI270_REG_CMD, BMI270_CMD_SOFT_RESET)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
delay(20);
|
||||
|
||||
// 4. Upload the configuration blob
|
||||
if (!load_config_file_()) {
|
||||
ESP_LOGE(TAG, "Config file upload failed");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Config file upload failed"));
|
||||
return;
|
||||
}
|
||||
ESP_LOGD(TAG, "Config blob uploaded ✓");
|
||||
@@ -111,11 +100,11 @@ void BMI270Component::setup() {
|
||||
uint8_t acc_conf =
|
||||
(uint8_t) (accel_odr_) | (BMI270_CONF_BWP_NORMAL << BMI270_CONF_BWP_SHIFT) | BMI270_ACC_CONF_PERF_MODE;
|
||||
if (!this->write_byte(BMI270_REG_ACC_CONF, acc_conf)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
if (!this->write_byte(BMI270_REG_ACC_RANGE, (uint8_t) accel_range_)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -124,18 +113,18 @@ void BMI270Component::setup() {
|
||||
uint8_t gyr_conf = (uint8_t) (gyro_odr_) | (BMI270_CONF_BWP_NORMAL << BMI270_CONF_BWP_SHIFT) |
|
||||
BMI270_GYR_CONF_NOISE_PERF | BMI270_GYR_CONF_FILTER_PERF;
|
||||
if (!this->write_byte(BMI270_REG_GYR_CONF, gyr_conf)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
if (!this->write_byte(BMI270_REG_GYR_RANGE, (uint8_t) gyro_range_)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
// 7. Enable accelerometer, gyroscope, and temperature sensor
|
||||
// PWR_CTRL bits: temp_en[3] | gyr_en[2] | acc_en[1]
|
||||
if (!this->write_byte(BMI270_REG_PWR_CTRL, BMI270_PWR_CTRL_IMU)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
delay(5);
|
||||
@@ -143,7 +132,7 @@ void BMI270Component::setup() {
|
||||
// 8. Re-enable advanced power save (optional; keeps current low between reads)
|
||||
// Disabled here for simplicity – leave in performance mode
|
||||
if (!this->write_byte(BMI270_REG_PWR_CONF, BMI270_PWR_CONF_FIFO_SELF_WAKEUP)) { // bit1 = fifo_self_wakeup
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -272,10 +261,8 @@ bool BMI270Component::setup_magnetometer_() {
|
||||
void BMI270Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BMI270 IMU:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, " Communication failed!");
|
||||
if (this->is_failed())
|
||||
return;
|
||||
}
|
||||
|
||||
ESP_LOGCONFIG(TAG, " Accel range : %s",
|
||||
LOG_STR_ARG(AccelRangeStrings::get_log_str(this->accel_range_, AccelRangeStrings::LAST_INDEX)));
|
||||
|
||||
@@ -20,12 +20,9 @@ CONF_AUX_DEVICE = "aux_device"
|
||||
# Enum proxies (must match the C++ enum values exactly)
|
||||
BMI270AuxDevice = bmi270_ns.enum("BMI270AuxDevice")
|
||||
BMI270AccelRange = bmi270_ns.enum("BMI270AccelRange")
|
||||
ACCEL_RANGE_OPTIONS = {
|
||||
"2G": BMI270AccelRange.BMI270_ACCEL_RANGE_2G,
|
||||
"4G": BMI270AccelRange.BMI270_ACCEL_RANGE_4G,
|
||||
"8G": BMI270AccelRange.BMI270_ACCEL_RANGE_8G,
|
||||
"16G": BMI270AccelRange.BMI270_ACCEL_RANGE_16G,
|
||||
}
|
||||
ACCEL_RANGE_OPTIONS = BMI270AccelRange.options(
|
||||
"2G", "4G", "8G", "16G", prefix="BMI270_ACCEL_RANGE_"
|
||||
)
|
||||
|
||||
BMI270GyroRange = bmi270_ns.enum("BMI270GyroRange")
|
||||
GYRO_RANGE_OPTIONS = {
|
||||
|
||||
@@ -24,7 +24,7 @@ void BMP085Component::update() {
|
||||
void BMP085Component::setup() {
|
||||
uint8_t data[22];
|
||||
if (!this->read_bytes(BMP085_REGISTER_AC1_H, data, 22)) {
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -44,9 +44,6 @@ void BMP085Component::setup() {
|
||||
void BMP085Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BMP085:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, "Connection with BMP085 failed!");
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
|
||||
LOG_SENSOR(" ", "Temperature", this->temperature_);
|
||||
|
||||
@@ -2,7 +2,6 @@ import esphome.codegen as cg
|
||||
from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_ID,
|
||||
CONF_PRESSURE,
|
||||
CONF_TEMPERATURE,
|
||||
DEVICE_CLASS_PRESSURE,
|
||||
@@ -44,9 +43,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_TEMPERATURE, var.set_temperature)
|
||||
|
||||
@@ -21,23 +21,14 @@ DOMAIN = "bmp280_base"
|
||||
|
||||
bmp280_ns = cg.esphome_ns.namespace("bmp280_base")
|
||||
BMP280Oversampling = bmp280_ns.enum("BMP280Oversampling")
|
||||
OVERSAMPLING_OPTIONS = {
|
||||
"NONE": BMP280Oversampling.BMP280_OVERSAMPLING_NONE,
|
||||
"1X": BMP280Oversampling.BMP280_OVERSAMPLING_1X,
|
||||
"2X": BMP280Oversampling.BMP280_OVERSAMPLING_2X,
|
||||
"4X": BMP280Oversampling.BMP280_OVERSAMPLING_4X,
|
||||
"8X": BMP280Oversampling.BMP280_OVERSAMPLING_8X,
|
||||
"16X": BMP280Oversampling.BMP280_OVERSAMPLING_16X,
|
||||
}
|
||||
OVERSAMPLING_OPTIONS = BMP280Oversampling.options(
|
||||
"NONE", "1X", "2X", "4X", "8X", "16X", prefix="BMP280_OVERSAMPLING_"
|
||||
)
|
||||
|
||||
BMP280IIRFilter = bmp280_ns.enum("BMP280IIRFilter")
|
||||
IIR_FILTER_OPTIONS = {
|
||||
"OFF": BMP280IIRFilter.BMP280_IIR_FILTER_OFF,
|
||||
"2X": BMP280IIRFilter.BMP280_IIR_FILTER_2X,
|
||||
"4X": BMP280IIRFilter.BMP280_IIR_FILTER_4X,
|
||||
"8X": BMP280IIRFilter.BMP280_IIR_FILTER_8X,
|
||||
"16X": BMP280IIRFilter.BMP280_IIR_FILTER_16X,
|
||||
}
|
||||
IIR_FILTER_OPTIONS = BMP280IIRFilter.options(
|
||||
"OFF", "2X", "4X", "8X", "16X", prefix="BMP280_IIR_FILTER_"
|
||||
)
|
||||
|
||||
CONFIG_SCHEMA_BASE = cv.Schema(
|
||||
{
|
||||
|
||||
@@ -2,8 +2,6 @@
|
||||
#include "esphome/core/hal.h"
|
||||
#include "esphome/core/log.h"
|
||||
|
||||
#define BMP280_ERROR_WRONG_CHIP_ID "Wrong chip ID or no response"
|
||||
|
||||
namespace esphome::bmp280_base {
|
||||
|
||||
ESPHOME_LOG_TAG(TAG, "bmp280.sensor");
|
||||
@@ -65,18 +63,15 @@ void BMP280Component::setup() {
|
||||
// Read the chip id twice, to work around a bug where the first read is 0.
|
||||
// https://community.st.com/t5/stm32-mcus-products/issue-with-reading-bmp280-chip-id-using-spi/td-p/691855
|
||||
if (!this->bmp_read_byte(0xD0, &chip_id)) {
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
if (!this->bmp_read_byte(0xD0, &chip_id)) {
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
if (chip_id != 0x58) {
|
||||
this->error_code_ = WRONG_CHIP_ID;
|
||||
this->mark_failed(LOG_STR(BMP280_ERROR_WRONG_CHIP_ID));
|
||||
this->mark_failed(LOG_STR("Wrong chip ID or no response"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -130,17 +125,6 @@ void BMP280Component::setup() {
|
||||
}
|
||||
void BMP280Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BMP280:");
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case WRONG_CHIP_ID:
|
||||
ESP_LOGE(TAG, BMP280_ERROR_WRONG_CHIP_ID);
|
||||
break;
|
||||
case NONE:
|
||||
default:
|
||||
break;
|
||||
}
|
||||
ESP_LOGCONFIG(TAG, " IIR Filter: %s", iir_filter_to_str(this->iir_filter_));
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
|
||||
|
||||
@@ -85,11 +85,6 @@ class BMP280Component : public PollingComponent {
|
||||
BMP280IIRFilter iir_filter_{BMP280_IIR_FILTER_OFF};
|
||||
sensor::Sensor *temperature_sensor_{nullptr};
|
||||
sensor::Sensor *pressure_sensor_{nullptr};
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
COMMUNICATION_FAILED,
|
||||
WRONG_CHIP_ID,
|
||||
} error_code_{NONE};
|
||||
};
|
||||
|
||||
} // namespace esphome::bmp280_base
|
||||
|
||||
@@ -43,35 +43,27 @@ static const LogString *iir_filter_to_str(IIRFilter filter) {
|
||||
}
|
||||
|
||||
void BMP3XXComponent::setup() {
|
||||
this->error_code_ = NONE;
|
||||
// Call the Device base class "initialise" function
|
||||
if (!reset()) {
|
||||
ESP_LOGE(TAG, "Failed to reset");
|
||||
this->error_code_ = ERROR_SENSOR_RESET;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to reset"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (!read_byte(BMP388_CHIP_ID, &this->chip_id_.reg)) {
|
||||
ESP_LOGE(TAG, "Can't read chip id");
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
ESP_LOGCONFIG(TAG, "Chip %s Id 0x%X", LOG_STR_ARG(chip_type_to_str(this->chip_id_.reg)), this->chip_id_.reg);
|
||||
|
||||
if (chip_id_.reg != BMP388_ID && chip_id_.reg != BMP390_ID) {
|
||||
ESP_LOGE(TAG, "Unknown chip id - is this really a BMP388 or BMP390?");
|
||||
this->error_code_ = ERROR_WRONG_CHIP_ID;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Wrong chip ID - please check if you are really using a BMP 388 or BMP 390"));
|
||||
return;
|
||||
}
|
||||
// set sensor in sleep mode
|
||||
stop_conversion();
|
||||
// Read the calibration parameters into the params structure
|
||||
if (!read_bytes(BMP388_TRIM_PARAMS, (uint8_t *) &compensation_params_, sizeof(compensation_params_))) {
|
||||
ESP_LOGE(TAG, "Can't read calibration data");
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Can't read calibration data"));
|
||||
return;
|
||||
}
|
||||
compensation_float_params_.param_T1 =
|
||||
@@ -92,9 +84,7 @@ void BMP3XXComponent::setup() {
|
||||
|
||||
// Initialise the BMP388 IIR filter register
|
||||
if (!set_iir_filter(this->iir_filter_)) {
|
||||
ESP_LOGE(TAG, "Failed to set IIR filter");
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to set IIR filter"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -113,9 +103,7 @@ void BMP3XXComponent::setup() {
|
||||
}
|
||||
// Initialise the BMP388 oversampling register
|
||||
if (!set_oversampling_register(this->pressure_oversampling_, this->temperature_oversampling_)) {
|
||||
ESP_LOGE(TAG, "Failed to set oversampling register");
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to set oversampling register"));
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -125,23 +113,6 @@ void BMP3XXComponent::dump_config() {
|
||||
"BMP3XX:\n"
|
||||
" Type: %s (0x%X)",
|
||||
LOG_STR_ARG(chip_type_to_str(this->chip_id_.reg)), this->chip_id_.reg);
|
||||
switch (this->error_code_) {
|
||||
case NONE:
|
||||
break;
|
||||
case ERROR_COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case ERROR_WRONG_CHIP_ID:
|
||||
ESP_LOGE(TAG, "Wrong chip ID (reported id: 0x%X) - please check if you are really using a BMP 388 or BMP 390",
|
||||
this->chip_id_.reg);
|
||||
break;
|
||||
case ERROR_SENSOR_RESET:
|
||||
ESP_LOGE(TAG, "Failed to reset");
|
||||
break;
|
||||
default:
|
||||
ESP_LOGE(TAG, "Error code %d", (int) this->error_code_);
|
||||
break;
|
||||
}
|
||||
ESP_LOGCONFIG(TAG, " IIR Filter: %s", LOG_STR_ARG(iir_filter_to_str(this->iir_filter_)));
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
if (this->temperature_sensor_) {
|
||||
@@ -165,8 +136,7 @@ void BMP3XXComponent::update() {
|
||||
meas_time += 2.02f * oversampling_to_time(this->pressure_oversampling_) + 0.392f;
|
||||
meas_time += 0.234f;
|
||||
if (!set_mode(FORCED_MODE)) {
|
||||
ESP_LOGE(TAG, "Failed start forced mode");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed start forced mode"));
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -124,13 +124,6 @@ class BMP3XXComponent : public PollingComponent {
|
||||
OperationMode operation_mode_{FORCED_MODE};
|
||||
sensor::Sensor *temperature_sensor_{nullptr};
|
||||
sensor::Sensor *pressure_sensor_{nullptr};
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
ERROR_COMMUNICATION_FAILED,
|
||||
ERROR_WRONG_CHIP_ID,
|
||||
ERROR_SENSOR_STATUS,
|
||||
ERROR_SENSOR_RESET,
|
||||
} error_code_{NONE};
|
||||
|
||||
struct { // The BMP388 compensation trim parameters (coefficients)
|
||||
uint16_t param_T1;
|
||||
|
||||
@@ -38,29 +38,6 @@ static const LogString *iir_filter_to_str(IIRFilter filter) {
|
||||
void BMP581Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BMP581:");
|
||||
|
||||
switch (this->error_code_) {
|
||||
case NONE:
|
||||
break;
|
||||
case ERROR_COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case ERROR_WRONG_CHIP_ID:
|
||||
ESP_LOGE(TAG, "Unknown chip ID");
|
||||
break;
|
||||
case ERROR_SENSOR_RESET:
|
||||
ESP_LOGE(TAG, "Reset failed");
|
||||
break;
|
||||
case ERROR_SENSOR_STATUS:
|
||||
ESP_LOGE(TAG, "Get status failed");
|
||||
break;
|
||||
case ERROR_PRIME_IIR_FAILED:
|
||||
ESP_LOGE(TAG, "IIR Filter failed to prime with initial measurement");
|
||||
break;
|
||||
default:
|
||||
ESP_LOGE(TAG, "Error %d", (int) this->error_code_);
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
|
||||
ESP_LOGCONFIG(TAG, " Measurement conversion time: %ums", this->conversion_time_);
|
||||
@@ -96,17 +73,13 @@ void BMP581Component::setup() {
|
||||
* 6) Configure and prime IIR Filter(s), if enabled
|
||||
*/
|
||||
|
||||
this->error_code_ = NONE;
|
||||
////////////////////
|
||||
// 1) Soft reboot //
|
||||
////////////////////
|
||||
|
||||
// Power-On-Reboot bit is asserted if sensor successfully reset
|
||||
if (!this->reset_()) {
|
||||
ESP_LOGE(TAG, "Reset failed");
|
||||
|
||||
this->error_code_ = ERROR_SENSOR_RESET;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Reset failed"));
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -119,20 +92,14 @@ void BMP581Component::setup() {
|
||||
|
||||
// read chip id from sensor
|
||||
if (!this->bmp_read_byte(BMP581_CHIP_ID, &chip_id)) {
|
||||
ESP_LOGE(TAG, "Read chip ID failed");
|
||||
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Read chip ID failed"));
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// verify id
|
||||
if (chip_id != BMP581_ASIC_ID && chip_id != BMP585_ASIC_ID) {
|
||||
ESP_LOGE(TAG, "Unknown chip ID");
|
||||
|
||||
this->error_code_ = ERROR_WRONG_CHIP_ID;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Unknown chip ID"));
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -142,30 +109,21 @@ void BMP581Component::setup() {
|
||||
////////////////////////////////////////////////////
|
||||
|
||||
if (!this->bmp_read_byte(BMP581_STATUS, &this->status_.reg)) {
|
||||
ESP_LOGE(TAG, "Failed to read status register");
|
||||
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to read status register"));
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// verify status_nvm_rdy bit (it is asserted if boot was successful)
|
||||
if (!(this->status_.bit.status_nvm_rdy)) {
|
||||
ESP_LOGE(TAG, "NVM not ready");
|
||||
|
||||
this->error_code_ = ERROR_SENSOR_STATUS;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("NVM not ready"));
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// verify status_nvm_err bit (it is asserted if an error is detected)
|
||||
if (this->status_.bit.status_nvm_err) {
|
||||
ESP_LOGE(TAG, "NVM error detected");
|
||||
|
||||
this->error_code_ = ERROR_SENSOR_STATUS;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("NVM error detected"));
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -176,10 +134,7 @@ void BMP581Component::setup() {
|
||||
|
||||
// enable the data ready interrupt source
|
||||
if (!this->write_interrupt_source_settings_(true)) {
|
||||
ESP_LOGE(TAG, "Failed to write interrupt source register");
|
||||
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to write interrupt source register"));
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -198,10 +153,7 @@ void BMP581Component::setup() {
|
||||
|
||||
// write oversampling settings
|
||||
if (!this->write_oversampling_settings_(this->temperature_oversampling_, this->pressure_oversampling_)) {
|
||||
ESP_LOGE(TAG, "Failed to write oversampling register");
|
||||
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to write oversampling register"));
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -218,19 +170,13 @@ void BMP581Component::setup() {
|
||||
|
||||
if ((this->iir_temperature_level_ != IIR_FILTER_OFF) || (this->iir_pressure_level_ != IIR_FILTER_OFF)) {
|
||||
if (!this->write_iir_settings_(this->iir_temperature_level_, this->iir_pressure_level_)) {
|
||||
ESP_LOGE(TAG, "Failed to write IIR configuration registers");
|
||||
|
||||
this->error_code_ = ERROR_COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to write IIR configuration registers"));
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this->prime_iir_filter_()) {
|
||||
ESP_LOGE(TAG, "Failed to prime the IIR filter with an initial measurement");
|
||||
|
||||
this->error_code_ = ERROR_PRIME_IIR_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Failed to prime the IIR filter with an initial measurement"));
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -133,15 +133,6 @@ class BMP581Component : public PollingComponent {
|
||||
// Sets the power mode on the BMP581 by writing to the ODR register
|
||||
bool write_power_mode_(OperationMode mode);
|
||||
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
ERROR_COMMUNICATION_FAILED,
|
||||
ERROR_WRONG_CHIP_ID,
|
||||
ERROR_SENSOR_STATUS,
|
||||
ERROR_SENSOR_RESET,
|
||||
ERROR_PRIME_IIR_FAILED
|
||||
} error_code_{NONE};
|
||||
|
||||
// BMP581's interrupt source register (address 0x15) to configure which interrupts are enabled (page 54 of datasheet)
|
||||
union {
|
||||
struct {
|
||||
|
||||
@@ -338,9 +338,7 @@ CONFIGURE_ACTION_SCHEMA = automation.maybe_simple_id(
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
if config[CONF_CONFIGURE_ON_BOOT]:
|
||||
cg.add(var.set_setup_registers(cg.ArrayInitializer(*pack_registers(config))))
|
||||
|
||||
@@ -79,19 +79,9 @@ bool BQ25186Component::apply_config(const BQ25186ConfigRegisters ®s) {
|
||||
}
|
||||
|
||||
void BQ25186Component::setup() {
|
||||
uint8_t mask_id;
|
||||
if (!this->read_byte(BQ25186_REG_MASK_ID, &mask_id)) {
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
// Another charger at this address could lay its registers out differently, so do not write into it
|
||||
const uint8_t device_id = mask_id & 0x0F;
|
||||
if (device_id != 0x01) {
|
||||
ESP_LOGE(TAG, "Unexpected device id 0x%X (expected 0x1)", device_id);
|
||||
this->mark_failed(LOG_STR("Not a BQ25186"));
|
||||
if (!this->check_chip_id(this, BQ25186_REG_MASK_ID, 0x01, 0x0F))
|
||||
return;
|
||||
}
|
||||
|
||||
// A failed write only sets the warning status: the chip has identified itself, so a later
|
||||
// apply_configuration may retry
|
||||
|
||||
@@ -48,7 +48,7 @@ void BQ27220Component::setup() {
|
||||
}
|
||||
if (device_number != DEVICE_NUMBER) {
|
||||
ESP_LOGE(TAG, "Unexpected device number 0x%04X (expected 0x%04X)", device_number, DEVICE_NUMBER);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Unexpected device number"));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -76,9 +76,6 @@ void BQ27220Component::update() {
|
||||
void BQ27220Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "BQ27220 Battery Fuel Gauge:");
|
||||
LOG_I2C_DEVICE(this);
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
LOG_UPDATE_INTERVAL(this);
|
||||
LOG_SENSOR(" ", "Voltage", this->voltage_sensor_);
|
||||
LOG_SENSOR(" ", "Current", this->current_sensor_);
|
||||
|
||||
@@ -5,7 +5,6 @@ import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_BATTERY_LEVEL,
|
||||
CONF_CURRENT,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
CONF_VOLTAGE,
|
||||
DEVICE_CLASS_BATTERY,
|
||||
@@ -108,9 +107,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_VOLTAGE, var.set_voltage_sensor)
|
||||
|
||||
@@ -4,7 +4,6 @@ from esphome.components import i2c, sensor
|
||||
import esphome.config_validation as cv
|
||||
from esphome.const import (
|
||||
CONF_ADDRESS,
|
||||
CONF_ID,
|
||||
DEVICE_CLASS_TEMPERATURE,
|
||||
DEVICE_CLASS_VOLTAGE,
|
||||
STATE_CLASS_MEASUREMENT,
|
||||
@@ -75,9 +74,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
cg.add(var.set_crc_mode(config[CONF_CRC_ENABLED]))
|
||||
cg.add(var.set_reg_disable(config[CONF_REG_DISABLED]))
|
||||
|
||||
@@ -15,6 +15,11 @@ from esphome.const import (
|
||||
DEVICE_CLASS_IDENTIFY,
|
||||
DEVICE_CLASS_RESTART,
|
||||
DEVICE_CLASS_UPDATE,
|
||||
ENTITY_CATEGORY_CONFIG,
|
||||
ENTITY_CATEGORY_DIAGNOSTIC,
|
||||
ICON_DATABASE,
|
||||
ICON_RESTART,
|
||||
ICON_RESTART_ALERT,
|
||||
)
|
||||
from esphome.core import CORE, ID, CoroPriority, coroutine_with_priority
|
||||
from esphome.core.entity_helpers import (
|
||||
@@ -83,6 +88,40 @@ def button_schema(
|
||||
return _BUTTON_SCHEMA.extend(schema)
|
||||
|
||||
|
||||
def factory_reset_button_schema(class_: MockObjClass) -> cv.Schema:
|
||||
"""Schema for a button that resets the connected module to factory settings.
|
||||
|
||||
For a sensor or radio module's own reset, not the ESPHome node.
|
||||
"""
|
||||
return button_schema(
|
||||
class_,
|
||||
device_class=DEVICE_CLASS_RESTART,
|
||||
entity_category=ENTITY_CATEGORY_CONFIG,
|
||||
icon=ICON_RESTART_ALERT,
|
||||
)
|
||||
|
||||
|
||||
def restart_button_schema(class_: MockObjClass) -> cv.Schema:
|
||||
"""Schema for a button that restarts the connected module.
|
||||
|
||||
For a sensor or radio module's own restart, not the ESPHome node; the core
|
||||
restart button uses the config category instead of diagnostic.
|
||||
"""
|
||||
return button_schema(
|
||||
class_,
|
||||
device_class=DEVICE_CLASS_RESTART,
|
||||
entity_category=ENTITY_CATEGORY_DIAGNOSTIC,
|
||||
icon=ICON_RESTART,
|
||||
)
|
||||
|
||||
|
||||
def query_button_schema(class_: MockObjClass) -> cv.Schema:
|
||||
"""Schema for a button that reads the settings back from the connected module."""
|
||||
return button_schema(
|
||||
class_, entity_category=ENTITY_CATEGORY_DIAGNOSTIC, icon=ICON_DATABASE
|
||||
)
|
||||
|
||||
|
||||
_CALLBACK_AUTOMATIONS = (
|
||||
automation.CallbackAutomation(CONF_ON_PRESS, "add_on_press_callback"),
|
||||
)
|
||||
|
||||
@@ -11,8 +11,9 @@ namespace esphome::camera {
|
||||
* IDLE: Camera requests to send an image to the API.
|
||||
* API_REQUESTER: API requests a new image.
|
||||
* WEB_REQUESTER: ESP32 web server request an image. Ignored by API.
|
||||
* RTSP_REQUESTER: RTSP server requests a stream of images. Ignored by API and web server.
|
||||
*/
|
||||
enum CameraRequester : uint8_t { IDLE, API_REQUESTER, WEB_REQUESTER };
|
||||
enum CameraRequester : uint8_t { IDLE, API_REQUESTER, WEB_REQUESTER, RTSP_REQUESTER };
|
||||
|
||||
/// Enumeration of different pixel formats.
|
||||
enum PixelFormat : uint8_t {
|
||||
|
||||
@@ -56,29 +56,30 @@ CanbusTrigger = canbus_ns.class_(
|
||||
)
|
||||
CanSpeed = canbus_ns.enum("CAN_SPEED")
|
||||
|
||||
CAN_SPEEDS = {
|
||||
"1KBPS": CanSpeed.CAN_1KBPS,
|
||||
"5KBPS": CanSpeed.CAN_5KBPS,
|
||||
"10KBPS": CanSpeed.CAN_10KBPS,
|
||||
"12K5BPS": CanSpeed.CAN_12K5BPS,
|
||||
"16KBPS": CanSpeed.CAN_16KBPS,
|
||||
"20KBPS": CanSpeed.CAN_20KBPS,
|
||||
"25KBPS": CanSpeed.CAN_25KBPS,
|
||||
"31K25BPS": CanSpeed.CAN_31K25BPS,
|
||||
"33KBPS": CanSpeed.CAN_33KBPS,
|
||||
"40KBPS": CanSpeed.CAN_40KBPS,
|
||||
"50KBPS": CanSpeed.CAN_50KBPS,
|
||||
"80KBPS": CanSpeed.CAN_80KBPS,
|
||||
"83K3BPS": CanSpeed.CAN_83K3BPS,
|
||||
"95KBPS": CanSpeed.CAN_95KBPS,
|
||||
"100KBPS": CanSpeed.CAN_100KBPS,
|
||||
"125KBPS": CanSpeed.CAN_125KBPS,
|
||||
"200KBPS": CanSpeed.CAN_200KBPS,
|
||||
"250KBPS": CanSpeed.CAN_250KBPS,
|
||||
"500KBPS": CanSpeed.CAN_500KBPS,
|
||||
"800KBPS": CanSpeed.CAN_800KBPS,
|
||||
"1000KBPS": CanSpeed.CAN_1000KBPS,
|
||||
}
|
||||
CAN_SPEEDS = CanSpeed.options(
|
||||
"1KBPS",
|
||||
"5KBPS",
|
||||
"10KBPS",
|
||||
"12K5BPS",
|
||||
"16KBPS",
|
||||
"20KBPS",
|
||||
"25KBPS",
|
||||
"31K25BPS",
|
||||
"33KBPS",
|
||||
"40KBPS",
|
||||
"50KBPS",
|
||||
"80KBPS",
|
||||
"83K3BPS",
|
||||
"95KBPS",
|
||||
"100KBPS",
|
||||
"125KBPS",
|
||||
"200KBPS",
|
||||
"250KBPS",
|
||||
"500KBPS",
|
||||
"800KBPS",
|
||||
"1000KBPS",
|
||||
prefix="CAN_",
|
||||
)
|
||||
|
||||
|
||||
def get_rate(value: str) -> int:
|
||||
|
||||
@@ -37,8 +37,7 @@ void CAP1188Component::finish_setup_() {
|
||||
this->read_byte(CAP1188_REVISION, &this->cap1188_revision_);
|
||||
|
||||
if ((this->cap1188_product_id_ != 0x50) || (this->cap1188_manufacture_id_ != 0x5D)) {
|
||||
this->error_code_ = COMMUNICATION_FAILED;
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("Product ID or Manufacture ID of the connected device does not match a known CAP1188"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -70,15 +69,6 @@ void CAP1188Component::dump_config() {
|
||||
this->cap1188_product_id_, this->cap1188_manufacture_id_, this->cap1188_revision_);
|
||||
LOG_I2C_DEVICE(this);
|
||||
LOG_PIN(" Reset Pin: ", this->reset_pin_);
|
||||
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGE(TAG, "Product ID or Manufacture ID of the connected device does not match a known CAP1188.");
|
||||
break;
|
||||
case NONE:
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void CAP1188Component::loop() {
|
||||
|
||||
@@ -59,11 +59,6 @@ class CAP1188Component final : public Component, public i2c::I2CDevice {
|
||||
uint8_t cap1188_product_id_{0};
|
||||
uint8_t cap1188_manufacture_id_{0};
|
||||
uint8_t cap1188_revision_{0};
|
||||
|
||||
enum ErrorCode {
|
||||
NONE = 0,
|
||||
COMMUNICATION_FAILED,
|
||||
} error_code_{NONE};
|
||||
};
|
||||
|
||||
} // namespace esphome::cap1188
|
||||
|
||||
@@ -67,41 +67,30 @@ CONF_GDO0_PIN = "gdo0_pin"
|
||||
|
||||
# Enums
|
||||
SyncMode = ns.enum("SyncMode", True)
|
||||
SYNC_MODE = {
|
||||
"None": SyncMode.SYNC_MODE_NONE,
|
||||
"15/16": SyncMode.SYNC_MODE_15_16,
|
||||
"16/16": SyncMode.SYNC_MODE_16_16,
|
||||
"30/32": SyncMode.SYNC_MODE_30_32,
|
||||
}
|
||||
SYNC_MODE = SyncMode.options("None", "15/16", "16/16", "30/32", prefix="SYNC_MODE_")
|
||||
|
||||
Modulation = ns.enum("Modulation", True)
|
||||
MODULATION = {
|
||||
"2-FSK": Modulation.MODULATION_2_FSK,
|
||||
"GFSK": Modulation.MODULATION_GFSK,
|
||||
"ASK/OOK": Modulation.MODULATION_ASK_OOK,
|
||||
"4-FSK": Modulation.MODULATION_4_FSK,
|
||||
"MSK": Modulation.MODULATION_MSK,
|
||||
}
|
||||
MODULATION = Modulation.options(
|
||||
"2-FSK", "GFSK", "ASK/OOK", "4-FSK", "MSK", prefix="MODULATION_"
|
||||
)
|
||||
|
||||
RxAttenuation = ns.enum("RxAttenuation", True)
|
||||
RX_ATTENUATION = {
|
||||
"0dB": RxAttenuation.RX_ATTENUATION_0DB,
|
||||
"6dB": RxAttenuation.RX_ATTENUATION_6DB,
|
||||
"12dB": RxAttenuation.RX_ATTENUATION_12DB,
|
||||
"18dB": RxAttenuation.RX_ATTENUATION_18DB,
|
||||
}
|
||||
RX_ATTENUATION = RxAttenuation.options(
|
||||
"0dB", "6dB", "12dB", "18dB", prefix="RX_ATTENUATION_"
|
||||
)
|
||||
|
||||
MagnTarget = ns.enum("MagnTarget", True)
|
||||
MAGN_TARGET = {
|
||||
"24dB": MagnTarget.MAGN_TARGET_24DB,
|
||||
"27dB": MagnTarget.MAGN_TARGET_27DB,
|
||||
"30dB": MagnTarget.MAGN_TARGET_30DB,
|
||||
"33dB": MagnTarget.MAGN_TARGET_33DB,
|
||||
"36dB": MagnTarget.MAGN_TARGET_36DB,
|
||||
"38dB": MagnTarget.MAGN_TARGET_38DB,
|
||||
"40dB": MagnTarget.MAGN_TARGET_40DB,
|
||||
"42dB": MagnTarget.MAGN_TARGET_42DB,
|
||||
}
|
||||
MAGN_TARGET = MagnTarget.options(
|
||||
"24dB",
|
||||
"27dB",
|
||||
"30dB",
|
||||
"33dB",
|
||||
"36dB",
|
||||
"38dB",
|
||||
"40dB",
|
||||
"42dB",
|
||||
prefix="MAGN_TARGET_",
|
||||
)
|
||||
|
||||
MaxLnaGain = ns.enum("MaxLnaGain", True)
|
||||
MAX_LNA_GAIN = {
|
||||
@@ -140,20 +129,14 @@ FILTER_LENGTH_FSK_MSK = {
|
||||
}
|
||||
|
||||
FilterLengthAskOok = ns.enum("FilterLengthAskOok", True)
|
||||
FILTER_LENGTH_ASK_OOK = {
|
||||
"4dB": FilterLengthAskOok.FILTER_LENGTH_4DB,
|
||||
"8dB": FilterLengthAskOok.FILTER_LENGTH_8DB,
|
||||
"12dB": FilterLengthAskOok.FILTER_LENGTH_12DB,
|
||||
"16dB": FilterLengthAskOok.FILTER_LENGTH_16DB,
|
||||
}
|
||||
FILTER_LENGTH_ASK_OOK = FilterLengthAskOok.options(
|
||||
"4dB", "8dB", "12dB", "16dB", prefix="FILTER_LENGTH_"
|
||||
)
|
||||
|
||||
Freeze = ns.enum("Freeze", True)
|
||||
FREEZE = {
|
||||
"Default": Freeze.FREEZE_DEFAULT,
|
||||
"On Sync": Freeze.FREEZE_ON_SYNC,
|
||||
"Analog Only": Freeze.FREEZE_ANALOG_ONLY,
|
||||
"Analog And Digital": Freeze.FREEZE_ANALOG_AND_DIGITAL,
|
||||
}
|
||||
FREEZE = Freeze.options(
|
||||
"Default", "On Sync", "Analog Only", "Analog And Digital", prefix="FREEZE_"
|
||||
)
|
||||
|
||||
WaitTime = ns.enum("WaitTime", True)
|
||||
WAIT_TIME = {
|
||||
@@ -164,34 +147,16 @@ WAIT_TIME = {
|
||||
}
|
||||
|
||||
HystLevel = ns.enum("HystLevel", True)
|
||||
HYST_LEVEL = {
|
||||
"None": HystLevel.HYST_LEVEL_NONE,
|
||||
"Low": HystLevel.HYST_LEVEL_LOW,
|
||||
"Medium": HystLevel.HYST_LEVEL_MEDIUM,
|
||||
"High": HystLevel.HYST_LEVEL_HIGH,
|
||||
}
|
||||
HYST_LEVEL = HystLevel.options("None", "Low", "Medium", "High", prefix="HYST_LEVEL_")
|
||||
|
||||
FocLimit = ns.enum("FocLimit", True)
|
||||
FOC_LIMIT = {
|
||||
"Disabled": FocLimit.FOC_LIMIT_DISABLED,
|
||||
"BW/8": FocLimit.FOC_LIMIT_BW_8,
|
||||
"BW/4": FocLimit.FOC_LIMIT_BW_4,
|
||||
"BW/2": FocLimit.FOC_LIMIT_BW_2,
|
||||
}
|
||||
FOC_LIMIT = FocLimit.options("Disabled", "BW/8", "BW/4", "BW/2", prefix="FOC_LIMIT_")
|
||||
|
||||
FocPreK = ns.enum("FocPreK", True)
|
||||
FOC_PRE_K = {
|
||||
"K": FocPreK.FOC_PRE_K_K,
|
||||
"2K": FocPreK.FOC_PRE_K_2K,
|
||||
"3K": FocPreK.FOC_PRE_K_3K,
|
||||
"4K": FocPreK.FOC_PRE_K_4K,
|
||||
}
|
||||
FOC_PRE_K = FocPreK.options("K", "2K", "3K", "4K", prefix="FOC_PRE_K_")
|
||||
|
||||
FocPostK = ns.enum("FocPostK", True)
|
||||
FOC_POST_K = {
|
||||
"Same": FocPostK.FOC_POST_K_SAME,
|
||||
"K/2": FocPostK.FOC_POST_K_K_2,
|
||||
}
|
||||
FOC_POST_K = FocPostK.options("Same", "K/2", prefix="FOC_POST_K_")
|
||||
|
||||
BsLimit = ns.enum("BsLimit", True)
|
||||
BS_LIMIT = {
|
||||
@@ -202,32 +167,16 @@ BS_LIMIT = {
|
||||
}
|
||||
|
||||
BsPreKi = ns.enum("BsPreKi", True)
|
||||
BS_PRE_KI = {
|
||||
"KI": BsPreKi.BS_PRE_KI_KI,
|
||||
"2KI": BsPreKi.BS_PRE_KI_2KI,
|
||||
"3KI": BsPreKi.BS_PRE_KI_3KI,
|
||||
"4KI": BsPreKi.BS_PRE_KI_4KI,
|
||||
}
|
||||
BS_PRE_KI = BsPreKi.options("KI", "2KI", "3KI", "4KI", prefix="BS_PRE_KI_")
|
||||
|
||||
BsPreKp = ns.enum("BsPreKp", True)
|
||||
BS_PRE_KP = {
|
||||
"KP": BsPreKp.BS_PRE_KP_KP,
|
||||
"2KP": BsPreKp.BS_PRE_KP_2KP,
|
||||
"3KP": BsPreKp.BS_PRE_KP_3KP,
|
||||
"4KP": BsPreKp.BS_PRE_KP_4KP,
|
||||
}
|
||||
BS_PRE_KP = BsPreKp.options("KP", "2KP", "3KP", "4KP", prefix="BS_PRE_KP_")
|
||||
|
||||
BsPostKi = ns.enum("BsPostKi", True)
|
||||
BS_POST_KI = {
|
||||
"Same": BsPostKi.BS_POST_KI_SAME,
|
||||
"KI/2": BsPostKi.BS_POST_KI_KI_2,
|
||||
}
|
||||
BS_POST_KI = BsPostKi.options("Same", "KI/2", prefix="BS_POST_KI_")
|
||||
|
||||
BsPostKp = ns.enum("BsPostKp", True)
|
||||
BS_POST_KP = {
|
||||
"Same": BsPostKp.BS_POST_KP_SAME,
|
||||
"KP": BsPostKp.BS_POST_KP_KP,
|
||||
}
|
||||
BS_POST_KP = BsPostKp.options("Same", "KP", prefix="BS_POST_KP_")
|
||||
|
||||
# Optional settings to generate setter calls for
|
||||
CONFIG_MAP = {
|
||||
|
||||
@@ -10,29 +10,28 @@ ESPHOME_LOG_TAG(TAG, "ccs811");
|
||||
// based on
|
||||
// - https://cdn.sparkfun.com/datasheets/BreakoutBoards/CCS811_Programming_Guide.pdf
|
||||
|
||||
#define CHECK_TRUE(f, error_code) \
|
||||
#define CHECK_TRUE(f, message) \
|
||||
if (!(f)) { \
|
||||
this->mark_failed(); \
|
||||
this->error_code_ = (error_code); \
|
||||
this->mark_failed(LOG_STR(message)); \
|
||||
return; \
|
||||
}
|
||||
|
||||
#define CHECKED_IO(f) CHECK_TRUE(f, COMMUNICATION_FAILED)
|
||||
#define CHECKED_IO(f) CHECK_TRUE(f, ESP_LOG_MSG_COMM_FAIL)
|
||||
|
||||
void CCS811Component::setup() {
|
||||
// page 9 programming guide - hwid is always 0x81
|
||||
uint8_t hw_id;
|
||||
CHECKED_IO(this->read_byte(0x20, &hw_id))
|
||||
CHECK_TRUE(hw_id == 0x81, INVALID_ID)
|
||||
CHECK_TRUE(hw_id == 0x81, "Sensor reported an invalid ID. Is this a CCS811?")
|
||||
|
||||
// software reset, page 3 - allowed to fail
|
||||
this->write_bytes(0xFF, {0x11, 0xE5, 0x72, 0x8A});
|
||||
delay(5);
|
||||
|
||||
// page 10, APP_START
|
||||
CHECK_TRUE(!this->status_has_error_(), SENSOR_REPORTED_ERROR)
|
||||
CHECK_TRUE(this->status_app_is_valid_(), APP_INVALID)
|
||||
CHECK_TRUE(this->write_bytes(0xF4, {}), APP_START_FAILED)
|
||||
CHECK_TRUE(!this->status_has_error_(), "Sensor reported internal error")
|
||||
CHECK_TRUE(this->status_app_is_valid_(), "Sensor reported invalid APP installed")
|
||||
CHECK_TRUE(this->write_bytes(0xF4, {}), "Sensor reported APP start failed")
|
||||
// App setup, wait for it to load
|
||||
delay(1);
|
||||
|
||||
@@ -160,29 +159,6 @@ void CCS811Component::dump_config() {
|
||||
} else {
|
||||
ESP_LOGCONFIG(TAG, " Baseline: NOT SET");
|
||||
}
|
||||
if (this->is_failed()) {
|
||||
switch (this->error_code_) {
|
||||
case COMMUNICATION_FAILED:
|
||||
ESP_LOGW(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
break;
|
||||
case INVALID_ID:
|
||||
ESP_LOGW(TAG, "Sensor reported an invalid ID. Is this a CCS811?");
|
||||
break;
|
||||
case SENSOR_REPORTED_ERROR:
|
||||
ESP_LOGW(TAG, "Sensor reported internal error");
|
||||
break;
|
||||
case APP_INVALID:
|
||||
ESP_LOGW(TAG, "Sensor reported invalid APP installed.");
|
||||
break;
|
||||
case APP_START_FAILED:
|
||||
ESP_LOGW(TAG, "Sensor reported APP start failed.");
|
||||
break;
|
||||
case UNKNOWN:
|
||||
default:
|
||||
ESP_LOGW(TAG, "Unknown setup error!");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace esphome::ccs811
|
||||
|
||||
@@ -31,15 +31,6 @@ class CCS811Component final : public PollingComponent, public i2c::I2CDevice {
|
||||
bool status_has_data_() { return this->read_status_().value_or(0) & (1 << 3); }
|
||||
void send_env_data_();
|
||||
|
||||
enum ErrorCode {
|
||||
UNKNOWN,
|
||||
COMMUNICATION_FAILED,
|
||||
INVALID_ID,
|
||||
SENSOR_REPORTED_ERROR,
|
||||
APP_INVALID,
|
||||
APP_START_FAILED,
|
||||
} error_code_{UNKNOWN};
|
||||
|
||||
sensor::Sensor *co2_{nullptr};
|
||||
sensor::Sensor *tvoc_{nullptr};
|
||||
text_sensor::TextSensor *version_{nullptr};
|
||||
|
||||
@@ -5,7 +5,6 @@ from esphome.const import (
|
||||
CONF_BASELINE,
|
||||
CONF_ECO2,
|
||||
CONF_HUMIDITY,
|
||||
CONF_ID,
|
||||
CONF_TEMPERATURE,
|
||||
CONF_TVOC,
|
||||
CONF_VERSION,
|
||||
@@ -61,9 +60,7 @@ CONFIG_SCHEMA = (
|
||||
|
||||
|
||||
async def to_code(config: ConfigType) -> None:
|
||||
var = cg.new_Pvariable(config[CONF_ID])
|
||||
await cg.register_component(var, config)
|
||||
await i2c.register_i2c_device(var, config)
|
||||
var = await i2c.new_i2c_component(config)
|
||||
|
||||
sensors = sensor.sub_sensors(config)
|
||||
await sensors(CONF_ECO2, var.set_co2)
|
||||
|
||||
@@ -18,7 +18,7 @@ void CH422GComponent::setup() {
|
||||
// Set mode and check for errors
|
||||
if (!this->set_mode_(this->mode_value_) || !this->read_inputs_()) {
|
||||
ESP_LOGE(TAG, "CH422G not detected at 0x%02X", this->address_);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -34,9 +34,6 @@ void CH422GComponent::loop() {
|
||||
void CH422GComponent::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "CH422G:");
|
||||
LOG_I2C_DEVICE(this)
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
void CH422GComponent::pin_mode(uint8_t pin, gpio::Flags flags) {
|
||||
|
||||
@@ -24,8 +24,7 @@ void CH423Component::setup() {
|
||||
success = this->read_inputs_();
|
||||
}
|
||||
if (!success) {
|
||||
ESP_LOGE(TAG, "CH423 not detected");
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR("CH423 not detected"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -38,12 +37,7 @@ void CH423Component::loop() {
|
||||
this->pin_read_flags_ = 0x00;
|
||||
}
|
||||
|
||||
void CH423Component::dump_config() {
|
||||
ESP_LOGCONFIG(TAG, "CH423:");
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
void CH423Component::dump_config() { ESP_LOGCONFIG(TAG, "CH423:"); }
|
||||
|
||||
void CH423Component::pin_mode(uint8_t pin, gpio::Flags flags) {
|
||||
if (pin < 8) {
|
||||
|
||||
@@ -69,67 +69,68 @@ ClimateCall = climate_ns.class_("ClimateCall")
|
||||
ClimateTraits = climate_ns.class_("ClimateTraits")
|
||||
|
||||
ClimateMode = climate_ns.enum("ClimateMode")
|
||||
CLIMATE_MODES = {
|
||||
"OFF": ClimateMode.CLIMATE_MODE_OFF,
|
||||
"HEAT_COOL": ClimateMode.CLIMATE_MODE_HEAT_COOL,
|
||||
"COOL": ClimateMode.CLIMATE_MODE_COOL,
|
||||
"HEAT": ClimateMode.CLIMATE_MODE_HEAT,
|
||||
"DRY": ClimateMode.CLIMATE_MODE_DRY,
|
||||
"FAN_ONLY": ClimateMode.CLIMATE_MODE_FAN_ONLY,
|
||||
"AUTO": ClimateMode.CLIMATE_MODE_AUTO,
|
||||
}
|
||||
CLIMATE_MODES = ClimateMode.options(
|
||||
"OFF",
|
||||
"HEAT_COOL",
|
||||
"COOL",
|
||||
"HEAT",
|
||||
"DRY",
|
||||
"FAN_ONLY",
|
||||
"AUTO",
|
||||
prefix="CLIMATE_MODE_",
|
||||
)
|
||||
validate_climate_mode = cv.enum(CLIMATE_MODES, upper=True)
|
||||
|
||||
ClimateFanMode = climate_ns.enum("ClimateFanMode")
|
||||
CLIMATE_FAN_MODES = {
|
||||
"ON": ClimateFanMode.CLIMATE_FAN_ON,
|
||||
"OFF": ClimateFanMode.CLIMATE_FAN_OFF,
|
||||
"AUTO": ClimateFanMode.CLIMATE_FAN_AUTO,
|
||||
"LOW": ClimateFanMode.CLIMATE_FAN_LOW,
|
||||
"MEDIUM": ClimateFanMode.CLIMATE_FAN_MEDIUM,
|
||||
"HIGH": ClimateFanMode.CLIMATE_FAN_HIGH,
|
||||
"MIDDLE": ClimateFanMode.CLIMATE_FAN_MIDDLE,
|
||||
"FOCUS": ClimateFanMode.CLIMATE_FAN_FOCUS,
|
||||
"DIFFUSE": ClimateFanMode.CLIMATE_FAN_DIFFUSE,
|
||||
"QUIET": ClimateFanMode.CLIMATE_FAN_QUIET,
|
||||
}
|
||||
CLIMATE_FAN_MODES = ClimateFanMode.options(
|
||||
"ON",
|
||||
"OFF",
|
||||
"AUTO",
|
||||
"LOW",
|
||||
"MEDIUM",
|
||||
"HIGH",
|
||||
"MIDDLE",
|
||||
"FOCUS",
|
||||
"DIFFUSE",
|
||||
"QUIET",
|
||||
prefix="CLIMATE_FAN_",
|
||||
)
|
||||
|
||||
validate_climate_fan_mode = cv.enum(CLIMATE_FAN_MODES, upper=True)
|
||||
|
||||
ClimatePreset = climate_ns.enum("ClimatePreset")
|
||||
CLIMATE_PRESETS = {
|
||||
"NONE": ClimatePreset.CLIMATE_PRESET_NONE,
|
||||
"ECO": ClimatePreset.CLIMATE_PRESET_ECO,
|
||||
"AWAY": ClimatePreset.CLIMATE_PRESET_AWAY,
|
||||
"BOOST": ClimatePreset.CLIMATE_PRESET_BOOST,
|
||||
"COMFORT": ClimatePreset.CLIMATE_PRESET_COMFORT,
|
||||
"HOME": ClimatePreset.CLIMATE_PRESET_HOME,
|
||||
"SLEEP": ClimatePreset.CLIMATE_PRESET_SLEEP,
|
||||
"ACTIVITY": ClimatePreset.CLIMATE_PRESET_ACTIVITY,
|
||||
}
|
||||
CLIMATE_PRESETS = ClimatePreset.options(
|
||||
"NONE",
|
||||
"ECO",
|
||||
"AWAY",
|
||||
"BOOST",
|
||||
"COMFORT",
|
||||
"HOME",
|
||||
"SLEEP",
|
||||
"ACTIVITY",
|
||||
prefix="CLIMATE_PRESET_",
|
||||
)
|
||||
|
||||
validate_climate_preset = cv.enum(CLIMATE_PRESETS, upper=True)
|
||||
|
||||
ClimateSwingMode = climate_ns.enum("ClimateSwingMode")
|
||||
CLIMATE_SWING_MODES = {
|
||||
"OFF": ClimateSwingMode.CLIMATE_SWING_OFF,
|
||||
"BOTH": ClimateSwingMode.CLIMATE_SWING_BOTH,
|
||||
"VERTICAL": ClimateSwingMode.CLIMATE_SWING_VERTICAL,
|
||||
"HORIZONTAL": ClimateSwingMode.CLIMATE_SWING_HORIZONTAL,
|
||||
}
|
||||
CLIMATE_SWING_MODES = ClimateSwingMode.options(
|
||||
"OFF", "BOTH", "VERTICAL", "HORIZONTAL", prefix="CLIMATE_SWING_"
|
||||
)
|
||||
|
||||
validate_climate_swing_mode = cv.enum(CLIMATE_SWING_MODES, upper=True)
|
||||
|
||||
ClimateAction = climate_ns.enum("ClimateAction")
|
||||
CLIMATE_ACTIONS = {
|
||||
"OFF": ClimateAction.CLIMATE_ACTION_OFF,
|
||||
"COOLING": ClimateAction.CLIMATE_ACTION_COOLING,
|
||||
"HEATING": ClimateAction.CLIMATE_ACTION_HEATING,
|
||||
"IDLE": ClimateAction.CLIMATE_ACTION_IDLE,
|
||||
"DRYING": ClimateAction.CLIMATE_ACTION_DRYING,
|
||||
"FAN": ClimateAction.CLIMATE_ACTION_FAN,
|
||||
"DEFROSTING": ClimateAction.CLIMATE_ACTION_DEFROSTING,
|
||||
}
|
||||
CLIMATE_ACTIONS = ClimateAction.options(
|
||||
"OFF",
|
||||
"COOLING",
|
||||
"HEATING",
|
||||
"IDLE",
|
||||
"DRYING",
|
||||
"FAN",
|
||||
"DEFROSTING",
|
||||
prefix="CLIMATE_ACTION_",
|
||||
)
|
||||
|
||||
validate_climate_action = cv.enum(CLIMATE_ACTIONS, upper=True)
|
||||
|
||||
|
||||
@@ -135,13 +135,14 @@ void LgIrClimate::transmit_state() {
|
||||
default:
|
||||
return;
|
||||
}
|
||||
this->transmit_(remote_state);
|
||||
this->publish_state();
|
||||
return;
|
||||
} else { // just toggle swing when advanced_commands_support is not set
|
||||
remote_state |= HEADER_BASIC;
|
||||
remote_state |= BASIC_SWING_TOGGLE;
|
||||
}
|
||||
// The remote's swing button sends a fixed code with no fan speed or temperature bits, so the
|
||||
// frame goes out as is instead of falling through to them
|
||||
this->transmit_(remote_state);
|
||||
return;
|
||||
} else { // Mode commands
|
||||
const bool climate_is_off = (this->mode_before_ == climate::CLIMATE_MODE_OFF);
|
||||
switch (this->mode) {
|
||||
@@ -208,7 +209,6 @@ void LgIrClimate::transmit_state() {
|
||||
}
|
||||
|
||||
this->transmit_(remote_state);
|
||||
this->publish_state();
|
||||
}
|
||||
|
||||
bool LgIrClimate::on_receive(remote_base::RemoteReceiveData data) {
|
||||
|
||||
@@ -27,8 +27,7 @@ uint8_t cm1106_checksum(const uint8_t *response, size_t len) {
|
||||
void CM1106Component::setup() {
|
||||
uint8_t response[8] = {0};
|
||||
if (!this->cm1106_write_command_(C_M1106_CMD_GET_CO2, sizeof(C_M1106_CMD_GET_CO2), response, sizeof(response))) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
this->mark_failed();
|
||||
this->mark_failed(LOG_STR(ESP_LOG_MSG_COMM_FAIL));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -139,9 +138,6 @@ void CM1106Component::dump_config() {
|
||||
" ABC baseline: %uppm",
|
||||
ONOFF(this->abc_boot_logic_ == CM1106_ABC_ENABLED), this->abc_cycle_, this->abc_baseline_);
|
||||
}
|
||||
if (this->is_failed()) {
|
||||
ESP_LOGE(TAG, ESP_LOG_MSG_COMM_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace esphome::cm1106
|
||||
|
||||
@@ -30,6 +30,7 @@ CONF_CRC_ENABLE = "crc_enable"
|
||||
CONF_DATA_BITS = "data_bits"
|
||||
CONF_DESCRIPTION = "description"
|
||||
CONF_DRAW_ROUNDING = "draw_rounding"
|
||||
CONF_DRIVE_STRENGTH = "drive_strength"
|
||||
CONF_ENABLE_OTA_DOWNGRADE_PROTECTION = "enable_ota_downgrade_protection"
|
||||
CONF_ENABLED = "enabled"
|
||||
CONF_GREEN_CHANNEL = "green_channel"
|
||||
@@ -54,6 +55,7 @@ CONF_ON_STATE_CHANGE = "on_state_change"
|
||||
CONF_ON_STOP = "on_stop"
|
||||
CONF_OUT_PIN_LEVEL = "out_pin_level"
|
||||
CONF_PARITY = "parity"
|
||||
CONF_QUERY_PARAMS = "query_params"
|
||||
CONF_RECEIVER_FREQUENCY = "receiver_frequency"
|
||||
CONF_RECONNECT_INTERVAL = "reconnect_interval"
|
||||
CONF_RED_CHANNEL = "red_channel"
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user