Tags

, , , , , , , , , , ,

‘Why so sad?’ I asked Arkwood. ‘Because I don’t have a girlfriend,’ he replied. Not to worry, I told him, I’ll soon knock you one up.

First, we need a way of talking to this girlfriend, and for that we will use the PiAUISuite software. Our speech_to_text function is supplied with a path to the PiAUISuite speech-recog.sh file, which it uses to process speech into text. Simply speak into a microphone attached to the Raspberry Pi and your voice will be turned into a string by the underlying Google API (https://www.google.com/speech-api/v1/recognize).

Great. Now, we’ve also got a text_to_speech function so that the girlfriend can talk back to him. For this we will use Google direct (http://translate.google.com/translate_tts), passing it his sweetheart’s text and receiving back an audio file, which is then broadcast through the speakers using MPlayer.

Here’s the Speech class containing the two functions…

from subprocess import Popen, PIPE, call
import urllib

class Speech(object):

    # converts speech to text
    def speech_to_text(self, filepath):
        try:
            # utilise PiAUISuite to turn speech into text
            text = Popen(['sudo', filepath], stdout=PIPE).communicate()[0]

            # tidy up text
            text = text.replace('"', '').strip()

            return text
        except:
            print ("Error translating speech")

    # converts text to speech
    def text_to_speech(self, text):
        try:
            # truncate text as google only allows 100 chars
            text = text[:100]

            # encode the text
            query = urllib.quote_plus(text)

            # build endpoint
            endpoint = "http://translate.google.com/translate_tts?tl=en&q=" + query

            # debug
            #print(endpoint)

            # get google to translate and mplayer to play
            call(["mplayer", endpoint], shell=False, stdout=PIPE, stderr=PIPE)
        except:
            print ("Error translating text")

Now that we have two-way communication in place, it is time for Arkwood to get down and dirty with his special lady. For this we will use the RasWIK Wireless Inventors Kit, which provides a button to press each time my buddy wants to whisper sweet nothings into her ear. Once Arkwood has said his piece, a file is opened and the word or phrase is searched for – if it is found then we grab the girlfriend’s corresponding response to play out through the sound system.

from raswik import Raswik
from speech import Speech
from time import sleep

# loop forever in romance
while True:

    # if button pressed...
    if(Raswik().is_button_pressed("a--D10READ--")):
       
        # ...speak to girlfriend
        my_smoothtalk = Speech().speech_to_text('/home/pi/PiAUISuite/VoiceCommand/speech-recog.sh')
        print(my_smoothtalk)   
        sleep(5)
        
        # get textbook
        book = {}
        with open("textbook.conf") as textbook:
            for line in textbook:
                me, her = line.partition("=")[::2]
                book[me.strip()] = her.strip()
        
        # now girlfriend speaks to Arkwood
        if my_smoothtalk in book:
            Speech().text_to_speech(book[my_smoothtalk])
        else:
            Speech().text_to_speech("What you say baby")

        sleep(5)

You can see from the screenshot that the Python program is recognising Arkwood’s voice, and then selecting the correct retort from his lover.

pi_girlfriend

Of course, we can really go to town with the textbook file, perhaps adding subcategories and artificial intelligence. But Arkwood ain’t too bothered for a smart lass.

By the way, did you notice the following line of code: book[me.strip()] = her.strip(). Hmm. Lovely nakedness.

And as way of completeness, here is the RasWIK code that checks for a button press to trigger the chat:

import serial
from time import sleep
 
# class to handle communication to
# raswik wirerless inventors kit
class Raswik(object):
 
    # com port and speed
    port = "/dev/ttyAMA0"
    baud = 9600
 
    #check if a button has been pressed
    def is_button_pressed(self, pin):
  
        #check pin param
        if(pin == ""):
            return False
 
        reply = ""
        try:
            # establish a serial connection
            ser = serial.Serial(port= self.port, baudrate= self.baud)           
 
            # wait a mo...
            sleep(0.2)
 
            # write to pin e.g. a--D10READ--
            ser.write(pin)
     
            # wait some more...
            sleep(0.2)
     
            # now read from pin
            reply = ser.read(12)
 
            # close serial connection
            ser.close()
        except:
            print ("Error detecting raswik button press")
            return False
 
        # grab the bit of the reply we care about
        message = reply[6:].strip('-')
 
        # return whether button is currently pressed down
        if(message == "LOW"):
            return True
        else:
            return False

The RasWIK button can be seen in the foreground, hooked into the breadboard:

raswik_girlfriend

So there you have it. A bidirectional conversation between a lonely, pathetic human being and a cold, soulless robot. As my Belgian friend said, ‘She’s no hassle’.

As a footnote, if you do get any trouble with audio on your Raspberry Pi, check out the following article:

http://www.raspberrypi-spy.co.uk/2013/06/raspberry-pi-command-line-audio/

Ciao!