Reputation: 11
I have an appliaction which asks the user questions which they should answer. The application uses pyttsx3 (version 2.9) to generate speech and I would like that while it speaks and only then, a gif animation would play for as long as it speaks. How can this be accomplished? For example:
import pyttsx3
engine = pyttsx3.init()
engine.say("I will speak this text")
engine.runAndWait()
And i want the gif animation to start running while runAndWait runs and stop when it stops
Upvotes: 0
Views: 119
Reputation: 2244
Ok I've found another program that works with the GIF images I have.
This program speaks for itself and displays a gif image.
I'm using tkinter
Text
object for output and a Label
to hold the image.
It should allow GIF animes to run but it requires specific information about the GIF.
This runs on windows 10 and pyttsx3 - 2.5
"""
Program outputs text while voice is speaking.
This program works on Python 2.6.14 and Python 3.7.3
"""
import tkinter as tk
from tkinter import filedialog as fido
import random, pyttsx3
class chatter:
terminate = False
def showText( self, m ):
"""talk.showText( m )"""
self.main.insert( "insert", m )
self.master.update( )
self.main.edit_separator( )
def Start( self, name ) ->"":
"""talk.Start( name )"""
self.sentence = name.split( )
def Use( self, name, location, length ) ->"":
"""talk.Use( name, location, length )"""
name = self.sentence.pop( 0 )
self.showText( f"{name} " )
def End( self, name, completed ) ->"":
"""talk.End( name, completed )"""
if len( self.sentence ) > 0:
while len( self.sentence ) > 0:
name = self.sentence.pop( 0 )
self.showText( f"{name}\n" )
else:
self.showText( "\n" )
def Error( self, name, exception ) ->"":
"""talk.Error( name, exception )"""
self.terminate = True
self.engine.stop( )
self.showText( f"\n{name}\n{exception}\n" )
def say( self, m ):
"""talk.say( m )"""
self.engine.say( m, m )
self.engine.runAndWait( )
def intro( self ):
for m in [
"This program works on Python 2.6 and Python 3",
"I am PYTTSX version 2.5" ]:
talk.say( m )
self.master.after( 100, self.imageUpdate, 0 )
def displayInCanvas( self ):
"""talk.displayInCanvas( )"""
self.image = fido.askopenfilename( title = 'Pick Gif' )
w, h = self.image.width() + 14, self.image.height() + 46
self.item = self.canvas.create_image( 2,2, anchor = "nw" )
self.canvas.itemconfig( self.item, image = self.image )
self.master.geometry( f"{w}x{h}" )
self.labelframe[ "text" ] = self.image
def getImage( self ):
"""talk.getImage( )"""
self.item = tk.Label( anchor = "nw" )
self.item.grid( row=0, column=1, sticky="nsew" )
self.image = fido.askopenfilename( title = 'Pick Gif' )
# This requires specific knowledge about the GIF image
# n = number of animation frames
# self.frame = [ tk.PhotoImage( master = self.master, file=self.image, format = 'gif -index %i' %( i ) ) for i in range( n ) ]
self.frame = [ tk.PhotoImage(
master = self.master, file = self.image, format = "gif -index 0" ) ]
self.item.configure( image = self.frame[ 0 ] )
def imageUpdate( self, ind ):
"""imageUpdate( ind )"""
frame = self.frame[ ind ]
ind += 1
print( ind )
# Will play gif infinitely
if ind > 0:
ind = 0
self.item.configure( image = frame )
self.master.after( 100, self.imageUpdate, ind )
def closer( self, ev = None ):
self.master.destroy( )
def __init__( self ):
"""talk.init"""
self.engine = pyttsx3.init( )
self.startUtter = self.engine.connect(
"started-utterance", self.Start )
self.wordsUtter = self.engine.connect(
"started-word", self.Use )
self.endsUtter = self.engine.connect(
"finished-utterance", self.End )
self.erraUtter = self.engine.connect(
"error", self.Error )
self.persona = self.engine.getProperty( "voices" )[~0].id
self.engine.setProperty( "voice", self.persona )
for a,b in [ ("rate", 150 ), ( "volume", 0.25 ) ]:
self.engine.setProperty( a,b )
self.engine.runAndWait( )
self.master = tk.Tk()
self.main = tk.Text(
self.master, undo =1, wrap = "word",
block = 1, width = 80, height = 25 )
self.main.grid( row = 0, column = 0, sticky = "nsew" )
self.master.bind( "<Escape>", self.closer )
self.showText( __doc__ + "\n" )
self.main.update_idletasks( )
self.getImage( ) # load and display gif
self.main.focus_set()
self.master.after( 100, self.intro )
if __name__ == "__main__":
talk = chatter( )
tk.mainloop()
Upvotes: 0