文字转拼音

安装 pinyin4js 三方库

ohpm install @ohos/pinyin4js

pinyin4js 提供了以下接口:

● 文字转拼音(带声调和不带声调)

● 文字转拼音首字母

● 简体繁体互转

let rawText = "风急天高猿萧哀,渚清沙白鸟飞回;"
let pinyin1: string =
pinyin4js.convertToPinyinString(rawText, " ", pinyin4js.WITH_TONE_MARK)
//fēng jí tiān gāo yuán xiāo āi , zhǔ qīng shā bái niǎo fēi huí ;
let pinyin2: string = pinyin4js.convertToPinyinString(rawText, " ", pinyin4js.WITHOUT_TONE)
//feng ji tian gao yuan xiao ai , zhu qing sha bai niao fei hui ;
let pinyinFirst: string = pinyin4js.getShortPinyin(rawText)
//fjtgyxa,zqsbnfh;
let sTot: string = pinyin4js.convertToTraditionalChinese(rawText)
//風急天高猿蕭哀,渚清沙白鳥飛回;
let tTos: string = pinyin4js.convertToSimplifiedChinese(sTot)
//风急天高猿萧哀,渚清沙白鸟飞回;

文字转语音

import { textToSpeech } from '@kit.CoreSpeechKit';

创建引擎

textToSpeech 提供 createEngine 方法来创建引擎

function createEngine(createEngineParams: CreateEngineParams): Promise<TextToSpeechEngine>;

CreateEngineParams 包含如下字段

● language:语种,当前仅支持“zh-CN”中文

● person:音色。0为聆小珊女声音色,当前仅支持聆小珊女声音色。

● online:模式。0为在线,目前不支持;1为离线,当前仅支持离线模式

● extraParams:扩展参数

其中 extraParams 扩展参数包含如下字段

● style :string 风格。可选,不设置时默认为“interaction-broadcast”,当前仅支持“interaction-broadcast”广播风格。

● locate:string 区域信息。可选,不设置时默认为“CN”

● name:string 引擎名称。可选,引擎名称,不设置时默认为空

● isBackStage:boolean 是否支持后台播报。默认不支持后台播报

let extraParams: Record<string, Object> = {
"style": 'interaction-broadcast',
"locate": 'CN',
"name": '',
"isBackStage": true
}
let paramsInfo: textToSpeech.CreateEngineParams = {
language: 'zh-CN',
person: 0,
online: 1,
extraParams: extraParams
}
textToSpeech.createEngine(paramsInfo).then((value) => {
this.ttsEngine = value
}).catch((err: BusinessError) => { })

文本播报

创建引擎后,通过调用引擎对象的 speak 方法进行文本播报

TextToSpeechEngine.speak(text: string, speakParams: SpeakParams): void;

● text:待播报的文本

● speakParams:合成播报音频的相关参数

speakParams 包含如下字段

● requestId:合成播报ID,全局不允许重复

● extraParams

○ speed:语速,可选,支持范围[0.5-2],不传参时默认为1

○ volume:音量,可选,支持范围[0-2],不传参时默认为1,

○ pitch:音调。可选,支持范围[0.5-2],不传参时默认为1,

○ languageContext:语境,播放阿拉伯数字用的语种。可选,当前仅支持“zh-CN”中文,默认“zh-CN”

○ audioType:音频类型。可选,当前仅支持“pcm”且为默认

○ playType:合成类型。0:仅合成不播报,返回音频流。1:合成与播报不返回音频流(默认)

○ soundChannel:播报通道,默认为3语音助手通道

○ queueMode:播报模式。可选,0:排队模式播报(默认)。1:抢占模式播报。

let extraParams: Record<string, Object> = {
"speed": 1,
"volume": 1,
"pitch": 1,
"languageContext": 'zh-CN',
"audioType": 'pcm',
"playType": 1,
"soundChannel": 3,
"queueMode": 1
}
let params: textToSpeech.SpeakParams = {
requestId: util.generateRandomUUID(),
extraParams: extraParams
}
this.ttsEngine?.speak(text, params)

停止播报

this.ttsEngine.stop()

状态监听

设置播报监听,可以收到开始,完成,暂停,播报信息,错误等状态回调

let listener: textToSpeech.SpeakListener = {
//播报开始时,回调此接口
onStart: (requestId: string, response: textToSpeech.StartResponse): void => { },
//合成或播报结束后分别回调此接口,CompleteResponse.type = 0:合成结束。1:播报结束。
onComplete: (requestId: string, response: textToSpeech.CompleteResponse): void => { },
//调用stop()方法时,回调此接口
onStop: (requestId: string, response: textToSpeech.StopResponse): void => { },
//合成播报过程中,出现错误时回调
onError: (requestId: string, errorCode: number, errorMessage: string): void => { },
//合成播报过程中回调此接口,返回请求ID,音频流信息,音频附加信息如格式、时长等
onData:(requestId: string, audio: ArrayBuffer, response: textToSpeech.SynthesisResponse) :void => { }
}
this.ttsEngine?.setListener(listener)

播报策略

● 单词播报方式:[hN] (N=0/1/2) 0-智能判断,1-逐个字母播报,2-单词播报 例如:hello[h1] world

● 数字播报策略:[nN] (N=0/1/2) 0-智能判断,1-逐个号码播报,2-作为数值播报 例如:[n2]123[n1]456[n0]

● 静音停顿:[pN] N为无符号整数,单位为ms,例如:你好[p500]小艺

● 指定汉字发音:[=MN] M表示拼音,N表示声调,1~5分别表示阴平、阳平、上声、去声和轻声5个声调。例如:着[=zhuo2]手

诗词拼音展示

创建拼音展示组件

此组件使用Column和Flex组件来实现,每个Flex组件为一个段落,Flex内容包含多个单个汉字和拼音。

@Component
struct PinyinView {
@Prop text: string
@Prop pinyin: string
private textArray: Array<string> = []
private pinyinArray: Array<Array<string>> = [] aboutToAppear(): void {
this.textArray = this.text.split("\n")
let pinyinRow = this.pinyin.split("\n")
for (let row of pinyinRow) {
this.pinyinArray.push(row.trim().split(" "))
}
} build() {
Column() {
ForEach(this.textArray, (item: string, rowIndex) => {
if (item) {
Flex({
direction: FlexDirection.Row,
wrap: FlexWrap.Wrap,
space: { cross: LengthMetrics.vp(8) }
}) {
ForEach(item.split(""), (item1: string, index) => {
this.WordView(item1, this.pinyinArray[rowIndex][index])
})
}.width('90%').margin({ top: rowIndex == 0 ? 0 : 8 })
} else {
Row().width('100%').height(22)
}
})
}
} @Builder
WordView(text: string, pinyin: string) {
Column() {
Text(pinyin)
.fontSize(12)
.fontColor(Theme.Color.textSecondary)
.padding({ top: 3, bottom: 3 })
.visibility(this.isHanZi(text) ? Visibility.Visible : Visibility.Hidden)
Text(text)
.fontSize(20)
.fontColor(Theme.Color.textPrimary)
.margin({ top: 3 })
}.width("12.5%")
} isHanZi(text: string) {
return text.charCodeAt(0) >= 0x4e00 && text.charCodeAt(0) <= 0x9fa5
}
}

诗词朗读

@ComponentV2
export struct PoetryDetailPage {
@Local soundPlayStatus: boolean = false
ttsEngine: textToSpeech.TextToSpeechEngine | null = null aboutToDisappear(): void {
if (this.ttsEngine) {
this.ttsEngine.stop()
this.ttsEngine.shutdown()
}
} initEngine(): Promise<void> {
return new Promise((resolve, reject) => {
if (this.ttsEngine == null) {
let extraParams: Record<string, Object> = {
"style": 'interaction-broadcast',
"locate": 'CN',
"name": '',
"isBackStage": true
}
let paramsInfo: textToSpeech.CreateEngineParams = {
language: 'zh-CN',
person: 0,
online: 1,
extraParams: extraParams
}
textToSpeech.createEngine(paramsInfo).then((value) => {
this.ttsEngine = value
resolve()
}).catch((err: BusinessError) => {
Toast.show(err.message)
reject()
})
} else {
resolve()
}
})
} speak() {
if (this.ttsEngine && this.ttsEngine.isBusy()) {
this.ttsEngine.stop()
return
}
this.initEngine().then(() => {
let listener: textToSpeech.SpeakListener = {
onStart: (requestId: string, response: textToSpeech.StartResponse): void => {
this.soundPlayStatus = true
},
onComplete: (requestId: string, response: textToSpeech.CompleteResponse): void => {
if (response.type == 1) {
this.soundPlayStatus = false
}
},
onStop: (requestId: string, response: textToSpeech.StopResponse): void => {
this.soundPlayStatus = false
},
onError: (requestId: string, errorCode: number, errorMessage: string): void => {
this.soundPlayStatus = false
}
}
this.ttsEngine?.setListener(listener)
let extraParams: Record<string, Object> = {
"speed": 1,
"volume": 1,
"pitch": 1,
"languageContext": 'zh-CN',
"audioType": 'pcm',
"playType": 1,
"soundChannel": 3,
"queueMode": 1
}
let params: textToSpeech.SpeakParams = {
requestId: util.generateRandomUUID(),
extraParams: extraParams
}
let speakText =
`${this.poetry?.title}[p200]
${this.poetry?.dynasty}[p50]${this.poetry?.author}[p200]
${this.poetry?.text}` this.ttsEngine?.speak(speakText, params)
})
}
}

本文的技术设计和实现都是基于作者工作中的经验总结,如有错误,请留言指正,谢谢。

HarmonyOS Next 入门实战 - 文字转拼音,文字转语音的更多相关文章

  1. javaScript对文字按照拼音排序

    <title>JavaScript对文字按照拼音排序</title> <SCRIPT type="text/javascript"> funct ...

  2. Atitit s2018.2 s2 doc list on home ntpc.docx  \Atiitt uke制度体系 法律 法规 规章 条例 国王诏书.docx \Atiitt 手写文字识别 讯飞科大 语音云.docx \Atitit 代码托管与虚拟主机.docx \Atitit 企业文化 每日心灵 鸡汤 值班 发布.docx \Atitit 几大研发体系对比 Stage-Gat

    Atitit s2018.2 s2 doc list on home ntpc.docx \Atiitt uke制度体系  法律 法规 规章 条例 国王诏书.docx \Atiitt 手写文字识别   ...

  3. 向大家介绍我的新书:《基于股票大数据分析的Python入门实战》

    我在公司里做了一段时间Python数据分析和机器学习的工作后,就尝试着写一本Python数据分析方面的书.正好去年有段时间股票题材比较火,就在清华出版社夏老师指导下构思了这本书.在这段特殊时期内,夏老 ...

  4. css图片+文字浮动(文字包围效果)

    css图片+文字浮动(文字包围效果): 在网页中,我们有时想实现这个效果,但是 <div id="test"> <img src="gdimages/0 ...

  5. Spark入门实战系列--10.分布式内存文件系统Tachyon介绍及安装部署

    [注]该系列文章以及使用到安装包/测试数据 可以在<倾情大奉送--Spark入门实战系列>获取 .Tachyon介绍 1.1 Tachyon简介 随着实时计算的需求日益增多,分布式内存计算 ...

  6. 003-Tuple、Array、Map与文件操作入门实战

    003-Tuple.Array.Map与文件操作入门实战 Tuple 各个元素可以类型不同 注意索引的方式 下标从1开始 灵活 Array 注意for循环的until用法 数组的索引方式 上面的for ...

  7. Scala深入浅出实战经典-----002Scala函数定义、流程控制、异常处理入门实战

    002-Scala函数定义.流程控制.异常处理入门实战 Scala函数定义 语句结束无分号 定义无参函数 def 函数名称(参数名称:参数类型)[:Unit=]{ 函数体 } 老师的代码 我的实际代码 ...

  8. Spark入门实战系列--1.Spark及其生态圈简介

    [注]该系列文章以及使用到安装包/测试数据 可以在<倾情大奉送--Spark入门实战系列>获取 .简介 1.1 Spark简介 年6月进入Apache成为孵化项目,8个月后成为Apache ...

  9. Spark入门实战系列--2.Spark编译与部署(上)--基础环境搭建

    [注] 1.该系列文章以及使用到安装包/测试数据 可以在<倾情大奉送--Spark入门实战系列>获取: 2.Spark编译与部署将以CentOS 64位操作系统为基础,主要是考虑到实际应用 ...

  10. Spark入门实战系列--2.Spark编译与部署(中)--Hadoop编译安装

    [注]该系列文章以及使用到安装包/测试数据 可以在<倾情大奉送--Spark入门实战系列>获取 .编译Hadooop 1.1 搭建环境 1.1.1 安装并设置maven 1. 下载mave ...

随机推荐

  1. PMP——如何区分赶工与快速跟进?

    如何区分赶工与快速跟进? 在PMP考试中经常出现由于时间不够需要进行进度压缩的场景.进度压缩的常用工具有赶工和快速跟进两种方式.也可以辅助调整某些活动的提前量与滞后量来进行缓解.提前量是相对于紧前活动 ...

  2. [TK] Rudolf and Subway ( CodeForces #933 div.3 - G )

    形式化题意 给定一个带权无向图,求从 \(s\) 点到 \(e\) 点的路径上途径边权种类的最小值. 思路 题图 我们把边权种类相同的点连成的子图抽象成一个 "平台" ,从题目给我 ...

  3. 【YashanDB知识库】如何dump数据文件,转换rowid, 查询对应内容

    本文来自YashanDB官网,具体内容可见https://www.yashandb.com/newsinfo/7459464.html?templateId=1718516 问题现象 客户环境有时候会 ...

  4. 【赵渝强老师】阿里云大数据ACP认证之阿里大数据产品体系

    阿里大数据产品体系是基于阿里云飞天平台上的数据处理服务.主要分为阿里云大数据基础产品和阿里云数加平台,其产品架构图如下所示: 一.阿里云大数据基础产品 1.云数据库--RDS(ApsaraDB for ...

  5. 高通dump ftrace & kernelshark使用

    简介 高通 ramdump 可以解析出 ftrace,方便用于追踪 快省稳 问题. kernelshark 是一个可以查看 trace event 的图形化工具,方便梳理和观察内核微观行为. trac ...

  6. Diffusion系列-预备知识I -(一)

    预备知识 范数 范数是一种函数,用来度量向量的大小1.在机器学习.信号处理等领域中,范数常常被用作正则化方法,通过对参数向量的范数进行约束,达到控制模型复杂度.防止过拟合等目的.常见的范数有0范数.1 ...

  7. day14-Scanner

    Scanner对象 之前我们学的基本语法中我们并没有实现程序和人的交互,但是Java给我们提供了这样一个工具类,我们可以获取用户的输入.Java.util.Scanner是Java5的新特征,我们可以 ...

  8. 基于云原生的私有化 PaaS 平台交付实践

    作者:牛玉富,某知名互联网公司专家工程师.喜欢开源 / 热衷分享,对 K8s 及 golang 网关有较深入研究. 本文将解读如何利用云原生解决私有化交付中的问题,进而打造一个 PaaS 平台,提升业 ...

  9. JS 本地存储 localStorage 操作总结

    现在前端做数据存储,跨页面传值,localStorage是一个很好的方式,以键值对的方式存储,也方便取值赋值,下面说一说使用方法和一些常见的使用技巧. 1.存值共有3种方式,localStorage相 ...

  10. 怎样替换 rhel 7.3 的 yum

    [背景] 想在自己安装的虚拟机上搭建一套 git+gitee+vscode 环境(欢迎看下期文章),发现python版本是2.7,这个版本太老 想通过yum进行更新,结果提示需要注册,索性就查查替换y ...