You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

229 lines
6.6 KiB

import 'dart:async';
import 'package:get/get.dart';
import '../../../data/services/azure_asr_service.dart';
import '../../../core/utils/logger.dart';
// Azure语音识别状态枚举
enum AzureAsrState {
notInitialized, // 未初始化
initialized, // 已初始化
listening, // 正在监听
notListening, // 未监听
error, // 错误
}
class AzureAsrTestController extends GetxController {
// 服务引用
final AzureAsrService _azureAsrService = Get.find<AzureAsrService>();
// 状态变量
final RxBool isListening = false.obs;
final RxString recognizedText = ''.obs;
final RxString partialText = ''.obs;
final Rx<AzureAsrState> asrState = AzureAsrState.notInitialized.obs;
// 语言选项
final RxString selectedLanguage = 'zh-CN'.obs;
final List<String> availableLanguages = [
'zh-CN', // 中文(中国大陆)
'en-US', // 英语(美国)
'ja-JP', // 日语
'ko-KR', // 韩语
'fr-FR', // 法语
'de-DE', // 德语
'es-ES', // 西班牙语
'it-IT', // 意大利语
'pt-BR', // 葡萄牙语(巴西)
'ru-RU', // 俄语
];
// 订阅
StreamSubscription? _recognitionSubscription;
@override
void onInit() {
super.onInit();
_initializeAsr();
}
// 初始化ASR服务
Future<void> _initializeAsr() async {
try {
final success = await _azureAsrService.initialize(language: selectedLanguage.value);
asrState.value = success ? AzureAsrState.initialized : AzureAsrState.error;
} catch (e) {
Logger.error('初始化ASR服务失败: $e');
asrState.value = AzureAsrState.error;
}
}
// 开始简单语音识别
Future<void> startSimpleRecognition() async {
try {
if (asrState.value == AzureAsrState.notInitialized) {
await _initializeAsr();
}
// 如果正在进行连续识别,先停止
if (_azureAsrService.isContinuousRecognitionActive()) {
await stopContinuousRecognition();
}
partialText.value = '';
final result = await _azureAsrService.recognizeSpeech();
if (result.isNotEmpty) {
recognizedText.value = result;
}
} catch (e) {
Logger.error('开始简单语音识别出错: $e');
asrState.value = AzureAsrState.error;
}
}
// 切换连续语音识别
Future<void> toggleContinuousRecognition() async {
try {
if (asrState.value == AzureAsrState.notInitialized) {
await _initializeAsr();
}
if (_azureAsrService.isContinuousRecognitionActive()) {
await stopContinuousRecognition();
} else {
await startContinuousRecognition();
}
} catch (e) {
Logger.error('切换连续语音识别出错: $e');
asrState.value = AzureAsrState.error;
}
}
// 开始连续语音识别
Future<void> startContinuousRecognition() async {
try {
if (_azureAsrService.isContinuousRecognitionActive()) {
await stopContinuousRecognition();
}
_recognitionSubscription?.cancel();
_recognitionSubscription = null;
isListening.value = true;
asrState.value = AzureAsrState.listening;
partialText.value = '';
final stream = await _azureAsrService.startContinuousRecognition();
_recognitionSubscription = stream.listen(
(event) {
switch (event.type) {
case RecognitionEventType.finalResult:
if (event.text.isNotEmpty) {
recognizedText.value = event.text;
}
partialText.value = '';
break;
case RecognitionEventType.intermediateResult:
if (event.text.isNotEmpty) {
partialText.value = event.text;
}
break;
case RecognitionEventType.sessionStarted:
isListening.value = true;
asrState.value = AzureAsrState.listening;
break;
case RecognitionEventType.sessionStopped:
isListening.value = false;
asrState.value = AzureAsrState.notListening;
partialText.value = '';
break;
case RecognitionEventType.canceled:
isListening.value = false;
asrState.value = AzureAsrState.notListening;
partialText.value = '';
break;
case RecognitionEventType.error:
asrState.value = AzureAsrState.error;
isListening.value = false;
partialText.value = '';
_initializeAsr();
break;
}
},
onError: (error) {
asrState.value = AzureAsrState.error;
isListening.value = false;
partialText.value = '';
},
onDone: () {
if (!_azureAsrService.isContinuousRecognitionActive()) {
isListening.value = false;
asrState.value = AzureAsrState.notListening;
}
},
);
} catch (e) {
Logger.error('开始连续语音识别出错: $e');
asrState.value = AzureAsrState.error;
isListening.value = false;
partialText.value = '';
}
}
// 停止连续语音识别
Future<void> stopContinuousRecognition() async {
try {
isListening.value = false;
asrState.value = AzureAsrState.notListening;
await _azureAsrService.stopContinuousRecognition();
_recognitionSubscription?.cancel();
_recognitionSubscription = null;
partialText.value = '';
} catch (e) {
Logger.error('停止连续语音识别出错: $e');
asrState.value = AzureAsrState.error;
}
}
// 更改语言
Future<void> changeLanguage(String language) async {
try {
if (selectedLanguage.value == language) return;
selectedLanguage.value = language;
if (_azureAsrService.isContinuousRecognitionActive()) {
await stopContinuousRecognition();
}
final success = await _azureAsrService.setRecognitionLanguage(language);
asrState.value = success ? AzureAsrState.initialized : AzureAsrState.error;
recognizedText.value = '';
partialText.value = '';
} catch (e) {
Logger.error('更改语言出错: $e');
asrState.value = AzureAsrState.error;
}
}
@override
void onClose() {
_recognitionSubscription?.cancel();
_recognitionSubscription = null;
if (_azureAsrService.isContinuousRecognitionActive()) {
_azureAsrService.stopContinuousRecognition();
}
super.onClose();
}
}