The Raspberry Pi Powered Speaking Doorbell – Part 3: Text to Speech

In Part 1 we looked at a simple input circuit to isolate our Raspberry Pi from our doorbell circuit and in part 2 we looked at making a camera overlay appear in Kodi. Next, we’ll look at building the text to speech server.

Please note that the following blog post uses code snippets from my Github project. You will need to clone or download the full source code to run the examples.

With my home setup, I have a dedicated media PC in the lounge which runs Kodi on Windows. It is connected to a Yamaha receiver which is permanently on. The doorbell circuit, however, is connected to a Raspberry Pi. In my case, it makes sense to have the audio for text to speech play over the media PC. But how do we trigger text to speech on the media PC from the Raspberry Pi when someone presses the doorbell?

To solve this problem, I built a simple text to speech handler using the Tornado Web Server – this web server runs on the media PC in the lounge. When the doorbell switch is pressed, the Raspberry Pi simply performs an HTTP request to the text to speech server, which then outputs the given text as speech over the Yamaha receiver.


from lib import handler
import pyttsx

class TextToSpeechHandler(handler.Handler):
    def post(self):
        text = self.get_argument('text')

        engine = pyttsx.init()

        engine.setProperty('rate', self._registry['config'].getint(
                    'text_to_speech.rate'))

        engine.setProperty('volume', self._registry['config'].getfloat(
                    'text_to_speech.volume'))

        voices = engine.getProperty('voices')
        for voice in voices:
            if voice.id.lower().find(self._registry['config'].get(
                    'text_to_speech.voice').lower()) != -1:
                engine.setProperty('voice', voice.id)

        engine.say(text)
        engine.runAndWait()

We define a handler “TextToSpeechHandler” which accepts HTTP posts and will convert an argument called “text” to speech. The handler inherits from my base Handler class (which contains some functionality which is common to all my handlers), which in turn inherits from the standard Tornado handler.

For text to speech, we’ll use the pyttsx package. I have made 3 parameters configurable here – The rate, which is how fast the text is spoken, the volume, and the voice to use (it performs a partial text match on the voice configured). I have the following configuration set up:

#System finds first voice ID that contains the below text, case insensitive
text_to_speech.voice = Hazel

#Speed of speech. 100 is "normal" speed
text_to_speech.rate = 130

#Volume. 1.0 is full volume, 0.0 is no volume.
text_to_speech.volume = 1.0

An example script that performs an HTTP post to the text to speech server:

from lib.bootstrap import Bootstrap
import requests

bootstrap = Bootstrap('default', ['config', 'log'])
registry = bootstrap.bootstrap()

text_to_speech_hosts = registry["config"].get('text_to_speech.hosts')

text = 'There is a visitor at the front door.'

for host_and_port in text_to_speech_hosts:
    url = 'http://' + host_and_port  + '/text_to_speech'
    payload = {"text": text}
    requests.post(url, payload)

We define the text we want to convert to speech in the “text” variable. Then, for all text to speech servers that are configured, we perform an HTTP post with the text as a JSON encoded string.

In the next part, we’ll look at some other utility libraries before digging into the actual doorbell code.

The Raspberry Pi Powered Speaking Doorbell – Part 2: Kodi Camera Overlay

In Part 1, we looked at building a simple input circuit to electrically isolate and protect our Raspberry Pi from damage when connecting it to our doorbell switch. Next, we’ll look at displaying a camera overlay directly in Kodi / XBMC and triggering the display from a Python script.

IP cameras have become really cheap and easy to come by, giving us many options to integrate video into our home automation systems. The front door is a great place to install a camera!

ip

The Digital Lifestyle has a very good write up on how to install and configure an add-on to display the camera overlay (especially if you have more than one camera) directly in Kodi itself.

We can then use some Python code to trigger the add-on using Kodi’s API.

Prerequisites: In Kodi, make sure “Allow control of Kodi via HTTP” is set to ON in Settings -> Services -> Webserver.

I wrote a small XBMC / Kodi client to make it easier to make calls to the API. Here is the method for triggering an add-on:

    def execute_addon(self, addon_id):
        payload = self._get_payload("Addons.ExecuteAddon",
{'addonid': addon_id})
        self._do_post_request(payload)

And here is the code for instantiating the client and executing the add-on:


xbmc_client = xbmc.XbmcClient(host, port)
xbmc_client.execute_addon("script.frontdoorcam")

On line 1, we instantiate the XBMC client by specifying the host and port. The port is configured in Kodi’s Settings -> Services -> Webserver -> Port.

The only parameter we are passing to the execute_addon method is the ID of the add-on we wish to run. Set it to the add-on ID that you specified in the addon.xml file.

That’s it. Next, we’ll look at how to build a text to speech server using Tornado.

Syncing TomTom GPS watch activities to Discovery Vitality

Edit 2016-04-01 – As far as I know, Discovery have disabled integration with MapMyFitness and Strava for all new TomTom watches since April 1st, 2016. Existing TomTom watch users that had MapMyFitness or Strava integrations added on their Vitality profile before 1 April will still have their workouts synced with Vitality. Apparently, TomTom is busy working on a integration which will allow TomTom watch users to sync their workouts directly with Vitality. There should be a announcement from Discovery as soon as this integration goes live.


If you are a member of Discovery Health medical aid and use its Vitality service, it is possible to link your TomTom GPS watch (TomTom Runner, Cardio or Multisport watches) so that your activities are uploaded automatically to the Living Vitality exercise tracker.

81yJUz4CvML._SL1500_

The Vitality workout tracker uses MapMyFitness, which is an activity tracking website similar to Strava or Endomondo, to log any workouts added to the Vitality site. This means that if we can export our TomTom activities to the correct MapMyFitness account, it will appear automatically in the Vitality workout tracker. Luckily for us, TomTom has added the ability to export to MapMyFitness from the MySports Connect software, allowing us to automate the upload of activities to Vitality as well.

Note – Vitality creates a MapMyFitness account for you using an auto-generated username and password. If you already had a MapMyFitness account before starting to use Vitality to log workouts, it is important to know that Vitality will not use your existing account, even if your usernames and passwords are the same for Vitality and MapMyFitness.

So, let’s get started…

Step 1 – Head over to the Living Vitality website, click the “Login” button and log in to your vitality account

Step 2 – From the top-right navigation menu, hover your mouse cursor over the “Vitality” heading which should open up a very large navigation menu. Look for the “Your Profile” link under the “Vitality Community” subheading. If you can’t find it, use your browser’s built in search function (Press Ctrl and F together which opens the search dialog – now type “Profile” and click search). Click on the “Your Profile” link.

Step 3 – Scroll down until you see the section titled “Change your MapMyFitness password”. Look for the “Username” field – there should be a username filled in – save this username somewhere safe. (If you do not see this information, please see *disclaimer at the bottom of this post). Change the password now so that it is set to something that you can remember – enter the new password and confirm password fields and press “Update”.

Step 4 – Next, we need to configure TomTom’s MySports Connect software to upload any new activities to MapMyFitness. To do this you need to make sure your software is up to date – usually when your PC is started up, it pops up a notification if your software is out of date – as long as you have updated the software recently, you’ll be good to go. Make sure your watch is connected to the PC and open the MySports Connect application.

Step 5 – On the main application window, select “Settings” and click on the “Upload & Export” tab. Click on the “Add” button. Select “MapMyFitness” from the export options and click “Add”. This will open a browser window that will open the MapMyFitness website. Log in using the username obtained in Step 3 and the new password you entered on the Vitality site. If you were already logged in, make sure the account you are logged into is the same as the one configured in Vitality. Next, the site will ask you to confirm if you want to connect the TomTom MySports software – go ahead and confirm – you should be all set.

Step 6 – Once you have logged at least one workout and the MySports Connect software has finished uploading and exporting your activity, log into the Vitality website again (see step 1) to see that the workouts are being synced correctly. In the Vitality navigation menu, look for the “Workout tracker” link under the “Gym and Fitness” subheading and click it. Now scroll down until you see the graph – it should show your activities plotted for the last week.

If you had any trouble setting up the automatic syncing, please drop me a comment below and I’ll see if I can help out.

*Disclaimerif you do not see a MapMyFitness username on the Vitality website, or the option to change your MapMyFitness does not appear on the site, it is possible that it only creates the MapMyFitness account once you log at least one workout (You will have to have set your MySports Connect software to export to .FIT or .GPX files before so that you have something to upload). Upload a single workout to the Vitality workout tracker and see if the MapMyFitness account details appear. If so, please drop me a comment so I can amend this guide.

*Disclaimer 2 – I do not work for Discovery Health and am not affiliated with them in any way.