esphome 2025.2.1__py3-none-any.whl → 2025.3.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- esphome/__main__.py +9 -1
- esphome/components/api/api_connection.cpp +426 -70
- esphome/components/api/api_connection.h +117 -25
- esphome/components/api/api_pb2.cpp +33 -0
- esphome/components/api/api_pb2.h +4 -0
- esphome/components/api/api_server.cpp +2 -2
- esphome/components/api/list_entities.cpp +76 -22
- esphome/components/api/list_entities.h +1 -0
- esphome/components/api/subscribe_state.h +2 -0
- esphome/components/audio/__init__.py +1 -1
- esphome/components/audio/audio_decoder.cpp +43 -11
- esphome/components/audio/audio_reader.cpp +9 -9
- esphome/components/audio/audio_reader.h +1 -1
- esphome/components/audio/audio_resampler.cpp +4 -2
- esphome/components/audio/audio_transfer_buffer.cpp +19 -9
- esphome/components/audio/audio_transfer_buffer.h +7 -2
- esphome/components/bluetooth_proxy/bluetooth_proxy.h +8 -0
- esphome/components/bmp085/bmp085.cpp +1 -1
- esphome/components/chsc6x/__init__.py +2 -0
- esphome/components/chsc6x/chsc6x_touchscreen.cpp +47 -0
- esphome/components/chsc6x/chsc6x_touchscreen.h +34 -0
- esphome/components/chsc6x/touchscreen.py +33 -0
- esphome/components/climate/__init__.py +0 -1
- esphome/components/cst816/binary_sensor/__init__.py +2 -25
- esphome/components/cst816/touchscreen/cst816_touchscreen.cpp +3 -14
- esphome/components/cst816/touchscreen/cst816_touchscreen.h +0 -4
- esphome/components/esp32_ble_beacon/__init__.py +3 -1
- esphome/components/esp32_ble_tracker/esp32_ble_tracker.cpp +2 -2
- esphome/components/esp8266/gpio.py +1 -2
- esphome/components/font/__init__.py +198 -215
- esphome/components/font/font.cpp +4 -4
- esphome/components/font/font.h +1 -0
- esphome/components/graph/graph.cpp +4 -0
- esphome/components/graph/graph.h +4 -0
- esphome/components/haier/climate.py +11 -10
- esphome/components/hbridge/switch/hbridge_switch.cpp +2 -2
- esphome/components/heatpumpir/climate.py +2 -1
- esphome/components/heatpumpir/heatpumpir.cpp +1 -0
- esphome/components/heatpumpir/heatpumpir.h +1 -0
- esphome/components/i2c/__init__.py +6 -6
- esphome/components/i2c/i2c_bus_esp_idf.cpp +6 -2
- esphome/components/i2s_audio/speaker/i2s_audio_speaker.cpp +1 -1
- esphome/components/ili9xxx/display.py +1 -0
- esphome/components/ili9xxx/ili9xxx_display.h +5 -0
- esphome/components/ili9xxx/ili9xxx_init.h +59 -0
- esphome/components/ld2450/__init__.py +51 -0
- esphome/components/ld2450/binary_sensor.py +47 -0
- esphome/components/ld2450/button/__init__.py +45 -0
- esphome/components/ld2450/button/reset_button.cpp +9 -0
- esphome/components/ld2450/button/reset_button.h +18 -0
- esphome/components/ld2450/button/restart_button.cpp +9 -0
- esphome/components/ld2450/button/restart_button.h +18 -0
- esphome/components/ld2450/ld2450.cpp +876 -0
- esphome/components/ld2450/ld2450.h +234 -0
- esphome/components/ld2450/number/__init__.py +121 -0
- esphome/components/ld2450/number/presence_timeout_number.cpp +12 -0
- esphome/components/ld2450/number/presence_timeout_number.h +18 -0
- esphome/components/ld2450/number/zone_coordinate_number.cpp +14 -0
- esphome/components/ld2450/number/zone_coordinate_number.h +19 -0
- esphome/components/ld2450/select/__init__.py +56 -0
- esphome/components/ld2450/select/baud_rate_select.cpp +12 -0
- esphome/components/ld2450/select/baud_rate_select.h +18 -0
- esphome/components/ld2450/select/zone_type_select.cpp +12 -0
- esphome/components/ld2450/select/zone_type_select.h +18 -0
- esphome/components/ld2450/sensor.py +156 -0
- esphome/components/ld2450/switch/__init__.py +45 -0
- esphome/components/ld2450/switch/bluetooth_switch.cpp +12 -0
- esphome/components/ld2450/switch/bluetooth_switch.h +18 -0
- esphome/components/ld2450/switch/multi_target_switch.cpp +12 -0
- esphome/components/ld2450/switch/multi_target_switch.h +18 -0
- esphome/components/ld2450/text_sensor.py +62 -0
- esphome/components/ltr390/ltr390.cpp +7 -7
- esphome/components/ltr390/ltr390.h +0 -1
- esphome/components/lvgl/defines.py +0 -2
- esphome/components/lvgl/font.cpp +1 -1
- esphome/components/lvgl/lvgl_esphome.cpp +27 -19
- esphome/components/lvgl/widgets/img.py +1 -3
- esphome/components/mcp2515/mcp2515.cpp +1 -0
- esphome/components/mdns/__init__.py +1 -1
- esphome/components/mixer/speaker/mixer_speaker.cpp +6 -1
- esphome/components/mixer/speaker/mixer_speaker.h +2 -0
- esphome/components/mlx90393/sensor.py +53 -33
- esphome/components/mlx90393/sensor_mlx90393.cpp +4 -0
- esphome/components/mlx90393/sensor_mlx90393.h +8 -3
- esphome/components/mqtt/__init__.py +2 -2
- esphome/components/msa3xx/__init__.py +189 -0
- esphome/components/msa3xx/binary_sensor.py +40 -0
- esphome/components/msa3xx/msa3xx.cpp +417 -0
- esphome/components/msa3xx/msa3xx.h +311 -0
- esphome/components/msa3xx/sensor.py +42 -0
- esphome/components/msa3xx/text_sensor.py +38 -0
- esphome/components/nfc/binary_sensor/__init__.py +4 -4
- esphome/components/opentherm/binary_sensor/__init__.py +4 -4
- esphome/components/opentherm/generate.py +6 -6
- esphome/components/opentherm/sensor/__init__.py +5 -6
- esphome/components/packages/__init__.py +35 -11
- esphome/components/pn532/binary_sensor.py +4 -4
- esphome/components/rc522/binary_sensor.py +4 -4
- esphome/components/resampler/speaker/resampler_speaker.h +2 -0
- esphome/components/socket/bsd_sockets_impl.cpp +1 -0
- esphome/components/socket/lwip_sockets_impl.cpp +1 -0
- esphome/components/socket/socket.h +3 -1
- esphome/components/speaker/speaker.h +2 -2
- esphome/components/ssd1306_base/__init__.py +7 -7
- esphome/components/thermostat/climate.py +1 -1
- esphome/components/tmp1075/tmp1075.cpp +7 -11
- esphome/components/tmp1075/tmp1075.h +1 -2
- esphome/components/tormatic/__init__.py +1 -0
- esphome/components/tormatic/cover.py +47 -0
- esphome/components/tormatic/tormatic_cover.cpp +355 -0
- esphome/components/tormatic/tormatic_cover.h +60 -0
- esphome/components/tormatic/tormatic_protocol.h +211 -0
- esphome/components/touchscreen/binary_sensor/__init__.py +3 -0
- esphome/components/touchscreen/binary_sensor/touchscreen_binary_sensor.cpp +7 -1
- esphome/components/touchscreen/binary_sensor/touchscreen_binary_sensor.h +3 -1
- esphome/components/touchscreen/touchscreen.cpp +3 -4
- esphome/components/udp/udp_component.h +4 -1
- esphome/components/web_server/list_entities.cpp +70 -66
- esphome/components/web_server/list_entities.h +43 -22
- esphome/components/web_server/web_server.cpp +345 -68
- esphome/components/web_server/web_server.h +138 -6
- esphome/components/web_server_base/__init__.py +1 -1
- esphome/components/web_server_idf/__init__.py +2 -0
- esphome/components/web_server_idf/web_server_idf.cpp +177 -30
- esphome/components/web_server_idf/web_server_idf.h +53 -4
- esphome/config_validation.py +23 -125
- esphome/const.py +5 -1
- esphome/core/config.py +15 -6
- esphome/core/defines.h +1 -1
- esphome/core/helpers.h +24 -3
- esphome/core/time.cpp +1 -0
- esphome/cpp_generator.py +3 -3
- esphome/dashboard/core.py +30 -21
- esphome/dashboard/dns.py +7 -1
- esphome/dashboard/entries.py +83 -16
- esphome/dashboard/settings.py +0 -4
- esphome/dashboard/status/mdns.py +43 -14
- esphome/dashboard/status/mqtt.py +22 -9
- esphome/dashboard/status/ping.py +54 -10
- esphome/dashboard/web_server.py +56 -24
- esphome/storage_json.py +4 -0
- esphome/wizard.py +13 -17
- esphome/writer.py +1 -3
- esphome/yaml_util.py +36 -33
- esphome/zeroconf.py +9 -21
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/METADATA +7 -7
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/RECORD +151 -111
- esphome/components/cst816/binary_sensor/cst816_button.h +0 -27
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/LICENSE +0 -0
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/WHEEL +0 -0
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/entry_points.txt +0 -0
- {esphome-2025.2.1.dist-info → esphome-2025.3.0.dist-info}/top_level.txt +0 -0
@@ -1,20 +1,21 @@
|
|
1
|
+
from esphome import pins
|
1
2
|
import esphome.codegen as cg
|
2
|
-
import esphome.config_validation as cv
|
3
3
|
from esphome.components import i2c, sensor
|
4
|
+
import esphome.config_validation as cv
|
4
5
|
from esphome.const import (
|
5
|
-
|
6
|
-
UNIT_MICROTESLA,
|
7
|
-
UNIT_CELSIUS,
|
8
|
-
STATE_CLASS_MEASUREMENT,
|
9
|
-
ICON_MAGNET,
|
10
|
-
ICON_THERMOMETER,
|
6
|
+
CONF_FILTER,
|
11
7
|
CONF_GAIN,
|
12
|
-
|
8
|
+
CONF_ID,
|
13
9
|
CONF_OVERSAMPLING,
|
14
|
-
|
10
|
+
CONF_RESOLUTION,
|
15
11
|
CONF_TEMPERATURE,
|
12
|
+
CONF_TEMPERATURE_COMPENSATION,
|
13
|
+
ICON_MAGNET,
|
14
|
+
ICON_THERMOMETER,
|
15
|
+
STATE_CLASS_MEASUREMENT,
|
16
|
+
UNIT_CELSIUS,
|
17
|
+
UNIT_MICROTESLA,
|
16
18
|
)
|
17
|
-
from esphome import pins
|
18
19
|
|
19
20
|
CODEOWNERS = ["@functionpointer"]
|
20
21
|
DEPENDENCIES = ["i2c"]
|
@@ -26,30 +27,46 @@ MLX90393Component = mlx90393_ns.class_(
|
|
26
27
|
)
|
27
28
|
|
28
29
|
GAIN = {
|
29
|
-
"1X":
|
30
|
-
"
|
31
|
-
"1_67X":
|
32
|
-
"2X":
|
33
|
-
"2_5X":
|
34
|
-
"3X":
|
35
|
-
"
|
36
|
-
"5X":
|
30
|
+
"1X": 0,
|
31
|
+
"1_25X": 1,
|
32
|
+
"1_67X": 2,
|
33
|
+
"2X": 3,
|
34
|
+
"2_5X": 4,
|
35
|
+
"3X": 5,
|
36
|
+
"3_75X": 6,
|
37
|
+
"5X": 7,
|
37
38
|
}
|
38
39
|
|
39
40
|
RESOLUTION = {
|
40
|
-
"
|
41
|
-
"
|
42
|
-
"
|
43
|
-
"
|
41
|
+
"DIV_8": 3,
|
42
|
+
"DIV_4": 2,
|
43
|
+
"DIV_2": 1,
|
44
|
+
"DIV_1": 0,
|
44
45
|
}
|
45
46
|
|
46
47
|
CONF_X_AXIS = "x_axis"
|
47
48
|
CONF_Y_AXIS = "y_axis"
|
48
49
|
CONF_Z_AXIS = "z_axis"
|
49
50
|
CONF_DRDY_PIN = "drdy_pin"
|
51
|
+
CONF_HALLCONF = "hallconf"
|
52
|
+
|
53
|
+
|
54
|
+
def _validate(config):
|
55
|
+
if config[CONF_TEMPERATURE_COMPENSATION]:
|
56
|
+
for axis in [CONF_X_AXIS, CONF_Y_AXIS, CONF_Z_AXIS]:
|
57
|
+
if axis not in config:
|
58
|
+
continue
|
59
|
+
if (res := config[axis][CONF_RESOLUTION]) in [
|
60
|
+
"DIV_8",
|
61
|
+
"DIV_4",
|
62
|
+
]:
|
63
|
+
raise cv.Invalid(
|
64
|
+
f"{axis}: {CONF_RESOLUTION} cannot be {res} with {CONF_TEMPERATURE_COMPENSATION} enabled"
|
65
|
+
)
|
66
|
+
return config
|
50
67
|
|
51
68
|
|
52
|
-
def mlx90393_axis_schema(
|
69
|
+
def mlx90393_axis_schema():
|
53
70
|
return sensor.sensor_schema(
|
54
71
|
unit_of_measurement=UNIT_MICROTESLA,
|
55
72
|
accuracy_decimals=0,
|
@@ -58,7 +75,7 @@ def mlx90393_axis_schema(default_resolution: str):
|
|
58
75
|
).extend(
|
59
76
|
cv.Schema(
|
60
77
|
{
|
61
|
-
cv.Optional(CONF_RESOLUTION, default=
|
78
|
+
cv.Optional(CONF_RESOLUTION, default="DIV_4"): cv.enum(
|
62
79
|
RESOLUTION, upper=True, space="_"
|
63
80
|
)
|
64
81
|
}
|
@@ -66,19 +83,19 @@ def mlx90393_axis_schema(default_resolution: str):
|
|
66
83
|
)
|
67
84
|
|
68
85
|
|
69
|
-
CONFIG_SCHEMA = (
|
86
|
+
CONFIG_SCHEMA = cv.All(
|
70
87
|
cv.Schema(
|
71
88
|
{
|
72
89
|
cv.GenerateID(): cv.declare_id(MLX90393Component),
|
73
|
-
cv.Optional(CONF_GAIN, default="
|
74
|
-
GAIN, upper=True, space="_"
|
75
|
-
),
|
90
|
+
cv.Optional(CONF_GAIN, default="1X"): cv.enum(GAIN, upper=True, space="_"),
|
76
91
|
cv.Optional(CONF_DRDY_PIN): pins.gpio_input_pin_schema,
|
77
|
-
cv.Optional(CONF_OVERSAMPLING, default=
|
92
|
+
cv.Optional(CONF_OVERSAMPLING, default=0): cv.int_range(min=0, max=3),
|
78
93
|
cv.Optional(CONF_FILTER, default=6): cv.int_range(min=0, max=7),
|
79
|
-
cv.Optional(CONF_X_AXIS): mlx90393_axis_schema(
|
80
|
-
cv.Optional(CONF_Y_AXIS): mlx90393_axis_schema(
|
81
|
-
cv.Optional(CONF_Z_AXIS): mlx90393_axis_schema(
|
94
|
+
cv.Optional(CONF_X_AXIS): mlx90393_axis_schema(),
|
95
|
+
cv.Optional(CONF_Y_AXIS): mlx90393_axis_schema(),
|
96
|
+
cv.Optional(CONF_Z_AXIS): mlx90393_axis_schema(),
|
97
|
+
cv.Optional(CONF_TEMPERATURE_COMPENSATION, default=False): bool,
|
98
|
+
cv.Optional(CONF_HALLCONF, default=0xC): cv.one_of(0xC, 0x0),
|
82
99
|
cv.Optional(CONF_TEMPERATURE): sensor.sensor_schema(
|
83
100
|
unit_of_measurement=UNIT_CELSIUS,
|
84
101
|
accuracy_decimals=1,
|
@@ -96,7 +113,8 @@ CONFIG_SCHEMA = (
|
|
96
113
|
},
|
97
114
|
)
|
98
115
|
.extend(cv.polling_component_schema("60s"))
|
99
|
-
.extend(i2c.i2c_device_schema(0x0C))
|
116
|
+
.extend(i2c.i2c_device_schema(0x0C)),
|
117
|
+
_validate,
|
100
118
|
)
|
101
119
|
|
102
120
|
|
@@ -111,6 +129,8 @@ async def to_code(config):
|
|
111
129
|
cg.add(var.set_gain(GAIN[config[CONF_GAIN]]))
|
112
130
|
cg.add(var.set_oversampling(config[CONF_OVERSAMPLING]))
|
113
131
|
cg.add(var.set_filter(config[CONF_FILTER]))
|
132
|
+
cg.add(var.set_temperature_compensation(config[CONF_TEMPERATURE_COMPENSATION]))
|
133
|
+
cg.add(var.set_hallconf(config[CONF_HALLCONF]))
|
114
134
|
|
115
135
|
if CONF_X_AXIS in config:
|
116
136
|
sens = await sensor.new_sensor(config[CONF_X_AXIS])
|
@@ -43,6 +43,10 @@ void MLX90393Cls::setup() {
|
|
43
43
|
this->mlx_.setDigitalFiltering(this->filter_);
|
44
44
|
|
45
45
|
this->mlx_.setTemperatureOverSampling(this->temperature_oversampling_);
|
46
|
+
|
47
|
+
this->mlx_.setTemperatureCompensation(this->temperature_compensation_);
|
48
|
+
|
49
|
+
this->mlx_.setHallConf(this->hallconf_);
|
46
50
|
}
|
47
51
|
|
48
52
|
void MLX90393Cls::dump_config() {
|
@@ -29,7 +29,10 @@ class MLX90393Cls : public PollingComponent, public i2c::I2CDevice, public MLX90
|
|
29
29
|
void set_resolution(uint8_t xyz, uint8_t res) { resolutions_[xyz] = res; }
|
30
30
|
void set_filter(uint8_t filter) { filter_ = filter; }
|
31
31
|
void set_gain(uint8_t gain_sel) { gain_ = gain_sel; }
|
32
|
-
|
32
|
+
void set_temperature_compensation(bool temperature_compensation) {
|
33
|
+
temperature_compensation_ = temperature_compensation;
|
34
|
+
}
|
35
|
+
void set_hallconf(uint8_t hallconf) { hallconf_ = hallconf; }
|
33
36
|
// overrides for MLX library
|
34
37
|
|
35
38
|
// disable lint because it keeps suggesting const uint8_t *response.
|
@@ -49,9 +52,11 @@ class MLX90393Cls : public PollingComponent, public i2c::I2CDevice, public MLX90
|
|
49
52
|
sensor::Sensor *t_sensor_{nullptr};
|
50
53
|
uint8_t gain_;
|
51
54
|
uint8_t oversampling_;
|
52
|
-
uint8_t temperature_oversampling_
|
55
|
+
uint8_t temperature_oversampling_{0};
|
53
56
|
uint8_t filter_;
|
54
|
-
uint8_t resolutions_[3]
|
57
|
+
uint8_t resolutions_[3]{0};
|
58
|
+
bool temperature_compensation_{false};
|
59
|
+
uint8_t hallconf_{0xC};
|
55
60
|
GPIOPin *drdy_pin_{nullptr};
|
56
61
|
};
|
57
62
|
|
@@ -36,6 +36,7 @@ from esphome.const import (
|
|
36
36
|
CONF_PAYLOAD_AVAILABLE,
|
37
37
|
CONF_PAYLOAD_NOT_AVAILABLE,
|
38
38
|
CONF_PORT,
|
39
|
+
CONF_PUBLISH_NAN_AS_NONE,
|
39
40
|
CONF_QOS,
|
40
41
|
CONF_REBOOT_TIMEOUT,
|
41
42
|
CONF_RETAIN,
|
@@ -49,7 +50,6 @@ from esphome.const import (
|
|
49
50
|
CONF_USE_ABBREVIATIONS,
|
50
51
|
CONF_USERNAME,
|
51
52
|
CONF_WILL_MESSAGE,
|
52
|
-
CONF_PUBLISH_NAN_AS_NONE,
|
53
53
|
PLATFORM_BK72XX,
|
54
54
|
PLATFORM_ESP32,
|
55
55
|
PLATFORM_ESP8266,
|
@@ -406,7 +406,7 @@ async def to_code(config):
|
|
406
406
|
if CONF_SSL_FINGERPRINTS in config:
|
407
407
|
for fingerprint in config[CONF_SSL_FINGERPRINTS]:
|
408
408
|
arr = [
|
409
|
-
cg.RawExpression(f"0x{fingerprint[i:i + 2]}") for i in range(0, 40, 2)
|
409
|
+
cg.RawExpression(f"0x{fingerprint[i : i + 2]}") for i in range(0, 40, 2)
|
410
410
|
]
|
411
411
|
cg.add(var.add_ssl_fingerprint(arr))
|
412
412
|
cg.add_build_flag("-DASYNC_TCP_SSL_ENABLED=1")
|
@@ -0,0 +1,189 @@
|
|
1
|
+
from esphome import automation
|
2
|
+
import esphome.codegen as cg
|
3
|
+
from esphome.components import i2c
|
4
|
+
import esphome.config_validation as cv
|
5
|
+
from esphome.const import (
|
6
|
+
CONF_CALIBRATION,
|
7
|
+
CONF_ID,
|
8
|
+
CONF_MIRROR_X,
|
9
|
+
CONF_MIRROR_Y,
|
10
|
+
CONF_OFFSET_X,
|
11
|
+
CONF_OFFSET_Y,
|
12
|
+
CONF_OFFSET_Z,
|
13
|
+
CONF_RANGE,
|
14
|
+
CONF_RESOLUTION,
|
15
|
+
CONF_SWAP_XY,
|
16
|
+
CONF_TRANSFORM,
|
17
|
+
CONF_TYPE,
|
18
|
+
)
|
19
|
+
|
20
|
+
CODEOWNERS = ["@latonita"]
|
21
|
+
DEPENDENCIES = ["i2c"]
|
22
|
+
|
23
|
+
MULTI_CONF = True
|
24
|
+
|
25
|
+
CONF_MSA3XX_ID = "msa3xx_id"
|
26
|
+
|
27
|
+
CONF_MIRROR_Z = "mirror_z"
|
28
|
+
CONF_ON_ACTIVE = "on_active"
|
29
|
+
CONF_ON_DOUBLE_TAP = "on_double_tap"
|
30
|
+
CONF_ON_FREEFALL = "on_freefall"
|
31
|
+
CONF_ON_ORIENTATION = "on_orientation"
|
32
|
+
CONF_ON_TAP = "on_tap"
|
33
|
+
|
34
|
+
MODEL_MSA301 = "MSA301"
|
35
|
+
MODEL_MSA311 = "MSA311"
|
36
|
+
|
37
|
+
msa3xx_ns = cg.esphome_ns.namespace("msa3xx")
|
38
|
+
MSA3xxComponent = msa3xx_ns.class_(
|
39
|
+
"MSA3xxComponent", cg.PollingComponent, i2c.I2CDevice
|
40
|
+
)
|
41
|
+
|
42
|
+
MSAModels = msa3xx_ns.enum("Model", True)
|
43
|
+
MSA_MODELS = {
|
44
|
+
MODEL_MSA301: MSAModels.MSA301,
|
45
|
+
MODEL_MSA311: MSAModels.MSA311,
|
46
|
+
}
|
47
|
+
|
48
|
+
MSARange = msa3xx_ns.enum("Range", True)
|
49
|
+
MSA_RANGES = {
|
50
|
+
"2G": MSARange.RANGE_2G,
|
51
|
+
"4G": MSARange.RANGE_4G,
|
52
|
+
"8G": MSARange.RANGE_8G,
|
53
|
+
"16G": MSARange.RANGE_16G,
|
54
|
+
}
|
55
|
+
|
56
|
+
MSAResolution = msa3xx_ns.enum("Resolution", True)
|
57
|
+
RESOLUTIONS_MSA301 = {
|
58
|
+
14: MSAResolution.RES_14BIT,
|
59
|
+
12: MSAResolution.RES_12BIT,
|
60
|
+
10: MSAResolution.RES_10BIT,
|
61
|
+
8: MSAResolution.RES_8BIT,
|
62
|
+
}
|
63
|
+
|
64
|
+
RESOLUTIONS_MSA311 = {
|
65
|
+
12: MSAResolution.RES_12BIT,
|
66
|
+
}
|
67
|
+
|
68
|
+
_COMMON_SCHEMA = cv.Schema(
|
69
|
+
{
|
70
|
+
cv.GenerateID(): cv.declare_id(MSA3xxComponent),
|
71
|
+
cv.Optional(CONF_RANGE, default="2G"): cv.enum(MSA_RANGES, upper=True),
|
72
|
+
cv.Optional(CONF_CALIBRATION): cv.Schema(
|
73
|
+
{
|
74
|
+
cv.Optional(CONF_OFFSET_X, default=0): cv.float_range(
|
75
|
+
min=-4.5, max=4.5
|
76
|
+
),
|
77
|
+
cv.Optional(CONF_OFFSET_Y, default=0): cv.float_range(
|
78
|
+
min=-4.5, max=4.5
|
79
|
+
),
|
80
|
+
cv.Optional(CONF_OFFSET_Z, default=0): cv.float_range(
|
81
|
+
min=-4.5, max=4.5
|
82
|
+
),
|
83
|
+
}
|
84
|
+
),
|
85
|
+
cv.Optional(CONF_TRANSFORM): cv.Schema(
|
86
|
+
{
|
87
|
+
cv.Optional(CONF_MIRROR_X, default=False): cv.boolean,
|
88
|
+
cv.Optional(CONF_MIRROR_Y, default=False): cv.boolean,
|
89
|
+
cv.Optional(CONF_MIRROR_Z, default=False): cv.boolean,
|
90
|
+
cv.Optional(CONF_SWAP_XY, default=False): cv.boolean,
|
91
|
+
}
|
92
|
+
),
|
93
|
+
cv.Optional(CONF_ON_ACTIVE): automation.validate_automation(single=True),
|
94
|
+
cv.Optional(CONF_ON_TAP): automation.validate_automation(single=True),
|
95
|
+
cv.Optional(CONF_ON_DOUBLE_TAP): automation.validate_automation(single=True),
|
96
|
+
cv.Optional(CONF_ON_FREEFALL): automation.validate_automation(single=True),
|
97
|
+
cv.Optional(CONF_ON_ORIENTATION): automation.validate_automation(single=True),
|
98
|
+
}
|
99
|
+
).extend(cv.polling_component_schema("10s"))
|
100
|
+
|
101
|
+
|
102
|
+
CONFIG_SCHEMA = cv.typed_schema(
|
103
|
+
{
|
104
|
+
MODEL_MSA301: _COMMON_SCHEMA.extend(
|
105
|
+
{
|
106
|
+
cv.Optional(CONF_RESOLUTION, default=14): cv.enum(RESOLUTIONS_MSA301),
|
107
|
+
}
|
108
|
+
).extend(i2c.i2c_device_schema(0x26)),
|
109
|
+
MODEL_MSA311: _COMMON_SCHEMA.extend(
|
110
|
+
{
|
111
|
+
cv.Optional(CONF_RESOLUTION, default=12): cv.enum(RESOLUTIONS_MSA311),
|
112
|
+
}
|
113
|
+
).extend(i2c.i2c_device_schema(0x62)),
|
114
|
+
},
|
115
|
+
upper=True,
|
116
|
+
enum=MSA_MODELS,
|
117
|
+
)
|
118
|
+
|
119
|
+
MSA_SENSOR_SCHEMA = cv.Schema(
|
120
|
+
{
|
121
|
+
cv.GenerateID(CONF_MSA3XX_ID): cv.use_id(MSA3xxComponent),
|
122
|
+
}
|
123
|
+
)
|
124
|
+
|
125
|
+
|
126
|
+
async def to_code(config):
|
127
|
+
var = cg.new_Pvariable(config[CONF_ID])
|
128
|
+
await cg.register_component(var, config)
|
129
|
+
await i2c.register_i2c_device(var, config)
|
130
|
+
|
131
|
+
cg.add(var.set_model(config[CONF_TYPE]))
|
132
|
+
cg.add(var.set_range(MSA_RANGES[config[CONF_RANGE]]))
|
133
|
+
cg.add(var.set_resolution(RESOLUTIONS_MSA301[config[CONF_RESOLUTION]]))
|
134
|
+
|
135
|
+
if transform := config.get(CONF_TRANSFORM):
|
136
|
+
cg.add(
|
137
|
+
var.set_transform(
|
138
|
+
transform[CONF_MIRROR_X],
|
139
|
+
transform[CONF_MIRROR_Y],
|
140
|
+
transform[CONF_MIRROR_Z],
|
141
|
+
transform[CONF_SWAP_XY],
|
142
|
+
)
|
143
|
+
)
|
144
|
+
|
145
|
+
if calibration_config := config.get(CONF_CALIBRATION):
|
146
|
+
cg.add(
|
147
|
+
var.set_offset(
|
148
|
+
calibration_config[CONF_OFFSET_X],
|
149
|
+
calibration_config[CONF_OFFSET_Y],
|
150
|
+
calibration_config[CONF_OFFSET_Z],
|
151
|
+
)
|
152
|
+
)
|
153
|
+
|
154
|
+
# Triggers secton
|
155
|
+
|
156
|
+
if CONF_ON_ORIENTATION in config:
|
157
|
+
await automation.build_automation(
|
158
|
+
var.get_orientation_trigger(),
|
159
|
+
[],
|
160
|
+
config[CONF_ON_ORIENTATION],
|
161
|
+
)
|
162
|
+
|
163
|
+
if CONF_ON_TAP in config:
|
164
|
+
await automation.build_automation(
|
165
|
+
var.get_tap_trigger(),
|
166
|
+
[],
|
167
|
+
config[CONF_ON_TAP],
|
168
|
+
)
|
169
|
+
|
170
|
+
if CONF_ON_DOUBLE_TAP in config:
|
171
|
+
await automation.build_automation(
|
172
|
+
var.get_double_tap_trigger(),
|
173
|
+
[],
|
174
|
+
config[CONF_ON_DOUBLE_TAP],
|
175
|
+
)
|
176
|
+
|
177
|
+
if CONF_ON_ACTIVE in config:
|
178
|
+
await automation.build_automation(
|
179
|
+
var.get_active_trigger(),
|
180
|
+
[],
|
181
|
+
config[CONF_ON_ACTIVE],
|
182
|
+
)
|
183
|
+
|
184
|
+
if CONF_ON_FREEFALL in config:
|
185
|
+
await automation.build_automation(
|
186
|
+
var.get_freefall_trigger(),
|
187
|
+
[],
|
188
|
+
config[CONF_ON_FREEFALL],
|
189
|
+
)
|
@@ -0,0 +1,40 @@
|
|
1
|
+
import esphome.codegen as cg
|
2
|
+
from esphome.components import binary_sensor
|
3
|
+
import esphome.config_validation as cv
|
4
|
+
from esphome.const import CONF_ACTIVE, CONF_NAME, DEVICE_CLASS_VIBRATION, ICON_VIBRATE
|
5
|
+
|
6
|
+
from . import CONF_MSA3XX_ID, MSA_SENSOR_SCHEMA
|
7
|
+
|
8
|
+
CODEOWNERS = ["@latonita"]
|
9
|
+
DEPENDENCIES = ["msa3xx"]
|
10
|
+
|
11
|
+
CONF_TAP = "tap"
|
12
|
+
CONF_DOUBLE_TAP = "double_tap"
|
13
|
+
|
14
|
+
ICON_TAP = "mdi:gesture-tap"
|
15
|
+
ICON_DOUBLE_TAP = "mdi:gesture-double-tap"
|
16
|
+
|
17
|
+
EVENT_SENSORS = (CONF_TAP, CONF_DOUBLE_TAP, CONF_ACTIVE)
|
18
|
+
ICONS = (ICON_TAP, ICON_DOUBLE_TAP, ICON_VIBRATE)
|
19
|
+
|
20
|
+
CONFIG_SCHEMA = MSA_SENSOR_SCHEMA.extend(
|
21
|
+
{
|
22
|
+
cv.Optional(event): cv.maybe_simple_value(
|
23
|
+
binary_sensor.binary_sensor_schema(
|
24
|
+
device_class=DEVICE_CLASS_VIBRATION,
|
25
|
+
icon=icon,
|
26
|
+
),
|
27
|
+
key=CONF_NAME,
|
28
|
+
)
|
29
|
+
for event, icon in zip(EVENT_SENSORS, ICONS)
|
30
|
+
}
|
31
|
+
)
|
32
|
+
|
33
|
+
|
34
|
+
async def to_code(config):
|
35
|
+
hub = await cg.get_variable(config[CONF_MSA3XX_ID])
|
36
|
+
|
37
|
+
for sensor in EVENT_SENSORS:
|
38
|
+
if sensor in config:
|
39
|
+
sens = await binary_sensor.new_binary_sensor(config[sensor])
|
40
|
+
cg.add(getattr(hub, f"set_{sensor}_binary_sensor")(sens))
|