1
0
mirror of https://github.com/esphome/esphome.git synced 2025-09-15 09:42:19 +01:00
This commit is contained in:
J. Nick Koston
2025-06-11 22:55:15 -05:00
parent c047aa47eb
commit a7bb7fc14d
2 changed files with 25 additions and 23 deletions

View File

@@ -339,23 +339,23 @@ void ESP32TouchComponent::loop() {
this->setup_mode_last_log_print_ = now; this->setup_mode_last_log_print_ = now;
} }
// Process any queued touch events // Process any queued touch events from interrupts
TouchPadEvent event; TouchPadEvent event;
while (xQueueReceive(this->touch_queue_, &event, 0) == pdTRUE) { while (xQueueReceive(this->touch_queue_, &event, 0) == pdTRUE) {
// Find the corresponding sensor // Find the corresponding sensor
for (auto *child : this->children_) { for (auto *child : this->children_) {
if (child->get_touch_pad() == event.pad) { if (child->get_touch_pad() == event.pad) {
child->value_ = event.value; child->value_ = event.value;
bool new_state;
#if !(defined(USE_ESP32_VARIANT_ESP32S2) || defined(USE_ESP32_VARIANT_ESP32S3)) // The interrupt gives us the triggered state directly
new_state = child->value_ < child->get_threshold(); bool new_state = event.triggered;
#else
new_state = child->value_ > child->get_threshold();
#endif
// Only publish if state changed // Only publish if state changed
if (new_state != child->last_state_) { if (new_state != child->last_state_) {
child->last_state_ = new_state; child->last_state_ = new_state;
child->publish_state(new_state); child->publish_state(new_state);
ESP_LOGD(TAG, "Touch Pad '%s' state: %s (value: %" PRIu32 ", threshold: %" PRIu32 ")",
child->get_name().c_str(), new_state ? "ON" : "OFF", event.value, child->get_threshold());
} }
break; break;
} }
@@ -401,24 +401,25 @@ void ESP32TouchComponent::on_shutdown() {
void IRAM_ATTR ESP32TouchComponent::touch_isr_handler(void *arg) { void IRAM_ATTR ESP32TouchComponent::touch_isr_handler(void *arg) {
ESP32TouchComponent *component = static_cast<ESP32TouchComponent *>(arg); ESP32TouchComponent *component = static_cast<ESP32TouchComponent *>(arg);
uint32_t pad_intr = touch_pad_get_status(); uint32_t pad_status = touch_pad_get_status();
touch_pad_clear_status(); touch_pad_clear_status();
// Check which pads triggered // pad_status contains the current trigger state of all pads
for (int i = 0; i < TOUCH_PAD_MAX; i++) { // Send status update for all configured pads
if ((pad_intr >> i) & 0x01) { for (auto *child : component->children_) {
touch_pad_t pad = static_cast<touch_pad_t>(i); touch_pad_t pad = child->get_touch_pad();
TouchPadEvent event; TouchPadEvent event;
event.pad = pad; event.pad = pad;
// Read value in ISR using HAL function (safe for all variants) // Check if this pad is currently triggered (1) or not (0)
// touch_pad_read() and touch_pad_read_raw_data() use semaphores and cannot be called from ISR event.triggered = (pad_status >> pad) & 0x01;
event.value = touch_ll_read_raw_data(pad); // Read current value using HAL function (safe for all variants)
// Send to queue from ISR event.value = touch_ll_read_raw_data(pad);
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
xQueueSendFromISR(component->touch_queue_, &event, &xHigherPriorityTaskWoken); // Send to queue from ISR
if (xHigherPriorityTaskWoken) { BaseType_t xHigherPriorityTaskWoken = pdFALSE;
portYIELD_FROM_ISR(); xQueueSendFromISR(component->touch_queue_, &event, &xHigherPriorityTaskWoken);
} if (xHigherPriorityTaskWoken) {
portYIELD_FROM_ISR();
} }
} }
} }

View File

@@ -20,6 +20,7 @@ class ESP32TouchBinarySensor;
struct TouchPadEvent { struct TouchPadEvent {
touch_pad_t pad; touch_pad_t pad;
uint32_t value; uint32_t value;
bool triggered; // Whether this pad is currently in triggered state
}; };
class ESP32TouchComponent : public Component { class ESP32TouchComponent : public Component {