SpeechRecognition簡介
iOS10中的公開的新API :Speech Recognition可以用于識(shí)別用戶的語音杯瞻,我們可以根據(jù)識(shí)別結(jié)果來實(shí)現(xiàn)一些我們想要的操作商源。
網(wǎng)上搜羅了下相關(guān)資料不多硕舆,本人參考了一些國外的網(wǎng)站轨香,自己寫了個(gè)DEMO慕的,在這做個(gè)簡單分享:
功能授權(quán)
現(xiàn)在iOS10對(duì)系統(tǒng)功能的使用都需要進(jìn)行一次用戶授權(quán)古胆,所以我們就像設(shè)置相機(jī)一樣,在info.plist文件中也要添加相關(guān)的使用描述香罐,語音識(shí)別功能需要用到兩個(gè)系統(tǒng)功能:
NSSpeechRecognitionUsageDescription: 語音識(shí)別使用描述
NSMicrophoneUsageDescription:麥克風(fēng)使用描述
所以我們添加:
<key>NSSpeechRecognitionUsageDescription</key>
<string>Speech Recognition</string>
<key>NSMicrophoneUsageDescription</key>
<string>Microphone</string>
這里的string即描述會(huì)在提示用戶的時(shí)候顯示。
圖:
基礎(chǔ)設(shè)置
功能很簡單时肿,點(diǎn)擊按鈕庇茫,開始聽寫,在label上顯示識(shí)別出的內(nèi)容
@property (nonatomic, strong) AVAudioEngine *audioEngine; // 聲音處理器
@property (nonatomic, strong) SFSpeechRecognizer *speechRecognizer; // 語音識(shí)別器
@property (nonatomic, strong) SFSpeechAudioBufferRecognitionRequest *speechRequest; // 語音請(qǐng)求對(duì)象
@property (nonatomic, strong) SFSpeechRecognitionTask *currentSpeechTask; // 當(dāng)前語音識(shí)別進(jìn)程
@property (nonatomic, weak) IBOutlet UILabel *showLb; // 用于展現(xiàn)的label
@property (nonatomic, weak) IBOutlet UIButton *startBtn; // 啟動(dòng)按鈕
在viewDidLoad中初始化螃成,并判斷用戶授權(quán)是否通過
// 初始化
self.audioEngine = [AVAudioEngine new];
// 這里需要先設(shè)置一個(gè)AVAudioEngine和一個(gè)語音識(shí)別的請(qǐng)求對(duì)象SFSpeechAudioBufferRecognitionRequest
self.speechRecognizer = [SFSpeechRecognizer new];
self.startBtn.enabled = NO;
[SFSpeechRecognizer requestAuthorization:^(SFSpeechRecognizerAuthorizationStatus status)
{
if (status != SFSpeechRecognizerAuthorizationStatusAuthorized)
{
// 如果狀態(tài)不是已授權(quán)則return
return;
}
// 初始化語音處理器的輸入模式
[self.audioEngine.inputNode installTapOnBus:0 bufferSize:1024
format:[self.audioEngine.inputNode outputFormatForBus:0]
block:^(AVAudioPCMBuffer * _Nonnull buffer,
AVAudioTime * _Nonnull when)
{
// 為語音識(shí)別請(qǐng)求對(duì)象添加一個(gè)AudioPCMBuffer旦签,來獲取聲音數(shù)據(jù)
[self.speechRequest appendAudioPCMBuffer:buffer];
}];
// 語音處理器準(zhǔn)備就緒(會(huì)為一些audioEngine啟動(dòng)時(shí)所必須的資源開辟內(nèi)存)
[self.audioEngine prepare];
self.startBtn.enabled = YES;
}];
注意: 如果你在info.plist文件中設(shè)置NSMicrophoneUsageDescription失敗,這時(shí)如果嘗試訪問_audioEngine.InputNode會(huì)使你的app崩潰寸宏,且你無法catch到有用的信息宁炫。
實(shí)現(xiàn)功能
點(diǎn)擊按鈕
- (IBAction)onStartBtnClicked:(id)sender
{
if (self.currentSpeechTask.state == SFSpeechRecognitionTaskStateRunning)
{ // 如果當(dāng)前進(jìn)程狀態(tài)是進(jìn)行中
[self.startBtn setTitle:@"Start Dictating" forState:UIControlStateNormal];
// 停止語音識(shí)別
[self stopDictating];
}
else
{ // 進(jìn)程狀態(tài)不在進(jìn)行中
[self.startBtn setTitle:@"Stop Dictaring" forState:UIControlStateNormal];
self.showLb.text = @"I'm waiting";
// 開啟語音識(shí)別
[self startDictating];
}
}
- (void)startDictating
{
NSError *error;
// 啟動(dòng)聲音處理器
[self.audioEngine startAndReturnError: &error];
// 初始化
self.speechRequest = [SFSpeechAudioBufferRecognitionRequest new];
// 使用speechRequest請(qǐng)求進(jìn)行識(shí)別
self.currentSpeechTask =
[self.speechRecognizer recognitionTaskWithRequest:self.speechRequest
resultHandler:^(SFSpeechRecognitionResult * _Nullable result,
NSError * _Nullable error)
{
// 識(shí)別結(jié)果,識(shí)別后的操作
if (result == NULL) return;
self.showLb.text = result.bestTranscription.formattedString;
}];
}
在這個(gè)方法中我們創(chuàng)建了一個(gè)新的識(shí)別請(qǐng)求和語音進(jìn)程氮凝。當(dāng)通過識(shí)別對(duì)象更新數(shù)據(jù)的時(shí)候羔巢,則更新label的text,無論聽寫是否仍然在進(jìn)行中罩阵。
最后 我們只需要實(shí)現(xiàn)stopDictating:
- (void)stopDictating
{
// 停止聲音處理器竿秆,停止語音識(shí)別請(qǐng)求進(jìn)程
[self.audioEngine stop];
[self.speechRequest endAudio];
}
好了,代碼很少永脓,很多東西也在注釋中寫明了袍辞,現(xiàn)在已經(jīng)可以實(shí)現(xiàn)聽寫的功能了。這時(shí)如果我們對(duì)識(shí)別的結(jié)果再進(jìn)行一次判斷常摧,根據(jù)不同的結(jié)果來執(zhí)行不同的操作搅吁,應(yīng)該會(huì)有不錯(cuò)的用戶體驗(yàn)吧。
參考:http://gregshackles.com/using-speech-recognition-in-ios-10/?utm_source=tuicool&utm_medium=referral