您的位置:首页 > 移动开发 > Unity3D

Unity5.3 API 之 Microphone(游戏语音SDK )

2017-05-18 18:26 274 查看


Unity5.3 API 之 Microphone(游戏语音SDK )

好久不见,最近手机游戏内置语音越来越普遍,这样的需求也难免多了起来.对就是像微信/阴阳师那样.

下面介绍两种实现方法:

1.unity内置API - Microphone

2.第三方包SDK

3. - API - sealed class Microphine

优点:unity爸爸自己内置的,以后功能应该会更强大,避免接SDK,和第三方包的不稳定因素.

缺点:提供的方法太少,编码和解码需要自己搞定,优化不够到位,没有语音识别功能.

我推荐第二种方法,具体还是看需求!

第一种:unityAPI

API - sealed class Microphone

[C#] 纯文本查看 复制代码
namespace UnityEngine

{

//

// 摘要:

//     ///

//     Use this class to record to an AudioClip using a connected microphone.

//     ///

public sealed class Microphone

{

public Microphone();

//

// 摘要:

//     ///

//     A list of available microphone devices, identified by name.

//     ///

public static string[] devices { get; }

//

// 摘要:

//     ///

//     Stops recording.

//     ///

//

// 参数:

//   deviceName:

//     The name of the device.

[WrapperlessIcall]

public static void End(string deviceName);

[WrapperlessIcall]

public static void GetDeviceCaps(string deviceName, out int minFreq, out int maxFreq);

//

// 摘要:

//     ///

//     Get the position in samples of the recording.

//     ///

//

// 参数:

//   deviceName:

//     The name of the device.

[WrapperlessIcall]

public static int GetPosition(string deviceName);

//

// 摘要:

//     ///

//     Query if a device is currently recording.

//     ///

//

// 参数:

//   deviceName:

//     The name of the device.

[WrapperlessIcall]

public static bool IsRecording(string deviceName);

//

// 摘要:

//     ///

//     Start Recording with device.

//     ///

//

// 参数:

//   deviceName:

//     The name of the device.

//

//   loop:

//     Indicates whether the recording should continue recording if lengthSec is reached,

//     and wrap around and record from the beginning of the AudioClip.

//

//   lengthSec:

//     Is the length of the AudioClip produced by the recording.

//

//   frequency:

//     The sample rate of the AudioClip produced by the recording.

//

// 返回结果:

//     ///

//     The function returns null if the recording fails to start.

//     ///

[WrapperlessIcall]

public static AudioClip Start(string deviceName, bool loop, int lengthSec, int frequency);

}

}


开关录音

[C#] 纯文本查看 复制代码
/// <summary>

/// 开关录音

/// </summary>

/// <param name="isFlag"></param>

public void StartMicro(bool isFlag)

{

if (Microphone.devices.Length < 0)

return;

if (isFlag)

{

Microphone.End(null);

m_CurrentClip = Microphone.Start(null, false, m_SamplingMaxTime, m_SamplingRate);

if (m_CurrentClip)

return;

}

else

{

int length;

int lastPos = Microphone.GetPosition(null);

Debug.Log(lastPos + "..........." + Microphone.IsRecording(null));

if (Microphone.IsRecording(null))

{

length = lastPos / m_SamplingRate;

Debug.Log(length);

}

else

{

length = m_SamplingMaxTime;

}

Microphone.End(null);

//if (length < m_SamplingMinTime)

//{

//    Debug.Log("长度小于两秒");

//    return;

//}

byte[] wav = m_CurrentClip.EncodeToWAV(m_SamplingRate * length);

int lengthSamples;

int frequency;

float[] pcm = AudioClipCompress.WavToPCM(wav, out lengthSamples, out frequency);

labelText = "pcm" + pcm.Length;

AudioClip mClip = AudioClip.Create("", lengthSamples, 1, frequency, false);

mClip.SetData(pcm, 0);

AudioSource source = gameObject.GetComponent<AudioSource>();

if (source == null)

source = gameObject.AddComponent<AudioSource>();

source.clip = mClip;

source.Play();

}

}


其实Microphone.Start的返回值就是AuidoClip,拿过来就可以播了.

但是语音聊天涉及到网络通信,所以需要进行一下数据转换.

EncodeToWAV - audioclip 转 byte

WavToPCM - byte 转 float

最后mClip.SetData(pcm, 0);

OK!

第二种:sdk(呀呀云SDK 和 亲加SDK)

本帖隐藏的内容

1.呀呀云Dome 和 说明书文档 在附件里!

特别注意的是 播放语音的时候有两种方式 本地 和 下载.

根据项目需求选择吧.

[C#] 纯文本查看 复制代码
using UnityEngine;

using System.Collections;

using System;

using YunvaIM;

public class Demo : MonoBehaviour

{

private string sUserId="123";

private string labelText = "ssss";

string filePath = "";

private string recordPath=string.Empty;//返回录音地址

private string recordUrlPath=string.Empty;//返回录音url地址

public GUISkin guiSkin;

void Start ()

{

EventListenerManager.AddListener(ProtocolEnum.IM_RECORD_VOLUME_NOTIFY, ImRecordVolume);//录音音量大小回调监听

#region 初始化注册

int init = YunVaImSDK.instance.YunVa_Init(0, 300000, Application.persistentDataPath, true);

#endregion

if (init == 0)

{

Debug.Log("初始化成功...");

labelText="初始化成功...";

}

else

{

Debug.Log("初始化失败...");

labelText="初始化失败...";

}

}

void OnGUI()

{

if (guiSkin != null)

{

GUI.skin=guiSkin;

}

GUI.Box(new Rect(10f, 10f, 340, 900f), "菜单");

sUserId = GUI.TextField(new Rect(20f, 50f, 150f, 100f), sUserId);

if(GUI.Button(new Rect(20f,150f,150f,100f),"登录"))

{

#region 登录

string ttFormat = "{{\"nickname\":\"{0}\",\"uid\":\"{1}\"}}";

string tt = string.Format(ttFormat, sUserId, sUserId);

string[] wildcard = new string[2];

wildcard[0] = "0x001";

wildcard[1] = "0x002";

YunVaImSDK.instance.YunVaOnLogin(tt, "1111", wildcard, 0, (data) =>

{

if (data.result == 0)

{

labelText = string.Format("登录成功,昵称:{0},用户ID:{1}", data.nickName, data.userId);

YunVaImSDK.instance.RecordSetInfoReq(true);//开启录音的音量大小回调

}

else

{

labelText = string.Format("登录失败,错误消息:{0}", data.msg);

}

});

#endregion

}

if (GUI.Button(new Rect(20f, 250f, 150f, 100f), "开始录音"))

{

labelText = "正在录音中。。。。。。";

#region 开始录音

filePath = string.Format("{0}/{1}.amr", Application.persistentDataPath, DateTime.Now.ToFileTime());

Debug.Log("FilePath:" + filePath);

YunVaImSDK.instance.RecordStartRequest(filePath);

#endregion

}

if (GUI.Button(new Rect(20f,350f, 150f, 100f),"停止录音"))

{

labelText = "停止录音.........";

#region 停止录音

YunVaImSDK.instance.RecordStopRequest(StopRecordResponse);

#endregion

}

if (GUI.Button(new Rect(20f, 450f, 150f, 100f), "播放语音"))

{

labelText = "播放语音.........";

#region 播放语音

string ext = DateTime.Now.ToFileTime().ToString();

YunVaImSDK.instance.RecordStartPlayRequest(filePath, "", ext, (data2) =>

//YunVaImSDK.instance.RecordStartPlayRequest("", recordUrlPath, ext, (data2) =>

{

if (data2.result == 0)

{

Debug.Log("播放成功");

labelText = "播放成功";

}

else

{

Debug.Log("播放失败");

labelText = "播放失败";

}

});

#endregion

}

if (GUI.Button(new Rect(190f,50f, 150f, 100f),"停止播放"))

{

labelText = "停止播放.........";

Debug.Log("停止播放");

#region 停止播放

YunVaImSDK.instance.RecordStopPlayRequest();

#endregion

}

if (GUI.Button(new Rect(190f,150f, 150f, 100f),"语音识别"))

{

labelText = "语音识别.........";

Debug.Log("语音识别");

string ext = DateTime.Now.ToFileTime().ToString();

YunVaImSDK.instance.SpeechStartRequest(recordPath, ext, (data3) =>

{

if(data3.result==0)

{

labelText = "识别成功,识别内容:" + data3.text;

}

else

{

labelText = "识别失败,原因:" + data3.msg;

}

});

}

if(GUI.Button(new Rect(190f,250f, 150f, 100f),"上传语音"))

{

Debug.Log("准备上传:" + recordPath);

labelText = "准备上传:"+ recordPath;

string fileId = DateTime.Now.ToFileTime().ToString();

YunVaImSDK.instance.UploadFileRequest(recordPath, fileId, (data1) =>

{

if(data1.result==0)

{

recordUrlPath=data1.fileurl;

Debug.Log("上传成功:"+recordUrlPath);

labelText = "上传成功:"+recordUrlPath;

}

else

{

labelText ="上传失败:"+data1.msg;

Debug.Log("上传失败:"+data1.msg);

}

});

}

if(GUI.Button(new Rect(190f,350f, 150f, 100f),"下载语音"))

{

labelText = "下载语音......";

string DownLoadfilePath = string.Format("{0}/{1}.amr", Application.persistentDataPath, DateTime.Now.ToFileTime());

Debug.Log("下载语音:"+DownLoadfilePath);

string fileid = DateTime.Now.ToFileTime().ToString();

YunVaImSDK.instance.DownLoadFileRequest(recordUrlPath, DownLoadfilePath, fileid, (data4) =>

{

if(data4.result==0)

{

Debug.Log("下载成功:"+data4.filename);

labelText = "下载成功:"+data4.filename;

}

else

{

Debug.Log("下载失败:"+data4.msg);

labelText = "下载失败:"+data4.msg;

}

});

}

if (GUI.Button(new Rect(190f, 450f, 150f, 100f), "登出"))

{

#region 登出

YunVaImSDK.instance.YunVaLogOut();

#endregion

}

GUI.Label(new Rect(400f, 10f, 500f, 30f), "返回提示");

GUI.Label(new Rect(400f, 30f, 500f, 50f), labelText);

}

/// <summary>

/// 停止录音

/// </summary>

/// <param name="data"></param>

private void  StopRecordResponse(ImRecordStopResp  data)

{

if(!string.IsNullOrEmpty(data.strfilepath))

{

recordPath=data.strfilepath;

labelText = "停止录音返回:"+recordPath;

Debug.Log("停止录音返回:"+recordPath);

}

}

public void ImRecordVolume(object data)

{

ImRecordVolumeNotify RecordVolumeNotify = data as ImRecordVolumeNotify;

Debug.Log("ImRecordVolumeNotify:v_volume=" + RecordVolumeNotify.v_volume);

}

}


2.亲加 主要是各种事件回调和接口

使用操作起来有点复杂,但是功能全面.

(慎重选择)

亲加说明文档连接
http://www.gotye.com.cn/docs/ime/ href="http://www.manew.com" target=_blank>unity3d.html

Dome

[C#] 纯文本查看 复制代码
using UnityEngine;

using System.Collections;

using gotye;

public class MainManager : MonoBehaviour {

public GotyeAPI api;

string appKey = "xxxxxxxxxxxxxxxx";

string packageName = "com.gotye.api";

ListenerLogin listenerLogin;

ListenerChat listenerChat;

ListenerRoom listenerRoom;

string resurt = "";

string text = "";

static MainManager _instance;

public static MainManager Instance {

get { return _instance; }

}

void Awake()

{

InvokeRepeating("mainLoop", 0.0f, 0.050f);//初始化

_instance = this;

}

// Use this for initialization

void Start()

{

//初始化

api = GotyeAPI.GetInstance();

api.Init(appKey, packageName);

//添加事件回调

listenerLogin = new ListenerLogin();

listenerChat = new ListenerChat();

listenerRoom = new ListenerRoom();

api.AddListener(listenerLogin);

api.AddListener(listenerChat);

api.AddListener(listenerRoom);

}

void OnGUI()

{

GUI.Label(new Rect(200, 0, 200, 200), text);

GUI.Label(new Rect(200, 200, 200, 200), resurt);

if (GUI.Button(new Rect(0, 0, 200, 100), "sq123登录"))

{

text = "sq123登录";

api.Login("sq123", null);

}

if (GUI.Button(new Rect(0, 100, 200, 100), "sq222登录"))

{

text = "sq222登录";

api.Login("sq222", null);

}

if (GUI.Button(new Rect(0, 200, 200, 100), "进入聊天室"))

{

//298926

text = "进入聊天室";

GotyeRoom room = new GotyeRoom(298926);

api.EnterRoom(room);

}

if (GUI.Button(new Rect(0, 300, 200, 100), "开始说话"))

{

text = "开始说话";

GotyeRoom room = new GotyeRoom(298926);

//api.SendMessage(GotyeMessage.CreateTextMessage(room, "111"));

api.StartTalk(room,0,false,20000);

}

if (GUI.Button(new Rect(0, 400, 200, 100), "停止说话"))

{

text = "停止说话";

api.StopTalk();

}

if (GUI.Button(new Rect(0, 500, 200, 100), "退出聊天室"))

{

text = "退出聊天室";

GotyeRoom room = new GotyeRoom(298926);

api.LeaveRoom(room);

}

if (GUI.Button(new Rect(0, 600, 200, 100), "退出登录"))

{

text = "退出登录";

api.Logout();

}

}

void mainLoop()//初始化

{

GotyeAPI.GetInstance().MainLoop();

}

//显示Gui信息

public void ShowAnimate(string log) {

text = log;

}

public void ShowResurt(string log)

{

resurt = log;

}

}


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: