龙空技术网

Python让课本动起来,使用Pygame给英语课文配动画和配音

软核改造祝融叔 187

前言:

眼前姐妹们对“pythonpygame教程”都比较看重,咱们都需要了解一些“pythonpygame教程”的相关资讯。那么小编也在网络上网罗了一些关于“pythonpygame教程””的相关文章,希望兄弟们能喜欢,我们快快来了解一下吧!

写个这个文章是在教家里小朋友学习Python时,发现他们对于用Python演示他们的课文非常有兴趣,比如英语课文这一段

如果把这个对话文字显示并且AI语音合成读出来.而且他们也会很有兴趣制作新的课件.最终我用Pygame + Edge 语音合成完成这个程序.

项目的设计

语音合成采用 edge-tts ,这个是最接近于人类的发音,我专门介绍这个包,现在这个仍然进行发音,本来我想采用Pgzero这个Pygame简化版方便小朋友理解,但是测试后发现,pgzero本身已经封装一个无限循环,并且主线无法跟Python原生的协程配合,而edge接口就是采用 async机制,运行下来,只要读完语音才能显示图片,完全没法同步,因此最后只能直接采用Pygame这个机制的来实现.

Pygame 运行框架

pygame程度大体分为三大块

初始化 pygame.init()游戏主循环退出游戏 pygame.quit()

没有并发执行的情况下是,顺序执行,各种按键等通过事件处理方式在主循环里处理.

但是引用语音的协程后,在运行主循环时,要向云端申请语音合成并播放.因此要改造,把游戏主循环用asyncio库进行改造运行.

以下是核心代码

def main():             print("start")          #asyncio.get_event_loop().run_until_complete(edge_main())    asyncio.run(edge_main())        while True:        for ev in pygame.event.get():            if ev.type == pygame.QUIT:                return                        time.sleep(0.05)           if __name__ == "__main__":    game_init()      main()    pygame.quit()

注意这里 asyncio.run() 表示运行合成协程后就进行pygame的主循环了

完整代码

完整代码如下,你只要更新dialogues里的参数就能形成新的对话了

import asyncioimport pygameimport timeWIDTH = 500HEIGHT = 508FPS = 60import edge_ttsimport tempfilefrom playsound import playsound#对话列表dialogues =[      {"text":"Hello,I'm Amy.","x":60,"y":60},      {"text":"Hello,Amy.","x":300,"y":160}    ]defaultFont =  NonecurrentIndex  = 0screen = Nonesomeone = edge_tts.Communicate()#生成语音并播放async def say(text,x=0,y=0):     print(text)                   with tempfile.NamedTemporaryFile() as temporary_file:         print(temporary_file.name)         async for i in someone.run(text):            if i[2] is not None:                temporary_file.write(i[2])         playsound(temporary_file.name)              if x>0:       await drawText(text,x,y)     #在窗口上绘制文本async def drawText(text,x,y):         surface = defaultFont.render(text,False,(0,0,10))     screen.blit(surface,(x,y))     pygame.display.flip()     async def edge_main():    """    Main function    """            print("Start talking")        for item in dialogues:#       print(text)       #asyncio.ensure_future(say(text))       tasks = [asyncio.create_task(say(item["text"],item["x"],item["y"]))]       await asyncio.wait(tasks)       time.sleep(1)        def game_init():        pygame.init()                #print("获取系统中所有可用字体",pygame.font.get_fonts())        global screen    global defaultFont        defaultFont=pygame.font.SysFont('arialunicode',30)        screen = pygame.display.set_mode((WIDTH, HEIGHT))    pygame.display.set_caption("Module 1")    clock = pygame.time.Clock()    #clock.tick(FPS)              background = pygame.image.load("images/background.png")    screen.blit(background,(0,0))        pygame.display.flip()    time.sleep(0.2)             def main():             print("start")        #asyncio.get_event_loop().run_until_complete(edge_main())    asyncio.run(edge_main())        while True:        for ev in pygame.event.get():            if ev.type == pygame.QUIT:                return                        time.sleep(0.05)           if __name__ == "__main__":    game_init()      main()    pygame.quit()

这里有两个实现代码

一个say() 用于语音合成, drawText 调用pygame的显示机制来显示文字

好了,你们可以从英语教材截一个图片来制作新的课件吧!

标签: #pythonpygame教程