参考文档:语音合成(流式版)WebAPI 文档

微信小程序背景音频播报可参考:uniapp实现微信小程序websocket+背景音频语音播报

实现步骤

  1. 注册讯飞账号,完成实名认证,获取应用appid
  2. 连接讯飞websocket,在握手阶段,请求方需要对请求进行签名
  3. 发送请求文本,讯飞服务器返回合成后的音频片段,采用base64编码
  4. 将返回的音频片段组合,并转成可播放的MP3文件

1.注册账号,并获取应用appid

打开官网网址:讯飞开放平台-语音合成 点击免费试用,按步骤完成实名认证后得到appid

 2.连接讯飞websocket,在握手阶段,请求方需要对请求进行签名

async getWebsocketUrl() {// 合成讯飞语音请求地址const that = this;return await new Promise((resolve, reject) => {var apiKey = API_KEY; // 讯飞控制台查看var apiSecret = API_SECRET; // 讯飞控制台查看var url = 'wss://tts-api.xfyun.cn/v2/tts';var host = BASEURL; // 请求的主机地址var date = new Date().toGMTString();var algorithm = 'hmac-sha256';var headers = 'host date request-line';var signatureOrigin = `host: ${host}\ndate: ${date}\nGET /v2/tts HTTP/1.1`;var signatureSha = CryptoJS.HmacSHA256(signatureOrigin, apiSecret);var signature = CryptoJS.enc.Base64.stringify(signatureSha);var authorizationOrigin = `api_key="${apiKey}", algorithm="${algorithm}", headers="${headers}", signature="${signature}"`;var authorization = that.base64_encode(authorizationOrigin);url = `${url}?authorization=${authorization}&date=${date}&host=${host}`;resolve(url);});}async linkXunfeiSocket() {// 连接讯飞Socket服务器let url = await this.getWebsocketUrl();let XunfeiSocketTask;await new Promise((resolve, reject) => {XunfeiSocketTask = uni.connectSocket({url: encodeURI(url),header: {'content-type': 'application/json'},success: () => {console.log(`讯飞 connect成功`);resolve();},fail: () => {console.log('讯飞 connect失败');reject();}});});this.xunfeiSocketTask = XunfeiSocketTask;this.initXunFei(this.xunfeiSocketTask);}initXunFei(xunfeiSocketTask) {// 监听消息xunfeiSocketTask.onMessage(res => {// console.log('接收讯飞消息');this.result(res.data);});xunfeiSocketTask.onOpen(() => {// console.log('讯飞websocket打开');this.webSocketSend();});xunfeiSocketTask.onClose(res => {clearTimeout(this.playTimeout);// console.error('讯飞断开');});xunfeiSocketTask.onError(err => {// console.error('讯飞连接错误', err);});}

注意:

(1)signature_sha:hmac-sha256算法结合apiSecret对signature_origin签名,使用crypto-js实现

// 安装
npm install crypto-js
yarn add crypto-js// 引用
import CryptoJS from 'crypto-js';

(2)signature:需要使用CryptoJS.enc.Base64.stringify()方式编码后使用

(3)authorization:需要base64编码后使用,编码方式如下(等同于Window.btoa())

 base64_encode(str) {// 编码,配合encodeURIComponent使用var c1, c2, c3;var base64EncodeChars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=';var i = 0,len = str.length,strin = '';while (i < len) {c1 = str.charCodeAt(i++) & 0xff;if (i == len) {strin += base64EncodeChars.charAt(c1 >> 2);strin += base64EncodeChars.charAt((c1 & 0x3) << 4);strin += '==';break;}c2 = str.charCodeAt(i++);if (i == len) {strin += base64EncodeChars.charAt(c1 >> 2);strin += base64EncodeChars.charAt(((c1 & 0x3) << 4) | ((c2 & 0xf0) >> 4));strin += base64EncodeChars.charAt((c2 & 0xf) << 2);strin += '=';break;}c3 = str.charCodeAt(i++);strin += base64EncodeChars.charAt(c1 >> 2);strin += base64EncodeChars.charAt(((c1 & 0x3) << 4) | ((c2 & 0xf0) >> 4));strin += base64EncodeChars.charAt(((c2 & 0xf) << 2) | ((c3 & 0xc0) >> 6));strin += base64EncodeChars.charAt(c3 & 0x3f);}return strin;}

3.发送和接收数据

发送文本消息

webSocketSend() {let params = {common: {app_id: APPID // 讯飞控制台查看},business: {aue: 'lame', // 音频编码表示mp3格式,当aue=lame时需传参sfl=1sfl: 1,vcn: 'xiaoyan', // 发音人选择tte: 'UTF8'},data: {status: 2,text: CryptoJS.enc.Base64.stringify(CryptoJS.enc.Utf8.parse(this.toAudioText))}};this.xunfeiSocketTask.send({data: JSON.stringify(params),success: res => {// console.log('发出讯飞消息');},fail: err => {// console.log('发出讯飞消息失败', err);}});}

注意:

(1)发送的文本数据data的text需要使用base64编码

(2)send方法发送的数据需要转成json字符串

(3)返回的数据为合成后的音频片段,采用base64编码

 4. 将返回的音频片段组合,并转成可播放的MP3文件

当code为0,data.status为1时,表示合并中,将base64字符串合并

当code为0,data.status为2时,表示一句话合并完成,在此处将合并的base64转成音频文件

 result(resultData) {let jsonData = JSON.parse(resultData);//陆续合并接收的base64音频流 this.audioBase64 += jsonData.data.audio;if (jsonData.code !== 0) {// 合成失败console.log(`${jsonData.code}:${jsonData.message}`);return;}if (jsonData.code === 0 && jsonData.data.status === 2) {// 分段发送完成,转成语音文件关闭连接// 注意:将base64转化成ArrayBufferconst data = uni.base64ToArrayBuffer(this.audioBase64);const target = `${wx.env.USER_DATA_PATH}/${new Date().getTime()}.mp3`;try {// 使用fs.writeFileSync完成音频文件的转化const res = fs.writeFileSync(target, data, 'binary');this.playAudio.push(target);this.xunfeiSocketTask.close();this.audioBase64 = '';} catch (e) {console.error(e);}}}

注意:使用fs.writeFileSync转文件时,传入的data为ArrayBuffer格式

微信小程序实现讯飞语音合成相关推荐

  1. 微信小程序使用讯飞接口语音识别

    之前看过网上其他几位使用讯飞的接口来做微信小程序的.在自己实际跟着别人的博客做的时候,却又会遇到一些问题.所以在此对使用讯飞接口做一个总结.这里我是用WebAPI来做. 1. 申请科大讯飞的接口 科大 ...

  2. 微信小程序控制硬件 第14篇 微信小程序腾讯地图控制 4G Cat.1模组 ,安信可CA-01加载定位显示当前位置。

    文章目录 一.前言 通讯协议 技术问题点 二.4G模组业务逻辑 上报基站信息 三.微信小程序控制 另外,不要把我的博客作为学习标准,我的只是笔记,难有疏忽之处,如果有,请指出来,也欢迎留言哈! 微信物 ...

  3. 【中级】 微信小程序 - 腾讯云 - wafer2 - PHP - DEMO - 003 - 源码分析 - 01 - 文件组成详细分析

    1 前言: 本文原创,欢迎转载,但是,务必保持原文并且给出原文链接. 微信小程序 - 腾讯云 - PHP - DEMO 是微信提供的一个微信小程序和腾讯云小程序云服务wafer 进行接口的例子. 本仓 ...

  4. 微信小程序使用腾讯位置服务地图选点实现地址的选取|微信小程序腾讯位置服务地图选点请求来源未被授权

    效果图 首先要在微信开放平台的小程序里 添加插件 具体配置,可以参考官方文档 腾讯位置服务地图选点 | 小程序插件 | 微信公众平台 (qq.com) 同时还要申请接口的权限,不然小程序上线的时候不能 ...

  5. php qcloud sdk weapp_微信小程序腾讯云php后台解决方案

    微信小程序腾讯云php后台解决方案 微信小程序前段需要添加必要的文件以配合后端 (1)wafer2-client-sdk sdk提供了几种接口包括登陆,获取用户openid,图片上传等 (2)conf ...

  6. Mpvue+koa开发微信小程序——腾讯云开发环境的搭建及部署实现真机测试

    为什么写这篇文章? 之前写过一篇文章:微信小程序开发错误:LoginError {type: "ERR_WX_GET_USER_INFO"}解决方法 有的伙伴在这篇文章中评论为什么 ...

  7. 【中级】【后台】 微信小程序 - 腾讯云 - wafer2 - PHP - DEMO - 003 - 源码分析 - 03 - 腾讯后台初始化 和 CodeIgniter

    本文原创,欢迎转载,但是,务必保持原文并且给出原文链接. 前言: 本节对Wafer 服务端 SDK 是腾讯云为微信小程序开发者提供的快速开发库,SDK 封装了以下功能供小程序开发者快速调用的源码的初始 ...

  8. 【基础问题】微信小程序 - 腾讯云 - 一站式方案 - PHP - wafer 和 wafer2的区别和wafer2的实践

    前言: 项目目前选择了腾讯小程序一站式部署,反而有点懵了,服务器怎么配置呢?好像接口没有,查询后,发现有的Demo有服务器配置有的没有,折腾观察了一会,原来有两个版本wafer.我把关键的地方高亮了, ...

  9. 【非常基础实践】 微信小程序 - 腾讯云 - PHP - DEMO - 002 - 云环境搭建和开通指引- 实践

    前言: 微信小程序最快捷的方式应该还是利用腾讯云做后台,本文对开启微信小程序和腾讯云的绑定实践了一下. 包括安装,开通,开发环境配置,生产环境配置.很大一部分内容来自官网 1 注册微信小程序(官网贴图 ...

最新文章

  1. 轮盘赌算法的简单说明
  2. 「杂谈」白身,初识,不惑,有识,你处于深度学习哪一重境界了
  3. Docker aufs存储驱动layer、diff、mnt目录的区别
  4. 非常好的dllimport 文章--在 C# 中通过 P/Invoke 调用Win32 DLL
  5. 图片中的Build 2016
  6. 二、Java面向对象(7)_封装思想——访问修饰符
  7. Windows Mobile 系列文章索引---不断整理中(2009-07-08)
  8. 《转》15种CSS混合模式让图片产生令人惊艳的效果
  9. mysql longbolb_MySql基本数据类型及约束
  10. 7种常见的音频格式简析 MP3,WMA,WAV,APE,FLAC,OGG,AAC
  11. 数电电子时钟(555定时器,cd4518)
  12. 西湖论剑 easyCpp writeup
  13. BIM(biologically inspired model)小结
  14. firewalld防火墙(二)实验案例:ip地址伪装,端口转发
  15. c++ opencv 彩色图rgb 转换hsv 再通道分离
  16. 【小家Spring】Spring AOP各个组件概述与总结【Pointcut、Advice、Advisor、Advised、TargetSource、AdvisorChainFactory...】
  17. python语音合成并播放_语音合成篇
  18. S形曲线-斜坡指(S形加减速)
  19. 离散数学期末试题:打印笛卡尔积
  20. 企业级JAVA快速开发平台, 内置代码生成器 - JavaFast快速开发平台

热门文章

  1. r720支持多少频率的内存吗_二维码门禁你知道支持多少种识别方式吗?
  2. 112358序列c语言,112358(112358的规律是什么)
  3. SpringBoot总结(六)--连接oracle数据库demo
  4. CSDN 写文章报错:标题含有非法字符,请修改的解决方法
  5. 华夏千秋事,风雨亦为之
  6. JAVA - Stream - stream has already been operated upon or closed
  7. SDN入门:Ubuntu下SDN环境搭建(Floodlight+Minite)(踩坑教程,解决FL1.2版本无法访问网页问题)
  8. 苹果4s怎么越狱_iPhone 12系列细节曝光:苹果调整屏幕尺寸
  9. java计算机毕业设计无线通信基站监控及管理系统源码+系统+数据库+lw文档+mybatis+运行部署
  10. 自然资源部卫星遥感应用报告(更新至2020)