Hello @MattG
Si tu as toujours le Korvo v1.1 sous le coude, la bonne nouvelle c’est que la sortie audio fonctionne enfin ( mode speaker mais pas media_player, c’est mieux que rien).
Vu que c’est un ESP32 Wrover , le wakeword ondevice est aussi possible.
@+
Hello,
J’utilise aussi un Korvo v1.1
Je me demandais quel était l’avantage d’utiliser la platform ESP-IDF au lieu d’Arduino si Arduino permet de faire Media Player ? Est ce que IDF fonctionne mieux ?
Et enfin, comment fais tu pour utiliser le wakeword on device dessus ? C’est Micro Wake Word ?
Merci !
Hello
Oui , il s’agit bien du micro wakeword.
Le pb avec ce device, c’est que ce soit avec le framework Arduino, idf ou adf, jusqu’à présent on n’arrivait pas à lui faire sortir un son via son ampli ou le jack 3.5.
Un développement spécifique pour cette carte d’un component est maintenant disponible mais que pour du speaker , pas du media player.
Je finalise quelques tests d’ici fin de semaine et publierai le code yaml ici
@+
MattG
Juin 24, 2024, 6:27
64
Salut Krull56,
Merci beaucoup pour le retour.
J’avais un peu laissé tomber vus les soucis mais ça me donne envie de m’y remettre ! Reste le temps mais on va trouver !
A+,
Matt.
1 « J'aime »
Hello @MattG
Tu peux ressortir ton korvo V1 du placard
Désolé pour le retard mais j’attendais la sortie de la nouvelle version d’ESPhome intégrant la V2 des microwakeword.
Dispo depuis ce matin donc je me suis attelé tout de suite à la tache
Voilà le code de mon proto , fait par agrégation de différentes sources ( je n’invente rien)
Au menu :
Du son ! Les sorties audio de la korvo sont enfin fonctionnelles , la gestion du volume par les 2 boutons ou directement dans HA est un peu capricieuse mais une fois réglé ça fonctionne correctement même si ce n’est pas très puissant. Les 4 autres boutons sont dispos pour y integrer d’autres fonctions
Microwakeword ( très très réactif) , les 3 sont implémentés dans le code ( Okay Nabu, Hey Jarvis, Alexa)
Ajout d’un selecteur pour choisir Microwakeword ou Wakeword défini du pipeline
En attente:
Media_player
Toujours obligé de faire un petit reset ( bouton latéral) après première mise sous tension
utilisation du paramètre VAD du MicroWakeword
A toi de jouer et de nous partager d’éventuelles améliorations
@+
substitutions:
name: korvosat2
friendly_name: korvosat2
voice_assist_idle_phase_id: "1"
voice_assist_listening_phase_id: "2"
voice_assist_thinking_phase_id: "3"
voice_assist_replying_phase_id: "4"
voice_assist_not_ready_phase_id: "10"
voice_assist_error_phase_id: "11"
voice_assist_muted_phase_id: "12"
esphome:
name: ${name}
friendly_name: ${friendly_name}
platformio_options:
board_build.flash_mode: dio
on_boot:
- priority: -100
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Fast Pulse
- delay: 1s
- wait_until:
condition:
wifi.connected:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Slow Pulse
- wait_until: api.connected
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 100%
effect: Pulse
- delay: 1s
- if:
condition:
lambda: return id(init_in_progress);
then:
- lambda: id(init_in_progress) = false;
- script.execute: reset_led
esp32:
board: esp-wrover-kit
framework:
type: esp-idf
version: recommended
sdkconfig_options:
CONFIG_IDF_TARGET_ESP32: y
CONFIG_ESPTOOLPY_FLASHMODE_QIO: y
CONFIG_ESPTOOLPY_FLASHFREQ_80M: y
CONFIG_ESPTOOLPY_FLASHSIZE_16MB: y
CONFIG_ESP32S3_DATA_CACHE_64KB: y
CONFIG_ESP32S3_DATA_CACHE_LINE_64B: y
CONFIG_PARTITION_TABLE_CUSTOM: y
CONFIG_PARTITION_TABLE_CUSTOM_FILENAME: "default_16MB.csv"
CONFIG_PARTITION_TABLE_FILENAME: "default_16MB.csv"
CONFIG_PARTITION_TABLE_OFFSET: "0x8000"
CONFIG_ESP32_DEFAULT_CPU_FREQ_240: y
CONFIG_ESP32_SPIRAM_SUPPORT: y
CONFIG_SPIRAM_SPEED_80M: y
CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT: y
CONFIG_I2S_ENABLE_DEBUG_LOG: y
CONFIG_AUDIO_BOARD_CUSTOM: y
components:
- name: esp32_korvo1_board
source: github://dwitgen/korvo_1@main
refresh: 0s
external_components:
- source: github://dwitgen/esphome@main
components: [esp_adf]
refresh: 0s
# Enable logging
logger:
# Enable Home Assistant API
api:
encryption:
key: "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
services:
- service: volume_up
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- service: volume_down
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
ota:
- platform: esphome
password: "xxxxxxxxxxxx"
wifi:
ssid: !secret wifi_ssid
password: !secret wifi_password
# Enable fallback hotspot (captive portal) in case wifi connection fails
ap:
ssid: "Korvosat Fallback Hotspot"
password: "yyyyyyyyy"
captive_portal:
output:
- platform: gpio
id: pa_ctrl
pin:
number: GPIO12
ignore_strapping_warning: true
esp_adf:
board: esp32korvo1
speaker:
- platform: esp_adf
id: external_speaker
microphone:
- platform: esp_adf
id: external_mic
micro_wake_word:
vad:
models:
- model: okay_nabu
- model: hey_jarvis
- model: alexa
on_wake_word_detected:
then:
- voice_assistant.start:
wake_word: !lambda return wake_word;
voice_assistant:
id: voice_asst
microphone: external_mic
speaker: external_speaker
noise_suppression_level: 2
auto_gain: 31dBFS
volume_multiplier: 6
on_listening:
- lambda: id(voice_assistant_phase) = ${voice_assist_listening_phase_id};
- script.execute: reset_led
on_stt_vad_end:
- lambda: id(voice_assistant_phase) = ${voice_assist_thinking_phase_id};
- script.execute: reset_led
on_tts_start:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 100%
brightness: 60%
effect: Working
on_stt_end:
- homeassistant.service:
service: media_player.play_media
data:
entity_id: media_player.mpd
media_content_id: !lambda return x;
media_content_type: music
announce: "true"
on_tts_stream_start:
- output.turn_on: pa_ctrl
- delay: 100ms
- lambda: id(voice_assistant_phase) = ${voice_assist_replying_phase_id};
- script.execute: reset_led
on_end:
- delay: 100ms
- wait_until:
not:
speaker.is_playing:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
- script.execute: reset_led
- if:
condition:
and:
- switch.is_off: mute
- lambda: return id(wake_word_engine_location).state == "On device";
then:
- wait_until:
not:
voice_assistant.is_running:
- micro_wake_word.start:
on_error:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_error_phase_id};
- script.execute: reset_led
- delay: 2s
- if:
condition:
switch.is_off: mute
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
else:
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- script.execute: reset_led
on_client_connected:
- if:
condition:
switch.is_off: mute
then:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.start
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
else:
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- lambda: id(init_in_progress) = false;
- script.execute: reset_led
on_client_disconnected:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.stop
- lambda: id(voice_assistant_phase) = ${voice_assist_not_ready_phase_id};
- script.execute: reset_led
script:
- id: reset_led
then:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_listening_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
brightness: 100%
effect: wakeword
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_thinking_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 0%
brightness: 100%
effect: Working
- delay: 100ms
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_replying_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 0%
green: 100%
brightness: 100%
effect: Working
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_idle_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 0%
brightness: 40%
effect: none
- delay: 200ms
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_not_ready_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 40%
red: 100%
green: 0%
effect: Slow Pulse
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_error_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
brightness: 100%
effect: none
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_muted_phase_id};
then:
- light.turn_off: led_ring
else:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Fast Pulse
light:
- platform: esp32_rmt_led_strip
id: led_ring
name: "${friendly_name} Light"
pin: GPIO33 #GPIO19
num_leds: 12
rmt_channel: 0
rgb_order: GRB
chipset: ws2812
default_transition_length: 0s
effects:
- pulse:
name: "Pulse"
transition_length: 300ms
update_interval: 300ms
min_brightness: 50%
max_brightness: 100%
- addressable_twinkle:
name: "Working"
twinkle_probability: 5%
progress_interval: 3ms
- addressable_color_wipe:
name: "Wakeword"
colors:
- red: 100%
green: 0%
blue: 0%
num_leds: 12
add_led_interval: 40ms
reverse: false
- pulse:
name: "Slow Pulse"
transition_length: 0.5s
update_interval: 1s
min_brightness: 0%
max_brightness: 100%
- pulse:
name: "Fast Pulse"
transition_length: 50ms
update_interval: 100ms
min_brightness: 50%
max_brightness: 100%
switch:
- platform: template
name: Mute
id: mute
optimistic: true
restore_mode: RESTORE_DEFAULT_OFF
entity_category: config
on_turn_off:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
- if:
condition:
not:
- voice_assistant.is_running
then:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.start
- script.execute: reset_led
on_turn_on:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop
- micro_wake_word.stop
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- script.execute: reset_led
- platform: restart
name: "${name} Restart"
select:
- platform: template
entity_category: config
name: Wake word engine location
id: wake_word_engine_location
optimistic: true
restore_value: true
options:
- In Home Assistant
- On device
initial_option: On device
on_value:
- wait_until:
lambda: return id(voice_assistant_phase) == ${voice_assist_muted_phase_id} || id(voice_assistant_phase) == ${voice_assist_idle_phase_id};
- if:
condition:
lambda: return x == "In Home Assistant";
then:
- micro_wake_word.stop
- delay: 500ms
- if:
condition:
switch.is_off: mute
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous:
- if:
condition:
lambda: return x == "On device";
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop
- delay: 500ms
- micro_wake_word.start
globals:
- id: init_in_progress
type: bool
restore_value: false
initial_value: "true"
- id: voice_assistant_phase
type: int
restore_value: false
initial_value: ${voice_assist_not_ready_phase_id}
- id: speaker_volume
type: int
restore_value: yes
initial_value: '50'
button:
- platform: template
name: "${friendly_name} Volume Up"
id: btn_volume_up
on_press:
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- platform: template
name: "${friendly_name} Volume Down"
id: btn_volume_down
on_press:
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
binary_sensor:
- platform: template
name: "${friendly_name} Volume Up"
id: btn_vol_up
publish_initial_state : True
on_press:
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- platform: template
name: "${friendly_name} Volume Down"
id: btn_vol_down
publish_initial_state : True
on_press:
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
- platform: template
name: "${friendly_name} Set"
id: btn_set
publish_initial_state : True
- platform: template
name: "${friendly_name} Play"
id: btn_play
publish_initial_state : True
- platform: template
name: "${friendly_name} Mode"
id: btn_mode
publish_initial_state : True
- platform: template
name: "${friendly_name} Record"
id: btn_record
publish_initial_state : True
sensor:
- id: button_adc
platform: adc
internal: true
pin: 39
attenuation: auto
update_interval: 15ms
filters:
- median:
window_size: 5
send_every: 5
send_first_at: 1
- delta: 0.1
on_value_range:
- below: 0.55
then:
- binary_sensor.template.publish:
id: btn_vol_up
state: ON
- above: 0.65
below: 0.92
then:
- binary_sensor.template.publish:
id: btn_vol_down
state: ON
- above: 1.02
below: 1.33
then:
- binary_sensor.template.publish:
id: btn_set
state: ON
- above: 1.43
below: 1.77
then:
- binary_sensor.template.publish:
id: btn_play
state: ON
- above: 1.87
below: 2.15
then:
- binary_sensor.template.publish:
id: btn_mode
state: ON
- above: 2.25
below: 2.56
then:
- binary_sensor.template.publish:
id: btn_record
state: ON
- above: 2.8
then:
- binary_sensor.template.publish:
id: btn_vol_up
state: OFF
- binary_sensor.template.publish:
id: btn_vol_down
state: OFF
- binary_sensor.template.publish:
id: btn_set
state: OFF
- binary_sensor.template.publish:
id: btn_play
state: OFF
- binary_sensor.template.publish:
id: btn_mode
state: OFF
- binary_sensor.template.publish:
id: btn_record
state: OFF
# Wifi signal
- platform: wifi_signal
name: "${friendly_name} WiFi Signal"
update_interval: 60s
# Generic volume sensor was used so it can be used in the esp_adf_speaker to get volume into HA
- platform: template
id: generic_volume_sensor
internal: true
- platform: template
name: "${friendly_name} Volume"
accuracy_decimals: 0
id: scaled_volume_sensor
lambda: |-
// Scale the volume from 0-100 to 0-10
return id(generic_volume_sensor).state / 10.0;
1 « J'aime »
MattG
Juillet 18, 2024, 4:34
66
Yes, top !!
Il faut vraiment que je m’y remette ! (Entre temps grosse promo sur les dernier echos spots, du coup j’ai décidé d’y jeter un oeil en attendant d’avoir la même chose maison. Mais il va y avoir du boulot, c’est bien foutu leur truc…)
Hello !
Je passais par ici avec un faible espoir (j’avoue) de trouver un moyen de faire fonctionner mon ESP32 Korvo v1.1 sous ESPHOME avec HA et microwakeword.
Et bien grâce à @Krull56 ; c’est hose faite ! Énorme merci à toi
J’ai un peu joué avec le YAML fourni et j’ai essayé d’y apporter quelques modifications; je voulai vous en faire toutes et tous profiter afin qu’on arrive à quelque chose d’utilisable.
Chez moi; voici ce qui marche:
Microwakeword (je n’arrive à faire fonctionner que ‹ OK Nabu › pour l’instant)
wake word on_device (je n’ai pas testé via HA; mais ça doit certainement marcher aussi)
lecture d’un son quand un wakeword est détecté (cf mes modifs dans le YAML)
retour vocal de Piper suite à la commande; via le son du Korvo
gestion du volume en +/-
Ce qui marche pas:
Le son marche; mais il est très faible (j’utilise un mini haut parleur avec ampli intégré branché sur le jack). Sur d’autres machines (Raspberry, Respeaker Core v2) il fonctionne très bien avec un très bon volume.
Initialisation du volume au boot (en changeant « initial_value: ‹ 100 › » dans « id: speaker_volume »); le haut-parleur ne fonctionne plus du tout avec cette config
Dans mon implémentation; je détecte le wake word → puis je déclenche le son « bip » → puis je lance voice_assistant pour attendre la commande. Ça provoque un délai de ~1 seconde entre le « bip » et le moment où voice assistant est prêt à écouter la commande. Je suis preneur de suggestions pour améliorer ça
J’espère que ça aidera d’autres à avancer et si quelqu’un ici a une idée pour augmenter le volume; je suis preneur
Mon YAML:
substitutions:
name: korvosat2
friendly_name: korvosat2
voice_assist_idle_phase_id: "1"
voice_assist_listening_phase_id: "2"
voice_assist_thinking_phase_id: "3"
voice_assist_replying_phase_id: "4"
voice_assist_not_ready_phase_id: "10"
voice_assist_error_phase_id: "11"
voice_assist_muted_phase_id: "12"
esphome:
name: ${name}
friendly_name: ${friendly_name}
platformio_options:
board_build.flash_mode: dio
on_boot:
- priority: -100
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Fast Pulse
- delay: 1s
- wait_until:
condition:
wifi.connected:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Slow Pulse
- wait_until: api.connected
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 100%
effect: Pulse
- delay: 1s
- if:
condition:
lambda: return id(init_in_progress);
then:
- lambda: id(init_in_progress) = false;
- script.execute: reset_led
esp32:
board: esp-wrover-kit
framework:
type: esp-idf
version: recommended
sdkconfig_options:
CONFIG_IDF_TARGET_ESP32: y
CONFIG_ESPTOOLPY_FLASHMODE_QIO: y
CONFIG_ESPTOOLPY_FLASHFREQ_80M: y
CONFIG_ESPTOOLPY_FLASHSIZE_16MB: y
CONFIG_ESP32S3_DATA_CACHE_64KB: y
CONFIG_ESP32S3_DATA_CACHE_LINE_64B: y
CONFIG_PARTITION_TABLE_CUSTOM: y
CONFIG_PARTITION_TABLE_CUSTOM_FILENAME: "default_16MB.csv"
CONFIG_PARTITION_TABLE_FILENAME: "default_16MB.csv"
CONFIG_PARTITION_TABLE_OFFSET: "0x8000"
CONFIG_ESP32_DEFAULT_CPU_FREQ_240: y
CONFIG_ESP32_SPIRAM_SUPPORT: y
CONFIG_SPIRAM_SPEED_80M: y
CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT: y
CONFIG_I2S_ENABLE_DEBUG_LOG: y
CONFIG_AUDIO_BOARD_CUSTOM: y
components:
- name: esp32_korvo1_board
source: github://dwitgen/korvo_1@main
refresh: 0s
####new
file:
- id: timer_finished_wave_file
file: https://github.com/esphome/firmware/raw/main/voice-assistant/sounds/timer_finished.wav
external_components:
- source: github://dwitgen/esphome@main
components: [esp_adf]
refresh: 0s
####new
- source: github://jesserockz/esphome-components
components: [file]
refresh: 0s
# Enable logging
logger:
# Enable Home Assistant API
api:
encryption:
key: "2p0zexXOjHNwfkD222YYY1dF8Vsdg/fozQaJZJa9hk0="
services:
- service: volume_up
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- service: volume_down
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
wifi:
ssid: !secret wifi_ssid
password: !secret wifi_password
captive_portal:
web_server:
port: 80
output:
- platform: gpio
id: pa_ctrl
pin:
number: GPIO12
ignore_strapping_warning: true
esp_adf:
board: esp32korvo1
speaker:
- platform: esp_adf
id: external_speaker
microphone:
- platform: esp_adf
id: external_mic
micro_wake_word:
vad:
models:
- model: okay_nabu
- model: hey_jarvis
- model: alexa
on_wake_word_detected:
then:
####new
- voice_assistant.stop
- lambda: id(external_speaker).play(id(timer_finished_wave_file), sizeof(id(timer_finished_wave_file)));
- voice_assistant.start:
wake_word: !lambda return wake_word;
voice_assistant:
id: voice_asst
microphone: external_mic
speaker: external_speaker
noise_suppression_level: 2
auto_gain: 31dBFS
volume_multiplier: 6
on_listening:
- lambda: id(voice_assistant_phase) = ${voice_assist_listening_phase_id};
- script.execute: reset_led
on_stt_vad_end:
- lambda: id(voice_assistant_phase) = ${voice_assist_thinking_phase_id};
- script.execute: reset_led
on_tts_start:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 100%
brightness: 60%
effect: Working
on_stt_end:
- homeassistant.service:
service: media_player.play_media
data:
entity_id: media_player.mpd
media_content_id: !lambda return x;
media_content_type: music
announce: "true"
on_tts_stream_start:
- output.turn_on: pa_ctrl
- delay: 100ms
- lambda: id(voice_assistant_phase) = ${voice_assist_replying_phase_id};
- script.execute: reset_led
on_end:
- delay: 100ms
- wait_until:
not:
speaker.is_playing:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
- script.execute: reset_led
- if:
condition:
and:
- switch.is_off: mute
- lambda: return id(wake_word_engine_location).state == "On device";
then:
- wait_until:
not:
voice_assistant.is_running:
- micro_wake_word.start:
on_error:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_error_phase_id};
- script.execute: reset_led
- delay: 2s
- if:
condition:
switch.is_off: mute
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
else:
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- script.execute: reset_led
on_client_connected:
- if:
condition:
switch.is_off: mute
then:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.start
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
else:
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- lambda: id(init_in_progress) = false;
- script.execute: reset_led
on_client_disconnected:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.stop
- lambda: id(voice_assistant_phase) = ${voice_assist_not_ready_phase_id};
- script.execute: reset_led
script:
- id: reset_led
then:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_listening_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
brightness: 100%
effect: wakeword
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_thinking_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 0%
brightness: 100%
effect: Working
- delay: 100ms
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_replying_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 0%
green: 100%
brightness: 100%
effect: Working
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_idle_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 100%
red: 0%
green: 0%
brightness: 40%
effect: none
- delay: 200ms
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_not_ready_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 40%
red: 100%
green: 0%
effect: Slow Pulse
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_error_phase_id};
then:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
brightness: 100%
effect: none
- if:
condition:
lambda: return id(voice_assistant_phase) == ${voice_assist_muted_phase_id};
then:
- light.turn_off: led_ring
else:
- light.turn_on:
id: led_ring
blue: 0%
red: 100%
green: 0%
effect: Fast Pulse
light:
- platform: esp32_rmt_led_strip
id: led_ring
name: "${friendly_name} Light"
pin: GPIO33 #GPIO19
num_leds: 12
rmt_channel: 0
rgb_order: GRB
chipset: ws2812
default_transition_length: 0s
effects:
- pulse:
name: "Pulse"
transition_length: 300ms
update_interval: 300ms
min_brightness: 50%
max_brightness: 100%
- addressable_twinkle:
name: "Working"
twinkle_probability: 5%
progress_interval: 3ms
- addressable_color_wipe:
name: "Wakeword"
colors:
- red: 100%
green: 0%
blue: 0%
num_leds: 12
add_led_interval: 40ms
reverse: false
- pulse:
name: "Slow Pulse"
transition_length: 0.5s
update_interval: 1s
min_brightness: 0%
max_brightness: 100%
- pulse:
name: "Fast Pulse"
transition_length: 50ms
update_interval: 100ms
min_brightness: 50%
max_brightness: 100%
switch:
- platform: template
name: Mute
id: mute
optimistic: true
restore_mode: RESTORE_DEFAULT_OFF
entity_category: config
on_turn_off:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_assistant_phase) = ${voice_assist_idle_phase_id};
- if:
condition:
not:
- voice_assistant.is_running
then:
- if:
condition:
lambda: return id(wake_word_engine_location).state == "In Home Assistant";
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous
- if:
condition:
lambda: return id(wake_word_engine_location).state == "On device";
then:
- micro_wake_word.start
- script.execute: reset_led
on_turn_on:
- if:
condition:
lambda: return !id(init_in_progress);
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop
- micro_wake_word.stop
- lambda: id(voice_assistant_phase) = ${voice_assist_muted_phase_id};
- script.execute: reset_led
- platform: restart
name: "${name} Restart"
select:
- platform: template
entity_category: config
name: Wake word engine location
id: wake_word_engine_location
optimistic: true
restore_value: true
options:
- In Home Assistant
- On device
initial_option: On device
on_value:
- wait_until:
lambda: return id(voice_assistant_phase) == ${voice_assist_muted_phase_id} || id(voice_assistant_phase) == ${voice_assist_idle_phase_id};
- if:
condition:
lambda: return x == "In Home Assistant";
then:
- micro_wake_word.stop
- delay: 500ms
- if:
condition:
switch.is_off: mute
then:
- lambda: id(voice_asst).set_use_wake_word(true);
- voice_assistant.start_continuous:
- if:
condition:
lambda: return x == "On device";
then:
- lambda: id(voice_asst).set_use_wake_word(false);
- voice_assistant.stop
- delay: 500ms
- micro_wake_word.start
globals:
- id: init_in_progress
type: bool
restore_value: false
initial_value: "true"
- id: voice_assistant_phase
type: int
restore_value: false
initial_value: ${voice_assist_not_ready_phase_id}
- id: speaker_volume
type: int
restore_value: yes
initial_value: '50'
button:
- platform: template
name: "${friendly_name} Volume Up"
id: btn_volume_up
on_press:
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- platform: template
name: "${friendly_name} Volume Down"
id: btn_volume_down
on_press:
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
binary_sensor:
- platform: template
name: "${friendly_name} Volume Up"
id: btn_vol_up
publish_initial_state : True
on_press:
then:
- lambda: |-
if (id(speaker_volume) < 100) {
id(external_speaker).volume_up();
}
- platform: template
name: "${friendly_name} Volume Down"
id: btn_vol_down
publish_initial_state : True
on_press:
then:
- lambda: |-
if (id(speaker_volume) > 0) {
id(external_speaker).volume_down();
}
- platform: template
name: "${friendly_name} Set"
id: btn_set
publish_initial_state : True
- platform: template
name: "${friendly_name} Play"
id: btn_play
publish_initial_state : True
####new
on_press:
then:
- lambda: id(external_speaker).play(id(timer_finished_wave_file), sizeof(id(timer_finished_wave_file)));
- platform: template
name: "${friendly_name} Mode"
id: btn_mode
publish_initial_state : True
- platform: template
name: "${friendly_name} Record"
id: btn_record
publish_initial_state : True
sensor:
- id: button_adc
platform: adc
internal: true
pin: 39
attenuation: auto
update_interval: 15ms
filters:
- median:
window_size: 5
send_every: 5
send_first_at: 1
- delta: 0.1
on_value_range:
- below: 0.55
then:
- binary_sensor.template.publish:
id: btn_vol_up
state: ON
- above: 0.65
below: 0.92
then:
- binary_sensor.template.publish:
id: btn_vol_down
state: ON
- above: 1.02
below: 1.33
then:
- binary_sensor.template.publish:
id: btn_set
state: ON
- above: 1.43
below: 1.77
then:
- binary_sensor.template.publish:
id: btn_play
state: ON
- above: 1.87
below: 2.15
then:
- binary_sensor.template.publish:
id: btn_mode
state: ON
- above: 2.25
below: 2.56
then:
- binary_sensor.template.publish:
id: btn_record
state: ON
- above: 2.8
then:
- binary_sensor.template.publish:
id: btn_vol_up
state: OFF
- binary_sensor.template.publish:
id: btn_vol_down
state: OFF
- binary_sensor.template.publish:
id: btn_set
state: OFF
- binary_sensor.template.publish:
id: btn_play
state: OFF
- binary_sensor.template.publish:
id: btn_mode
state: OFF
- binary_sensor.template.publish:
id: btn_record
state: OFF
# Wifi signal
- platform: wifi_signal
name: "${friendly_name} WiFi Signal"
update_interval: 60s
# Generic volume sensor was used so it can be used in the esp_adf_speaker to get volume into HA
- platform: template
id: generic_volume_sensor
internal: true
- platform: template
name: "${friendly_name} Volume"
accuracy_decimals: 0
id: scaled_volume_sensor
lambda: |-
// Scale the volume from 0-100 to 0-10
return id(generic_volume_sensor).state / 10.0;
Bien à vous
2 « J'aime »
Krull56
Septembre 27, 2024, 10:30
68
Hello @jerome83136
Bienvenue dans la communauté
Effectivement, la sortie audio est très très capricieuse, impossible d’initialiser le volume correctement au boot et il faut faire plusieurs appui vol UP pour obtenir un volume correct ( et ne plus y toucher après).
Mais concernant la détection vocale, il est plutôt efficace.
J’attends une livraison d’un kit vocal sur base de respeaker lite, je ferai un petit retour sur ce fil.
D’autres kit sont prévus pour fin d’année, dont un de Nabu Casa ( et à regarder le code yaml en cours de dev, il va être pas mal du tout) .
@+
1 « J'aime »
eh bien merci a @Krull56 et @jerome83163
encore une petite question peux ton faire sortir le son sur une enceinte en wifi
j’ai cette bete https://raspiaudio.com/product/esp-muse-luxe/
elle fonctionne très bien via un serveur lms et picoreplayer en squeezelite
Merci
orionis
Décembre 18, 2024, 10:20
70
J’ai aussi ce message d’erreur en tentant de compiler
INFO ESPHome 2024.11.3
INFO Reading configuration /config/esphome/korvo-2.yaml...
INFO Updating https://github.com/dwitgen/esphome.git@main
INFO Updating https://github.com/jesserockz/esphome-components.git@None
INFO Generating C++ source...
INFO Cloning https://github.com/dwitgen/korvo_1.git@main
Traceback (most recent call last):
File "/usr/local/bin/esphome", line 8, in <module>
sys.exit(main())
^^^^^^
File "/esphome/esphome/__main__.py", line 1036, in main
return run_esphome(sys.argv)
^^^^^^^^^^^^^^^^^^^^^
File "/esphome/esphome/__main__.py", line 1023, in run_esphome
rc = POST_CONFIG_ACTIONS[args.command](args, config)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/esphome/esphome/__main__.py", line 503, in command_run
exit_code = write_cpp(config)
^^^^^^^^^^^^^^^^^
File "/esphome/esphome/__main__.py", line 213, in write_cpp
return write_cpp_file()
^^^^^^^^^^^^^^^^
File "/esphome/esphome/__main__.py", line 231, in write_cpp_file
writer.write_cpp(code_s)
File "/esphome/esphome/writer.py", line 341, in write_cpp
copy_src_tree()
File "/esphome/esphome/writer.py", line 307, in copy_src_tree
copy_files()
File "/esphome/esphome/components/esp32/__init__.py", line 716, in copy_files
repo_dir, _ = git.clone_or_update(
^^^^^^^^^^^^^^^^^^^^
File "/esphome/esphome/git.py", line 67, in clone_or_update
run_git_command(cmd)
File "/esphome/esphome/git.py", line 31, in run_git_command
raise cv.Invalid(lines[-1][len("fatal: ") :])
voluptuous.error.Invalid: could not read Username for 'https://github.com': No such device or address
merci de votre aide