您的位置:首页 > 其它

集成讯飞SDK,实现离线命令词、离线语音合成、离线唤醒,语音在线/离线听写

2018-01-17 11:49 1331 查看

关于讯飞开发平台的注册以及SDK下载:

请参考:

http://blog.csdn.net/weixin_39923324/article/details/78924892


· 离线名命令词

· 离线语音合成

· 离线唤醒

· 语音在线听写

准备工作:

1、jar包

地址:https://pan.baidu.com/s/1hsanJBe

密码:523z

2、权限


<uses-permission android:name="android.permission.RECORD_AUDIO"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.CHANGE_NETWORK_STATE"/>
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.READ_CONTACTS"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_SETTINGS"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>


3.初始化引擎

我的appid已經沒有装机量,有些功能不能测试。


public void registerApp(Context context) {
StringBuffer param = new StringBuffer();
param.append("appid=5a4448f4");
param.append(",");
param.append(SpeechConstant.ENGINE_MODE + "=" + SpeechConstant.MODE_MSC);
SpeechUtility.createUtility(context, param.toString());
}


别忘了,在功能清单中申明Application 。


一、离线命令词

·Model层


离线命令的几个方法。

public interface IOcwBIZ {
/**
* 初始化
*
* @param initListener
*/
void createRecognizer(InitListener initListener);

/**
* 构件语法
*
* @param onBuildGrammar
*/
void localGrammar(OnBuildGrammar onBuildGrammar);
/**
* 开始识别
*
* @param onResultListener
* @param recognizerListener
*/
void onResult(OnResultListener onResultListener, RecognizerListener recognizerListener);

/**
* 销毁对象
*/
void destroyObj();


实现方法



@Override
public void createRecognizer(InitListener initListener) {
mAsr = SpeechRecognizer.createRecognizer(context, initListener);
}


@Override
public void localGrammar(final OnBuildGrammar onBuildGrammar) {
//读取本地文件,我的离线命令词在SD卡
String order = readOrderTxt(new File(SDCardUtils.getSDCardPath(), "order.hyco"));
if (TextUtils.isEmpty(order)) {
Log.e(TAG, "setParam: order 文件读取有误");
}
StringBuffer stringBuffer = new StringBuffer();
try {
JSONArray ja = new JSONArray(order);
for (int i = 0; i < ja.length(); i++) {
JSONObject jo = (JSONObject) ja.get(i);
stringBuffer.append("|").append(jo.getString("order"));
}
} catch (JSONException e) {
e.printStackTrace();
Log.e(TAG, "setParam: order 文件格式有误");
stringBuffer.append("|").append("西湖美景|塞外沙漠");
}
//采用bnf构建命令
StringBuffer sb = new StringBuffer();
sb.append("#BNF+IAT 1.0 UTF-8;\n")
.append("!grammar call;\n")
.append("!slot <single>;\n")
.append("!slot <zero>;\n")
.append("!start <callStart>;\n")
.append("<callStart>:")
.append("[<zero>][<zero>][<zero>][<zero>][<zero>][<zero>][<zero>][<zero>][<zero>]<zero>|<single>;\n")
.append("<zero>:").append(KEY_ZERO).append(";\n")
.append("<one>:").append(KEY_ZERO).append(";\n")
.append("<two>:").append(KEY_ZERO).append(";\n")
.append("<three>:").append(KEY_ZERO).append(";\n")
.append("<single>:").append(stringBuffer.toString().substring(1)).append(";\n");
if (null == mAsr) {
// TODO: 2017/12/29  请确认 libmsc.so 放置正确,且有调用 createUtility 进行初始化
onBuildGrammar.initFailure("创建对象失败。");
return;
}
mAsr.setParameter(SpeechConstant.PARAMS, null);
// 设置文本编码格式
mAsr.setParameter(SpeechConstant.TEXT_ENCODING, "utf-8");
// 设置引擎类型
mAsr.setParameter(SpeechConstant.ENGINE_TYPE, mEngineType);
// 设置语法构建路径
mAsr.setParameter(ResourceUtil.GRM_BUILD_PATH, grmPath);
mAsr.setParameter(ResourceUtil.ASR_RES_PATH, getResourcePath());
ret = mAsr.buildGrammar(GRAMMAR_TYPE_BNF, sb.toString(), new GrammarListener() {
@Override
public void onBuildFinish(String grammarId, SpeechError error) {
if (error == null) {
if (mEngineType.equals(SpeechConstant.TYPE_CLOUD)) {
SharedPreferences.Editor editor = mSharedPreferences.edit();
if (!TextUtils.isEmpty(grammarId))
editor.putString(KEY_GRAMMAR_ABNF_ID, grammarId);
editor.commit();
}
onBuildGrammar.buildGrammarSuccess("语法构建成功:" + grammarId);
} else {
onBuildGrammar.buildGrammarError("语法构建失败,错误码:" + error.getErrorCode());
}
}
});
if (ret != ErrorCode.SUCCESS) {
onBuildGrammar.buildGrammarError("语法构建失败,错误码:" + ret);
}
}


@Override
public void onResult(OnResultListener onResultListener, RecognizerListener recognizerListener) {
if (null == mAsr) {
// TODO: 2017/12/29  请确认 libmsc.so 放置正确,且有调用 createUtility 进行初始化
onResultListener.initFailure("创建对象失败。");
return;
}
// 设置参数
if (!setParam()) {
onResultListener.unBuildGrammar("语法未构建或构建失败");
return;
}
ret = mAsr.startListening(recognizerListener);
if (ret != ErrorCode.SUCCESS) {
onResultListener.notFindOrder("识别失败,错误码: " + ret);
}
}


@Override
public void destroyObj() {
if (null != mAsr) {
// 退出时释放连接
mAsr.cancel();
mAsr.destroy();
}
}


上述就是主要的核心方法,在onCreat()中调用初始化方法,在实现onClick()之前调用构建语法的方法,在onClick()s时调用开始识别的方法,退出界面时调用销毁的方法。


二、离线语音合成

这些方法可以酌情处理。

/**
* 初始化
*
* @param mTtsInitListener
* @return
*/
boolean createSynthesizer(InitListener mTtsInitListener);

/**
* 开始播放
*
* @param message
* @param mTtsListener
* @return
*/
int startSpeaking(String message, SynthesizerListener mTtsListener);

/**
* 取消播放
*/
void stopSpeaking();

/**
* 暂停播放
*/
void pauseSpeaking();

/**
* 继续播放
*/
void resumeSpeaking();

/**
* 销毁对象
*/
void destroyObj();


初始化

@Override
public boolean createSynthesizer(InitListener mTtsInitListener) {
// 初始化合成对象
mTts = SpeechSynthesizer.createSynthesizer(context, mTtsInitListener);
return mTts != null;
}


开始播放

@Override
public int startSpeaking(String message, SynthesizerListener mTtsListener) {
setParam();
int code = mTts.startSpeaking(message, mTtsListener);
return code;
}


取消播放

@Override
public void stopSpeaking() {
mTts.stopSpeaking();
}


暂停播放

@Override
public void pauseSpeaking() {
mTts.pauseSpeaking();
}


继续播放

@Override
public void resumeSpeaking() {
mTts.resumeSpeaking();
}


销毁对象

@Override
public void destroyObj() {
if (null != mTts) {
mTts.stopSpeaking();
// 退出时释放连接
mTts.destroy();
}
}


暂停播放和继续播放俩个方法,可以视情况取消,不影响操作。当然也可以读取本地的文件,这样就实现了小说朗读功能了。也可以做成服务,实现听书功能。

三、离线唤醒

离线唤醒,就是当手机处于待机黑屏状态,还能接受到特定的语音.

目前我的唤醒词为:

1.启动语音

2.八戒醒来

3.开机开机

4.来客人了

5.浩创科技

上代码:

public interface IWakeBIZ {
/**
* 初始化
*
* @return
*/
boolean createWakeUp();

/**
* 开启唤醒
*
* @param mWakeuperListener
* @param onInit
*/
void startWakeUp(WakeuperListener mWakeuperListener, OnInit onInit);

/**
* 停止唤醒
*/
void stopWakeUp();

/**
* 销毁对象
*/
void destroyObj();

}


//初始化
@Override
public boolean createWakeUp() {
mIvw = VoiceWakeuper.createWakeuper(context, null);
return null != mIvw;
}
//启动唤醒
@Override
public void startWakeUp(WakeuperListener mWakeuperListener, OnInit onInit) {
//非空判断,防止因空指针使程序崩溃
mIvw = VoiceWakeuper.getWakeuper();
if (mIvw != null) {
// 清空参数
mIvw.setParameter(SpeechConstant.PARAMS, null);
// 唤醒门限值,根据资源携带的唤醒词个数按照“id:门限;id:门限”的格式传入
mIvw.setParameter(SpeechConstant.IVW_THRESHOLD, "0:" + curThresh);
// 设置唤醒模式
mIvw.setParameter(SpeechConstant.IVW_SST, "wakeup");
// 设置持续进行唤醒
mIvw.setParameter(SpeechConstant.KEEP_ALIVE, keep_alive);
// 设置闭环优化网络模式
mIvw.setParameter(SpeechConstant.IVW_NET_MODE, ivwNetMode);
// 设置唤醒资源路径
mIvw.setParameter(SpeechConstant.IVW_RES_PATH, getResource());
// 设置唤醒录音保存路径,保存最近一分钟的音频
mIvw.setParameter(SpeechConstant.IVW_AUDIO_PATH, Environment.getExternalStorageDirectory().getPath() + "/hyco/ivw.wav");
mIvw.setParameter(SpeechConstant.AUDIO_FORMAT, "wav");
// 如有需要,设置 NOTIFY_RECORD_DATA 以实时通过 onEvent 返回录音音频流字节
//mIvw.setParameter( SpeechConstant.NOTIFY_RECORD_DATA, "1" );
// 启动唤醒
mIvw.startListening(mWakeuperListener);
} else {
onInit.InitError("初始化唤醒对象失败");
}

}

//停止唤醒
@Override
public void stopWakeUp() {
mIvw.stopListening();
}
//销毁对象
@Override
public void destroyObj() {
mIvw = VoiceWakeuper.getWakeuper();
if (mIvw != null) {
mIvw.destroy();
}
}


三、语音在线听写

讯飞很早以前关闭了离线语音听写,但是使用以前的jar可以实现离线听写功能。

但是二者不可混淆:

离线语音demo下载:http://download.csdn.net/download/weixin_39923324/10209576

言归正传,还是说在线听写:


public interface IRecBIZ {
/**
* 初始化
*
* @param mTtsInitListener
* @return
*/
boolean createRec(InitListener mTtsInitListener);

/**
* 开始听写
*
* @param mRecognizerListener
* @return
*/
int startSpeaking(RecognizerListener mRecognizerListener);

/**
* 停止听写
*/
void stopSpeaking();

/**
* 取消听写
*/
void cancelSpeaking();

/**
* 销毁对象
*/
void destroyObj();
}


@Override
public boolean createRec(InitListener mTtsInitListener) {
mIat = SpeechRecognizer.createRecognizer(context, mTtsInitListener);
return mIat != null;
}

@Override
public int startSpeaking(RecognizerListener mRecognizerListener) {
setParam();
return mIat.startListening(mRecognizerListener);
}

@Override
public void stopSpeaking() {
mIat.stopListening();
}

@Override
public void cancelSpeaking() {
mIat.cancel();
}

@Override
public void destroyObj() {
if (null != mIat) {
// 退出时释放连接
mIat.cancel();
mIat.destroy();
}
}


想象一下,自己的手机由自己所写的语音控制,那成就感有多么棒。

DEMO:http://download.csdn.net/download/weixin_39923324/10209490

转注注明出处。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐