AI文本朗读应用(二)

news2024/11/17 15:57:32

调用api实现TTS

注:如对api的使用有任何疑问,可以查阅文本转语音 REST API。

  1. 选择右侧“解决方案资源管理器”中的“TTS_Demo”,右键选择“添加”->“新建项”。

    选择“类”,名称为“Authentication.cs”,点击“添加”。

  2. Authentication.cs 文件中,引用如下命名空间。

    using System.Net.Http;
    using System.IO;

    添加如下代码。

    namespace TTS_Demo
    {
        public class Authentication
        {
            private string subscriptionKey;
            private string tokenFetchUri;
    ​
            public Authentication(string tokenFetchUri, string subscriptionKey)
            {
                if (string.IsNullOrWhiteSpace(tokenFetchUri))
                {
                    throw new ArgumentNullException(nameof(tokenFetchUri));
                }
                if (string.IsNullOrWhiteSpace(subscriptionKey))
                {
                    throw new ArgumentNullException(nameof(subscriptionKey));
                }
                this.tokenFetchUri = tokenFetchUri;
                this.subscriptionKey = subscriptionKey;
            }
    ​
            public async Task<string> FetchTokenAsync()
            {
                using (var client = new HttpClient())
                {
                    client.DefaultRequestHeaders.Add("Ocp-Apim-Subscription-Key", this.subscriptionKey);
                    UriBuilder uriBuilder = new UriBuilder(this.tokenFetchUri);
    ​
                    var result = await client.PostAsync(uriBuilder.Uri.AbsoluteUri, null).ConfigureAwait(false);
                    return await result.Content.ReadAsStringAsync().ConfigureAwait(false);
                }
            }
    ​
        }
    }

  3. 同理,新建类文件 TTSApi.cs,并添加如下代码。

    namespace TTS_Demo
    {      
        class TTSApi
        {
            //语言配置信息
            string locale = "zh-CN";
            string voiceName = "Microsoft Server Speech Text to Speech Voice (zh-CN, HuihuiRUS)";
        
            string accessToken;
            Authentication auth = new Authentication("https://westus.api.cognitive.microsoft.com/sts/v1.0/issuetoken", "REPLACE_WITH_YOUR_KEY");
            string host = "https://westus.tts.speech.microsoft.com/cognitiveservices/v1";
    ​
            //转换文本并保存
            public async Task textToSpeechAsync(string text, string savePath)
            {
                try
                {
                    accessToken = await auth.FetchTokenAsync().ConfigureAwait(false);
                }
                catch (Exception ex)
                {
                    Console.WriteLine(ex);
                }
    ​
                string body = "<speak version='1.0' xmlns='https://www.w3.org/2001/10/synthesis' xml:lang='"+locale+"'>"
                +"<voice name='"+voiceName+"'>" + text + "</voice></speak>";
    ​
                using (var client = new HttpClient())
                {
                    using (var request = new HttpRequestMessage())
                    {
                        // Set the HTTP method
                        request.Method = HttpMethod.Post;
                        // Construct the URI
                        request.RequestUri = new Uri(host);
                        // Set the content type header
                        request.Content = new StringContent(body, Encoding.UTF8, "application/ssml+xml");
                        // Set additional header, such as Authorization and User-Agent
                        request.Headers.Add("Authorization", "Bearer " + accessToken);
                        request.Headers.Add("Connection", "Keep-Alive");
                        // Update your resource name
                        request.Headers.Add("User-Agent", "YOUR_RESOURCE_NAME");
                        request.Headers.Add("X-Microsoft-OutputFormat", "riff-24khz-16bit-mono-pcm");
                        // Create a request
                        Console.WriteLine("Calling the TTS service. Please wait... \n");
                        using (var response = await client.SendAsync(request).ConfigureAwait(false))
                        {
                            response.EnsureSuccessStatusCode();
                            // Asynchronously read the response
                            using (var dataStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false))
                            {
                                using (var fileStream = new FileStream(savePath, FileMode.Create, FileAccess.Write, FileShare.Write))
                                {
                                    await dataStream.CopyToAsync(fileStream).ConfigureAwait(false);
                                    fileStream.Close();
                                }
                            }
                        }
                    }
                }
            }
        }
    }

    其中,需要特别注意以下代码片段:

            string locale = "zh-CN";
            string voiceName = "Microsoft Server Speech Text to Speech Voice (zh-CN, HuihuiRUS)";
        
            string accessToken;
            Authentication auth = new Authentication("https://westus.api.cognitive.microsoft.com/sts/v1.0/issuetoken", "REPLACE_WITH_YOUR_KEY"); //替换为你的终结点和Key
            string host = "https://westus.tts.speech.microsoft.com/cognitiveservices/v1";

    • 上述的初始化中,需要替换你在TTS-api中分配的终结点和Key。Authentication

    • 上述的和允许用户更改不同的语言及发音。具体可选值可以查阅标准语音。locale``voiceName

      以中文为例,我们这里选择了“zh-CN”的“HuiHuiRUS”。 因此我们根据查表内容,将和变量设置成对应值。其中,可以选择“完全服务名称映射”或“短语音名称”。locale``voiceName``voiceName

  4. Form1.cs 中,添加如下代码至类。Form1

    string tempFile = "temp.wav"; //临时文件存储路径
    TTSApi tts = new TTSApi(); 

  5. Form1.cs[设计] 界面中双击“生成”按钮,会自动生成函数,该函数绑定了“生成”按钮的点击事件,当用户点击“生成”按钮时会自动调用该函数。transferButton_Click

    完成此函数代码。

    private async void transferButton_Click(object sender, EventArgs e)
        {
           string text = textBox1.Text; //获取用户输入
                
            if (text.Length > 0)
            {
                await tts.textToSpeechAsync(text, tempFile);        
            }
        }

  6. 同理,双击"播放"按钮,完成函数代码。playButton_Click

    private void playButton_Click(object sender, EventArgs e)
        {
            SoundPlayer playSound = new SoundPlayer(tempFile);
            playSound.Play();
        }

  7. 双击"保存"按钮,完成函数代码。saveButton_Click

    private void saveButton_Click(object sender, EventArgs e)
        {
            string filePath = "";
            //取前10个字符作为文件名
            string fileName = (textBox1.Text.Length < 10) ? textBox1.Text : textBox1.Text.Substring(0, 10);
    ​
            SaveFileDialog saveFile = new SaveFileDialog();
            saveFile.FileName = fileName;
            saveFile.Filter = "音频文件 (*.wav) | *.wav"; 
            saveFile.RestoreDirectory = true; //保存并显示上次打开的目录
    ​
            if (saveFile.ShowDialog() == DialogResult.OK)
            {
                filePath = saveFile.FileName.ToString(); 
    ​
                if (File.Exists(tempFile))
                {
                    File.Copy(tempFile, filePath, true);
                }
                else
                {
                    Console.WriteLine("音频文件不存在");
                }
            }
        }

至此,我们就构建好了整个窗体应用。按即可运行程序。F5

将待朗读的文章复制到文本框,点击"生成"按钮,等待片刻即可生成对应的语音,你可以直接保存生成的音频文件,以便自己使用或分享给家人朋友。

在教程中,我们省略了部分细节,更多内容可以查看源代码。

作业和挑战

1. 程序复现

按照上述的教程,复现一遍文本朗读的桌面应用程序,要求实现输入文本后能够生成语音并保存到本地。

2. 增加从文件读取文本信息的功能

当前的程序需要手动输入或复制内容到文本框,再点击"生成"。但是,当我们需要让计算机朗读长文章时,手动复制内容会十分地麻烦。那么,是否能增加一个功能,从文本文件中读取内容到文本框呢?

可参考如下交互方式来实现。

  1. 点击按钮"打开文件"

  2. 选择文本文件

    3.根据选择的文件自动加载

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1371955.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【漏洞复现】锐捷EG易网关cli.php后台命令执行漏洞

Nx01 产品简介 锐捷EG易网关是一款综合网关&#xff0c;由锐捷网络完全自主研发。它集成了先进的软硬件体系架构&#xff0c;配备了DPI深入分析引擎、行为分析/管理引擎&#xff0c;可以在保证网络出口高效转发的条件下&#xff0c;提供专业的流控功能、出色的URL过滤以及本地化…

14:00面试,14:07就出来了,问的问题有点变态。。。

前言 刚从小厂出来&#xff0c;没想到在另一家公司我又寄了。 在这家公司上班&#xff0c;每天都要加班&#xff0c;但看在钱给的比较多的份上&#xff0c;也就不太计较了。但万万没想到一纸通知&#xff0c;所有人不准加班了&#xff0c;不仅加班费没有了&#xff0c;薪资还…

Zustand 状态管理

Zustand 状态管理 安装创建 Store给 Store 添加TS类型约束在页面使用 Store返回 Store 中所有状态在 Store 中使用 async 异步方法使用 Immer Middleware (中间件) 更新深层嵌套的 State使用 get 方法&#xff0c;在 set 方法外访问 State 中的数据使用 selector什么是 selecto…

炫技作品!极好!独家原创!一种新型改进的蜣螂优化算法(CCCDBO)

炫技作品&#xff01;&#xff0c;独家原创&#xff01; 蜣螂优化算法DBO的含金量不用我多介绍了吧&#xff0c;这是和麻雀优化算法SSA同一个课题组出的算法&#xff0c;业内公认的比较好的算法&#xff0c;这个算法认可度很高&#xff01; 一种新型改进蜣螂优化算法&#xf…

【web缓存】nginx和CDN应用

目录 一、代理的工作机制 二、代理服务器的概念 三、代理服务器的作用 四、常用的代理服务器 五、nginx缓存代理部署 步骤一&#xff1a;首先脚本完成三台nginx的部署 步骤二&#xff1a;在两个后端原始服务器上分别创建测试页面 步骤三&#xff1a;完成nginx缓存服务器…

中央处理器CPU(2)---流水CPU与RISC

1.流水CPU &#xff08;一看到这个就想起老家的流水席了&#xff0c;不知道各位吃过没。&#xff09; &#x1f308;1.1并行处理技术 对于计算机来说不论如何发展&#xff0c;最重要的一个追求目标就是很高的运算速度&#xff0c;冯诺依曼机是&#xff0c;现代计算机依然是&…

高效实用的电商数据分析产品之店铺分析如何入手?

在电商行业&#xff0c;如何做好店铺分析&#xff1f;应该从哪几个方面进行&#xff1f; 1、寻找竞品店铺 在众多店铺中找到与自己风格&#xff08;定位/用户群体等&#xff09;相仿的相关竞争对手的标签。研究竞品店铺中爆款产品作为一个店铺运营&#xff08;新品开发等&…

HubSpot CRM:卓越客户服务的关键引擎

在数字化时代&#xff0c;提供卓越的客户服务是企业成功的关键之一。HubSpot CRM以其强大的功能和灵活性&#xff0c;成为实现卓越客户服务的关键引擎&#xff0c;以下是强调HubSpot CRM在客户服务中的应用的关键方面&#xff1a; 1. 全面的客户视图 HubSpot CRM集成了全面的…

解决:接口中返回的文本不能保持原本格式也无法换行

一、问题&#xff1a; 原本传入的文本是有换行的&#xff0c;但是用div展示接口返回的文本&#xff0c;所示内容没有保持原有格式没达到换行效果 以下是传入到接口的文本格式 使用div标签展示接口返回的文本&#xff0c;但并没有保持原有格式&#xff0c;文本也没换行 <di…

docker 容器添加指定网络地址

docker 容器添加指定网络地址 在搭建halo博客时&#xff0c;准备让 halo、mysql8.1、nginx 三个容器在同一个网段中&#xff0c;并指定IP。 实现docker内部容器之间网络互通。 查看容器网络信息命令 docker inspect 容器名各容器部署成功后网络效果如下&#xff1a; nginx …

城堡世界源码

随着数字技术的飞速发展和人们对于娱乐需求的不断提升&#xff0c;城堡世界源码开发逐渐成为了新的热门话题。城堡世界是一个集潮流、艺术、科技于一体的数字娱乐新领域&#xff0c;通过将虚拟现实、增强现实等技术融入传统玩具设计中&#xff0c;为玩家们带来了全新的互动体验…

如何高效阅读Linux的man page

有时候需要在man page中查某个命令的用法&#xff0c;我们一般会使用man command的方式来查询&#xff0c;例如man vmstat.但是对于一些bash内置的命令&#xff0c;如alias,如果使用man alias会打开General Commands Manual ,如下图 可以看到&#xff0c;内置命令很多&#xff…

计算机毕业设计---ssm实验室设备管理系统

项目介绍 ssm实验室设备管理系统。前台jsplayuieasyui等框架渲染数据、后台java语言搭配ssm(spring、springmvc、mybatis、maven) 数据库mysql8.0。该系统主要分三种角色&#xff1a;管理员、教师、学生。主要功能学校实验设备的借、还、修以及实验课程的发布等等&#xff1b;…

使用kennycason.kumo.WordCloud For JAVA 制作词云图

官网&#xff1a;https://kennycason.com/posts/2014-07-03-kumo-wordcloud.html 一&#xff1a;添加POM文件 <!-- 词云 --><dependency><groupId>com.kennycason</groupId><artifactId>kumo-core</artifactId><version>1.27<…

【Verilog】期末复习——分别画出下面两个程序综合后的电路图/reg型数据和wire型数据的区别

系列文章 数值&#xff08;整数&#xff0c;实数&#xff0c;字符串&#xff09;与数据类型&#xff08;wire、reg、mem、parameter&#xff09; 运算符 数据流建模 行为级建模 结构化建模 组合电路的设计和时序电路的设计 有限状态机的定义和分类 期末复习——数字逻辑电路分…

认识Linux指令之 “find grep” 命令

01.find指令&#xff1a; -name Linux下find命令在目录结构中搜索文件&#xff0c;并执行指定的操作。 Linux下find命令提供了相当多的查找条件&#xff0c;功能很强大。由于find具有强大的功能&#xff0c;所以它的选项也很多&#xff0c;其中大部分选项都值得我们花时间来…

LeetCode 84:柱状图中的最大矩形

一、题目描述 给定 n 个非负整数&#xff0c;用来表示柱状图中各个柱子的高度。每个柱子彼此相邻&#xff0c;且宽度为 1 。 求在该柱状图中&#xff0c;能够勾勒出来的矩形的最大面积。 示例 1: 输入&#xff1a;heights [2,1,5,6,2,3] 输出&#xff1a;10 解释&#xff1a…

智慧工地SaaS云平台源码:监管端、工地端、危大工程、智慧大屏、物联网、塔机、吊钩、升降机

智慧工地解决方案依托计算机技术、物联网、云计算、大数据、人工智能、VR&AR等技术相结合&#xff0c;为工程项目管理提供先进技术手段&#xff0c;构建工地现场智能监控和控制体系&#xff0c;弥补传统方法在监管中的缺陷&#xff0c;最终实现项目对人、机、料、法、环的全…

vue组件内外数据保持同步 组件数据加载解析顺序

背景与简介 一个公共的组件&#xff0c;比如BaseTable&#xff0c;需要同步组件内外部数据的同步&#xff0c;组件内部数据修改&#xff0c;组件外数据同步修改&#xff0c;组件外部数据修改&#xff0c;组件内部数据同步修改&#xff1b;同时&#xff0c;当组件内外部数据修改…

Java建筑工程建设智慧工地源码

智慧工地管理平台依托物联网、互联网&#xff0c;建立云端大数据管理平台&#xff0c;形成“端云大数据”的业务体系和新的管理模式&#xff0c;从施工现场源头抓起&#xff0c;最大程度的收集人员、安全、环境、材料等关键业务数据&#xff0c;打通从一线操作与远程监管的数据…