feat(control-plane): show listening ui for ptt button

This commit is contained in:
chenjintao
2026-08-20 11:02:38 +08:00
parent 93f346a897
commit 045a803362
4 changed files with 58 additions and 27 deletions
@@ -213,6 +213,8 @@ typedef struct {
bool pending_press_after_teardown;
bool start_action_sent;
bool speech_action_sent;
bool listening_ui_active;
domain_expression_trigger_t listening_ui_trigger;
} ptt_runtime_t;
typedef struct {
@@ -552,7 +554,27 @@ static void control_plane_notify_wifi_state_task(void)
}
}
void control_plane_set_ptt_active(bool active)
static void control_plane_request_ptt_expression(
domain_expression_id_t id,
domain_expression_trigger_t trigger)
{
const domain_expression_request_t request = {
.id = id,
.trigger = trigger,
};
esp_err_t err = domain_runtime_request_expression(&request);
if (err != ESP_OK && err != ESP_ERR_INVALID_STATE) {
ESP_LOGW(TAG,
"PTT expression request failed: id=%d trigger=%d err=%s",
(int)id,
(int)trigger,
esp_err_to_name(err));
}
}
static void control_plane_set_ptt_active_with_trigger(
bool active,
domain_expression_trigger_t listening_ui_trigger)
{
if (active) {
control_plane_local_wake_pause_for_foreground();
@@ -563,6 +585,9 @@ void control_plane_set_ptt_active(bool active)
uint32_t generation = 0;
const char *transition_reason = active ? "press" : "release";
bool uplink_running = !active && control_plane_multimodal_is_uplink_running();
bool request_listening_ui = false;
bool restore_idle_ui = false;
domain_expression_trigger_t expression_trigger = listening_ui_trigger;
portENTER_CRITICAL(&s_runtime_lock);
old_state = s_ptt_runtime.state;
s_ptt_active = active;
@@ -575,6 +600,9 @@ void control_plane_set_ptt_active(bool active)
s_ptt_runtime.foreground_attempts = 0;
s_ptt_runtime.start_action_sent = false;
s_ptt_runtime.speech_action_sent = false;
s_ptt_runtime.listening_ui_active = true;
s_ptt_runtime.listening_ui_trigger = listening_ui_trigger;
request_listening_ui = true;
if (s_ptt_runtime.state == PTT_STATE_TEARDOWN_LOCAL ||
s_ptt_runtime.state == PTT_STATE_TEARDOWN_REMOTE) {
s_ptt_runtime.pending_press_after_teardown = true;
@@ -589,6 +617,9 @@ void control_plane_set_ptt_active(bool active)
s_ptt_runtime.foreground_attempts = 0;
s_ptt_runtime.pending_press_after_teardown = false;
s_ptt_runtime.generation++;
restore_idle_ui = s_ptt_runtime.listening_ui_active;
expression_trigger = s_ptt_runtime.listening_ui_trigger;
s_ptt_runtime.listening_ui_active = false;
if (uplink_running || s_ptt_runtime.state == PTT_STATE_STREAMING) {
control_plane_ptt_transition_locked(PTT_STATE_TEARDOWN_LOCAL, "release_streaming");
transition_reason = "release_streaming";
@@ -608,6 +639,15 @@ void control_plane_set_ptt_active(bool active)
generation = s_ptt_runtime.generation;
portEXIT_CRITICAL(&s_runtime_lock);
control_plane_ptt_log_transition(old_state, new_state, generation, transition_reason);
if (request_listening_ui) {
control_plane_request_ptt_expression(
DOMAIN_EXPRESSION_LISTENING,
expression_trigger);
} else if (restore_idle_ui) {
control_plane_request_ptt_expression(
DOMAIN_EXPRESSION_IDLE,
expression_trigger);
}
if (notify_worker) {
control_plane_notify_wifi_state_task();
}
@@ -616,6 +656,20 @@ void control_plane_set_ptt_active(bool active)
}
}
void control_plane_set_ptt_active(bool active)
{
control_plane_set_ptt_active_with_trigger(
active,
DOMAIN_EXPRESSION_TRIGGER_PTT_BUTTON);
}
void control_plane_set_ptt_active_from_local_wake(void)
{
control_plane_set_ptt_active_with_trigger(
true,
DOMAIN_EXPRESSION_TRIGGER_LOCAL_WAKE);
}
void control_plane_ptt_reset_capture_window(void)
{
bool active = false;