效果图:

参考资料

http://blog.csdn.net/imhxl/article/details/50854146

项目里要用语音听写,想到了科大讯飞,参考上面的资料完成了最简单的在线有UI的语音识别,后面想要改成离线也可以使用。参考下面的文章

http://blog.csdn.net/q4878802/article/details/47834601

下载好语记和离线资源之后,想要改成有UI的RecognizerDialog离线语音听写,但是没成功,试了一下没有UI的SpeechRecognizer,发现可以,只需在设置参数的时候加上一句

recognizer.setParameter(SpeechConstant.ENGINE_TYPE,SpeechConstant.TYPE_LOCAL);//调用语记接口

就可以使用了。可能是RecognizerDialog带有UI界面,已经默认写成在线的了吧
下面只贴出主活动的代码,其他参考上面的资料

package com.example.administrator.voicerecognition;

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.Toast;

import com.iflytek.cloud.ErrorCode;
import com.iflytek.cloud.InitListener;
import com.iflytek.cloud.RecognizerListener;
import com.iflytek.cloud.RecognizerResult;
import com.iflytek.cloud.SpeechConstant;
import com.iflytek.cloud.SpeechError;
import com.iflytek.cloud.SpeechRecognizer;
import com.iflytek.cloud.SpeechUtility;
import com.iflytek.cloud.ui.RecognizerDialog;
import com.iflytek.cloud.ui.RecognizerDialogListener;

public class MainActivity extends AppCompatActivity {
private Button btn_voiceRec,btn_voiceRecOffline;
private RecognizerDialog iatDialog=null;
private SpeechRecognizer recognizer=null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
SpeechUtility.createUtility(this, "appid=xxx");//替换为实际的appid
btn_voiceRec = (Button) findViewById(R.id.btn_voiceRec);
btn_voiceRec.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (iatDialog!=null){
iatDialog.cancel();
iatDialog.destroy();
}
startDialogOnline();
}
});
btn_voiceRecOffline= (Button) findViewById(R.id.btn_voiceRecOffline);
btn_voiceRecOffline.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
// if (recognizer!=null){
// recognizer.cancel();
// recognizer.destroy();
// }
startNoDialogOffline();
}
});
}

/**
* 初始化监听器。
*/

private InitListener mInitListener = new InitListener() {

@Override
public void onInit(int code) {
Log.d("tag", "SpeechRecognizer init() code = " + code);
if (code != ErrorCode.SUCCESS) {
Log.d("tag", "初始化失败,错误码:" + code);
}
}
};

public void startDialogOnline() {
//1.创建SpeechRecognizer对象,第二个参数:本地听写时传InitListener
iatDialog = new RecognizerDialog(this, mInitListener);
//2.设置听写参数

iatDialog.setParameter(SpeechConstant.LANGUAGE, "zh_cn");
iatDialog.setParameter(SpeechConstant.ACCENT, "mandarin ");


//3.设置回调接口
iatDialog.setListener(new RecognizerDialogListener() {
@Override
public void onResult(RecognizerResult recognizerResult, boolean b) {
if (!b) {
String json = recognizerResult.getResultString();
String str = JsonParser.parseIatResult(json);
Toast.makeText(MainActivity.this, str, Toast.LENGTH_SHORT).show();
}
}

@Override
public void onError(SpeechError speechError) {
Log.d("error", speechError.toString());
}
});
//4.开始听写
iatDialog.show();
}


private void startNoDialogOffline(){
//1.创建SpeechRecognizer对象,第二个参数:本地听写时传InitListener
recognizer = SpeechRecognizer.createRecognizer(this,null);
//2.设置听写参数

recognizer.setParameter(SpeechConstant.ENGINE_TYPE,SpeechConstant.TYPE_LOCAL);//调用语记接口


recognizer.setParameter(SpeechConstant.DOMAIN, "iat");//参数设为语音听写
recognizer.setParameter(SpeechConstant.LANGUAGE, "zh_cn");//中文
recognizer.setParameter(SpeechConstant.ACCENT, "mandarin ");//普通话

//3.设置回调接口
recognizer.startListening(new RecognizerListener() {
@Override
public void onVolumeChanged(int i, byte[] bytes) {

}

@Override
public void onBeginOfSpeech() {

}

@Override
public void onEndOfSpeech() {

}

@Override
public void onResult(RecognizerResult recognizerResult, boolean isLast) {
if (isLast) {
String json = recognizerResult.getResultString();
String str = JsonParser.parseIatResult(json);
Log.d("tag",str);
Toast.makeText(MainActivity.this, str, Toast.LENGTH_SHORT).show();
}
}

@Override
public void onError(SpeechError speechError) {
Log.d("error", speechError.toString());
}

@Override
public void onEvent(int i, int i1, int i2, Bundle bundle) {

}
});
}
}

—————————————————————————————————

2016.11.2更新

离线语音做了个简单的UI,效果如图:

完整代码如下,改动部分已注释:

package com.example.administrator.voicerecognition;

import android.app.ProgressDialog;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.Window;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.Toast;

import com.iflytek.cloud.ErrorCode;
import com.iflytek.cloud.InitListener;
import com.iflytek.cloud.RecognizerListener;
import com.iflytek.cloud.RecognizerResult;
import com.iflytek.cloud.SpeechConstant;
import com.iflytek.cloud.SpeechError;
import com.iflytek.cloud.SpeechRecognizer;
import com.iflytek.cloud.SpeechUtility;
import com.iflytek.cloud.ui.RecognizerDialog;
import com.iflytek.cloud.ui.RecognizerDialogListener;

public class MainActivity extends AppCompatActivity {
private Button btn_voiceRec,btn_voiceRecOffline;
private RecognizerDialog iatDialog=null;
private SpeechRecognizer recognizer=null;
//新增对话框和语音听写完成标志------------------
private ProgressDialog pDialog=null;
private boolean isFinish=false;
//-----------------------------------
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
SpeechUtility.createUtility(this, "appid=xxx");//替换为实际的appid
btn_voiceRec = (Button) findViewById(R.id.btn_voiceRec);
btn_voiceRec.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (iatDialog!=null){
iatDialog.cancel();
iatDialog.destroy();
}
startDialogOnline();
}
});
btn_voiceRecOffline= (Button) findViewById(R.id.btn_voiceRecOffline);
btn_voiceRecOffline.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
// if (recognizer!=null){
// recognizer.cancel();
// recognizer.destroy();
// }
startNoDialogOffline();
//显示对话框----------------
showProgressDialog();
//----------------------
}
});
}

//对话框显示方法-----------------------------------
private void showProgressDialog() {
pDialog = new ProgressDialog(MainActivity.this);

pDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
pDialog.setProgress(100);
pDialog.setMessage("请稍等...");
pDialog.setIndeterminate(false);
pDialog.show();

WindowManager.LayoutParams lp = pDialog.getWindow().getAttributes();
lp.gravity = Gravity.CENTER;
Window win = pDialog.getWindow();
win.setAttributes(lp);

new Thread(new Runnable() {

@Override
public void run() {
//long startTime = System.currentTimeMillis();
int progress = 0;

//while (System.currentTimeMillis() - startTime < 1000) {
//语音听写完成后,释放对话框
while (!isFinish) {
try {
progress += 10;
pDialog.setProgress(progress);
Thread.sleep(100);
} catch (InterruptedException e) {
pDialog.dismiss();
}
}

pDialog.dismiss();
isFinish=false;
}
}).start();
}
//--------------------------------------------------------

/**
* 初始化监听器。
*/

private InitListener mInitListener = new InitListener() {

@Override
public void onInit(int code) {
Log.d("tag", "SpeechRecognizer init() code = " + code);
if (code != ErrorCode.SUCCESS) {
Log.d("tag", "初始化失败,错误码:" + code);
}
}
};

public void startDialogOnline() {
//1.创建SpeechRecognizer对象,第二个参数:本地听写时传InitListener
iatDialog = new RecognizerDialog(this, mInitListener);
//2.设置听写参数

iatDialog.setParameter(SpeechConstant.LANGUAGE, "zh_cn");
iatDialog.setParameter(SpeechConstant.ACCENT, "mandarin ");


//3.设置回调接口
iatDialog.setListener(new RecognizerDialogListener() {
@Override
public void onResult(RecognizerResult recognizerResult, boolean isLast) {
if (!isLast) {
String json = recognizerResult.getResultString();
String str = JsonParser.parseIatResult(json);
Toast.makeText(MainActivity.this, str, Toast.LENGTH_SHORT).show();
}
}

@Override
public void onError(SpeechError speechError) {
Log.d("error", speechError.toString());
}
});
//4.开始听写
iatDialog.show();
}


private void startNoDialogOffline(){
//1.创建SpeechRecognizer对象,第二个参数:本地听写时传InitListener
recognizer = SpeechRecognizer.createRecognizer(this,null);
//2.设置听写参数

recognizer.setParameter(SpeechConstant.ENGINE_TYPE,SpeechConstant.TYPE_LOCAL);//调用语记接口


recognizer.setParameter(SpeechConstant.DOMAIN, "iat");//参数设为语音听写
recognizer.setParameter(SpeechConstant.LANGUAGE, "zh_cn");//中文
recognizer.setParameter(SpeechConstant.ACCENT, "mandarin ");//普通话

//3.设置回调接口
recognizer.startListening(new RecognizerListener() {
@Override
public void onVolumeChanged(int i, byte[] bytes) {

}

@Override
public void onBeginOfSpeech() {

}

@Override
public void onEndOfSpeech() {

}

@Override
public void onResult(RecognizerResult recognizerResult, boolean isLast) {
if (isLast) {
String json = recognizerResult.getResultString();
String str = JsonParser.parseIatResult(json);
Log.d("tag",str);
Toast.makeText(MainActivity.this, str, Toast.LENGTH_SHORT).show();
//语音听写完成标志---------------------------
isFinish=true;
//------------------------------------------
}
}

@Override
public void onError(SpeechError speechError) {
Log.d("error", speechError.toString());
}

@Override
public void onEvent(int i, int i1, int i2, Bundle bundle) {

}
});
}
}

注:经过多次测试后发现,第一次点击按钮离线语音听写无法识别,第二次点击按钮才可正常实现听写,之后都可以正常听写,这个bug目前还没有解决

—————————————————————————————————

2016.11.6 更新

第一次离线语音听写无反应bug的解决办法:在onCreat()里先执行一次,不显示UI,这样再点击就是第二次了。。。虽然很蠢,但是功能上算是实现了,后面有时间再仔细想想更好的办法

protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
SpeechUtility.createUtility(this, "appid=xxx");//替换为实际的appid
btn_voiceRec = (Button) findViewById(R.id.btn_voiceRec);
btn_voiceRec.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
startDialogOnline();
}
});
btn_voiceRecOffline = (Button) findViewById(R.id.btn_voiceRecOffline);
//先听写一次----------------------------
startNoDialogOffline();
//------------------------------------
btn_voiceRecOffline.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
startNoDialogOffline();
showProgressDialog();
}
});
}

注:调试过程中又发现,在单独使用在线的情况下,在线的RecognizerDialogListener的onResult()会调用两次,输出两个str,第一个是听写内容,第二个是标点符号。如果是if (!isLast),那么输出的是听写内容,如果是if (isLast),输出的是标点符号。很显然,需要的是听写内容,这时要用if (!isLast)。

如果和离线的混用,就像上面一样,在onCreat()里先执行了一次startNoDialogOffline(),那么经测试RecognizerDialogListener的onResult()只会调用一次,输出一个str,听写内容和标点符号连在一起的(具体原因不清楚),这时候如果是if (!isLast),就不会有输出了。所以这里要用if (isLast)。

单独使用离线的情况下,RecognizerListener的onResult()是只会调用一次,输出一个str。这时候如果是if (!isLast),就不会有输出了。所以这里要用if (isLast)。

所以说在线的要和离线的分开使用,本文只是个例子,实际使用过程中也不会同时使用。简单来说,在线用if (!isLast)判断,离线用if (isLast)判断

更多相关文章

  1. 如何在函数中将两个参数从1个类传递给另一个?
  2. Android的startActivityForResult()与onActivityResult()与setRe
  3. Android开发入门之为应用添加多个Activity与参数传递
  4. java socket参数详解:TcpNoDelay
  5. 在spring 中如何注入map,set,list,property等参数
  6. 如何将动态参数传递给jquery函数
  7. 使用字符串参数调用AndroidJni静态方法。
  8. Java开发水吧点饮品系统(顶层父类对象做接口参数)
  9. java返回值是list的时候获取list的参数类型

随机推荐

  1. 【JAVA】通过ISBN一键获取书籍信息
  2. 201621123014《Java程序设计》第六周学习
  3. 【Android学习】案例学开发,天气记事本项
  4. java读写中文文件
  5. Java开发环境搭建:JDK8 下载与安装
  6. 自学java 的,有心的高手帮帮忙
  7. javaee基础知识点
  8. Java IO编程全解(三)——伪异步IO编程
  9. java内存垃圾回收模型
  10. [置顶] Java排序再巩固--BubbleSo