Advanced Sonos Say w/ question: how to save the original volume and restore it later?

Nobody likes being brutally interrupted by the TTS message when listening to the music, neither do I. So I wrote a script(with original idea borrowed from here) that pauses the music, announce the message and then resume the playing. The script in the above link does a good job with a little bit modification.

However, the problem with the script is that the music is always brutally interrupted. Therefore, I added a fade out effect using while loop before playing the TTS and it worked well.

The next problem is how to fade-in the volume when the play is resumed. The service being called to restore is sonos.restore which will set the volume immediately to its previous value. My plan is, after sonos.store, the volume is immediately set to 0, and then increased to its original value. This means I need a way to persist variable among the sequences, like this

  sequences:
    ...
    - service: sonos.restore
      data:
        entity_id: media_player.bedroom_speaker
    # Save the volume to a template variable? How?
    # Something like
    # {% set old_volume = states.media_player['bedroom_speaker'].attributes['volume_level'] %}

    # Mute the speaker
    - service: media_player.set_volume
      data:
        entity_id: media_player.bedroom_speaker
        volume_level: 0
    # Then increase the volume gradually to its **Previous Value**

For anyone who wants to try the version without face-in effect, here’s the YAML I came up with:

# > SONOS TTS
sonos_say:
  alias: "Sonos TTS script"
  fields:
    sonos_entity:
      description: "The eneity of the sonos"
      example: "bedroom_speaker"
      default: "bedroom_speaker"
    message:
      description: "The message content"
      example: "The light is on!"
      default: "Test message"
    volume:
      description: "The volume"
      example: "0.5"
      default: 0.5

  sequence:
    - service: sonos.snapshot
      data_template:
        entity_id: "{{ 'media_player.' ~ sonos_entity }}"
    # Lower the volume gradually
    - repeat:
        while: "{{ states.media_player[sonos_entity].attributes['volume_level'] > 0 }}"
        sequence:
          - service: media_player.volume_set
            data_template:
              entity_id: "{{ 'media_player.' ~ sonos_entity }}"
              volume_level: >
                {% set n = states.media_player[sonos_entity].attributes['volume_level'] %}
                {{(n - 0.05) if (n - 0.05) > 0 else 0}}
          - delay:
              milliseconds: 100
    - service: sonos.unjoin
      data_template:
        entity_id: "{{ 'media_player.' ~ sonos_entity }}"
    - service: media_player.volume_set
      data_template:
        entity_id: "{{ 'media_player.' ~ sonos_entity }}"
        volume_level: "{{ volume }}"
    - service: tts.google_say
      data_template:
        entity_id: "{{ 'media_player.' ~ sonos_entity }}"
        message: "{{ message }}"
    - delay: "00:00:01"
    - delay: >-
        {% set duration = states.media_player[sonos_entity].attributes.media_duration %}
        {% if duration > 0 %}
          {% set duration = duration - 1 %}
        {% endif %}
        {% set seconds = duration % 60 %}
        {% set minutes = (duration / 60)|int % 60 %}
        {% set hours = (duration / 3600)|int %}
        {{ [hours, minutes, seconds]|join(':') }}
    - delay: "00:00:05"
    - service: sonos.restore
      data_template:
        entity_id: "{{ 'media_player.' ~ sonos_entity }}"

1 Like