@@ -1,4 +1,4 @@ | |||||
import 'package:demo001/scenes/%20RecordScene.dart'; | |||||
import 'package:demo001/scenes/translate/TranslateScene.dart'; | |||||
import 'package:flutter/material.dart'; | import 'package:flutter/material.dart'; | ||||
void main() { | void main() { | ||||
@@ -18,7 +18,7 @@ class MyApp extends StatelessWidget { | |||||
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple), | colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple), | ||||
useMaterial3: true, | useMaterial3: true, | ||||
), | ), | ||||
home: RecordScene(), | |||||
home: TranslateScene(), | |||||
); | ); | ||||
} | } | ||||
} | } |
@@ -1,218 +0,0 @@ | |||||
import 'dart:async'; | |||||
import 'dart:io'; | |||||
import 'dart:typed_data'; | |||||
import 'package:record/record.dart'; | |||||
import 'package:flutter/material.dart'; | |||||
import 'package:logger/logger.dart'; | |||||
import 'package:path_provider/path_provider.dart'; | |||||
import 'package:permission_handler/permission_handler.dart'; | |||||
import 'package:demo001/xunfei/xunfei_translate.dart'; | |||||
/* | |||||
录音测试场景 | |||||
*/ | |||||
class RecordScene extends StatefulWidget { | |||||
@override | |||||
_RecordSceneState createState() => _RecordSceneState(); | |||||
} | |||||
class _RecordSceneState extends State<RecordScene> { | |||||
late Directory savedirectory; | |||||
final XunFeiTranslate xunfei = XunFeiTranslate( | |||||
appId: "137dc132", | |||||
apiKey: "1c1891a475e71250ecd1320303ad6545", | |||||
apiSecret: "MjZhNDA1NTI1NWZkZDQxOTMxYzMyN2Yw"); | |||||
AudioRecorder _recorder = AudioRecorder(); | |||||
bool _isRecorderReady = false; //是否录音已准备 | |||||
bool _isRecording = false; //是否录音中 | |||||
@override | |||||
void initState() { | |||||
super.initState(); | |||||
_requestPermissions(); | |||||
} | |||||
// 初始化录音器 | |||||
void _initRecorder() async { | |||||
try { | |||||
// 获取外部存储目录路径 | |||||
savedirectory = (await getExternalStorageDirectory())!; | |||||
setState(() { | |||||
_isRecorderReady = true; | |||||
}); | |||||
_log('录音器初始化成功'); | |||||
} catch (e) { | |||||
_log('初始化录音器失败: $e'); | |||||
setState(() { | |||||
_isRecorderReady = false; | |||||
}); | |||||
} | |||||
} | |||||
// 请求麦克风权限 | |||||
void _requestPermissions() async { | |||||
try { | |||||
if (await Permission.microphone.request().isGranted) { | |||||
_log('麦克风权限已授予'); | |||||
} else { | |||||
_log('麦克风权限被拒绝'); | |||||
setState(() { | |||||
_isRecorderReady = false; | |||||
}); | |||||
} | |||||
} catch (e) { | |||||
_log('请求麦克风权限失败: $e'); | |||||
setState(() { | |||||
_isRecorderReady = false; | |||||
}); | |||||
} | |||||
} | |||||
// 切换按钮状态 | |||||
void _toggleCallStatus() { | |||||
if (!_isRecording) { | |||||
//开始通话 | |||||
_startRecorder(); | |||||
} else { | |||||
//结束通话 | |||||
_stopRecorder(); | |||||
} | |||||
setState(() { | |||||
_isRecording = !_isRecording; | |||||
}); | |||||
} | |||||
//开始录音 | |||||
void _startRecorder() async { | |||||
try { | |||||
if (!_isRecorderReady) { | |||||
_initRecorder(); | |||||
} | |||||
if (_isRecording) return; // 防止重复调用 | |||||
Stream<Uint8List> dataStream = await _recorder.startStream(RecordConfig( | |||||
sampleRate: 16000, encoder: AudioEncoder.pcm16bits, numChannels: 1)); | |||||
xunfei.starttranslate(dataStream); | |||||
setState(() { | |||||
_isRecording = true; | |||||
}); | |||||
_log('录音开始'); | |||||
} catch (e) { | |||||
_log('录音开始 异常: $e'); | |||||
} | |||||
} | |||||
//结束录音 | |||||
void _stopRecorder() async { | |||||
try { | |||||
if (!_isRecording) return; // 防止重复调用 | |||||
await _recorder.stop(); | |||||
await _recorder.cancel(); | |||||
xunfei.stoptranslate(); | |||||
setState(() { | |||||
_isRecorderReady = false; | |||||
_isRecording = false; | |||||
}); | |||||
_log('录音停止'); | |||||
} catch (e) { | |||||
_log('录音停止 异常: $e'); | |||||
} | |||||
} | |||||
@override | |||||
Widget build(BuildContext context) { | |||||
return Scaffold( | |||||
appBar: AppBar(title: Text("录音测试")), | |||||
// body: ListView.builder( | |||||
// itemCount: _records.length, | |||||
// itemBuilder: (context, index) { | |||||
// var audio = _records[index]; | |||||
// return _buildAudioMessage(audio); | |||||
// }, | |||||
// ), | |||||
bottomNavigationBar: Padding( | |||||
padding: const EdgeInsets.all(20.0), | |||||
child: InkWell( | |||||
onTap: _toggleCallStatus, | |||||
child: Container( | |||||
decoration: BoxDecoration( | |||||
borderRadius: BorderRadius.circular(30), // 圆角按钮 | |||||
color: _isRecording | |||||
? Colors.red | |||||
: Colors.green, // 通话状态红色,非通话状态绿色 | |||||
), | |||||
padding: EdgeInsets.symmetric( | |||||
vertical: 15, horizontal: 40), // 调整按钮大小 | |||||
child: Row( | |||||
mainAxisAlignment: MainAxisAlignment.center, | |||||
children: [ | |||||
Icon( | |||||
_isRecording ? Icons.call_end : Icons.mic, // 图标变化 | |||||
color: Colors.white, | |||||
size: 30, | |||||
), | |||||
SizedBox(width: 10), | |||||
Text( | |||||
_isRecording ? '挂断' : '开始通话', // 状态文字变化 | |||||
style: TextStyle( | |||||
color: Colors.white, | |||||
fontSize: 18, | |||||
), | |||||
), | |||||
], | |||||
), | |||||
))), | |||||
); | |||||
} | |||||
// 构建语音消息 | |||||
// Widget _buildAudioMessage(RecordData data) { | |||||
// Color buttColor = data.state == 0 ? Colors.red : Colors.green; | |||||
// return Padding( | |||||
// padding: const EdgeInsets.symmetric(vertical: 10, horizontal: 15), | |||||
// child: Column( | |||||
// crossAxisAlignment: CrossAxisAlignment.start, | |||||
// children: [ | |||||
// // 音频播放按钮 | |||||
// GestureDetector( | |||||
// onTap: () { | |||||
// // _playRecording(data); | |||||
// }, | |||||
// child: Container( | |||||
// padding: EdgeInsets.symmetric(vertical: 10, horizontal: 20), | |||||
// decoration: BoxDecoration( | |||||
// color: buttColor, | |||||
// borderRadius: BorderRadius.circular(30), | |||||
// ), | |||||
// child: Row( | |||||
// children: [ | |||||
// Icon( | |||||
// Icons.play_arrow, | |||||
// color: Colors.white, | |||||
// ), | |||||
// SizedBox(width: 10), | |||||
// Text( | |||||
// '播放音频', | |||||
// style: TextStyle(color: Colors.white), | |||||
// ), | |||||
// ], | |||||
// ), | |||||
// ), | |||||
// ), | |||||
// SizedBox(height: 5), | |||||
// // 文字内容 | |||||
// // Text( | |||||
// // message['text'], | |||||
// // style: TextStyle(fontSize: 16), | |||||
// // ), | |||||
// ], | |||||
// ), | |||||
// ); | |||||
// } | |||||
void _log(String msg) { | |||||
Logger().f("LIWEI---------------:$msg"); | |||||
} | |||||
} |
@@ -0,0 +1,135 @@ | |||||
import 'dart:convert'; | |||||
import 'dart:io'; | |||||
import 'dart:typed_data'; | |||||
import 'package:demo001/scenes/translate/TranslateState.dart'; | |||||
import 'package:demo001/tools/audio_tool.dart'; | |||||
import 'package:demo001/xunfei/recognition_result/recognition_content/recognition_content.dart'; | |||||
import 'package:demo001/xunfei/xunfei_translate.dart'; | |||||
import 'package:get/get.dart'; | |||||
import 'package:logger/logger.dart'; | |||||
import 'package:path_provider/path_provider.dart'; | |||||
import 'package:permission_handler/permission_handler.dart'; | |||||
import 'package:record/record.dart'; | |||||
class TranslateLogic extends GetxController { | |||||
late Directory savedirectory; | |||||
final state = TranslateState(); | |||||
late XunFeiTranslate xunfei; | |||||
late AudioRecorder _recorder; | |||||
@override | |||||
void onInit() { | |||||
super.onInit(); | |||||
_requestPermissions(); | |||||
_recorder = AudioRecorder(); | |||||
xunfei = XunFeiTranslate( | |||||
appId: "137dc132", | |||||
apiKey: "1c1891a475e71250ecd1320303ad6545", | |||||
apiSecret: "MjZhNDA1NTI1NWZkZDQxOTMxYzMyN2Yw", | |||||
onRecognitionResult: _handleRecognaitionData, | |||||
onStreamtransResult: _handleTranslateData, | |||||
onAudioResult: _handleAudioData); | |||||
} | |||||
// 初始化录音器 | |||||
void _initRecorder() async { | |||||
try { | |||||
// 获取外部存储目录路径 | |||||
savedirectory = (await getExternalStorageDirectory())!; | |||||
state.isRecorderReady.value = true; | |||||
_log('录音器初始化成功'); | |||||
} catch (e) { | |||||
_log('初始化录音器失败: $e'); | |||||
state.isRecorderReady.value = false; | |||||
} | |||||
} | |||||
// 请求麦克风权限 | |||||
void _requestPermissions() async { | |||||
try { | |||||
if (await Permission.microphone.request().isGranted) { | |||||
_log('麦克风权限已授予'); | |||||
} else { | |||||
_log('麦克风权限被拒绝'); | |||||
} | |||||
} catch (e) { | |||||
_log('请求麦克风权限失败: $e'); | |||||
} | |||||
} | |||||
// 切换按钮状态 | |||||
void toggleCallStatus() { | |||||
if (!state.isRecording.value) { | |||||
//开始通话 | |||||
_startRecorder(); | |||||
} else { | |||||
//结束通话 | |||||
_stopRecorder(); | |||||
} | |||||
state.isRecording.value = !state.isRecording.value; | |||||
} | |||||
//开始录音 | |||||
void _startRecorder() async { | |||||
try { | |||||
if (!state.isRecorderReady.value) { | |||||
_initRecorder(); | |||||
} | |||||
if (state.isRecording.value) return; // 防止重复调用 | |||||
Stream<Uint8List> dataStream = await _recorder.startStream(RecordConfig( | |||||
sampleRate: 16000, encoder: AudioEncoder.pcm16bits, numChannels: 1)); | |||||
xunfei.starttranslate(dataStream); | |||||
state.isRecording.value = true; | |||||
_log('录音开始'); | |||||
} catch (e) { | |||||
_log('录音开始 异常: $e'); | |||||
} | |||||
} | |||||
//结束录音 | |||||
void _stopRecorder() async { | |||||
try { | |||||
if (!state.isRecording.value) return; // 防止重复调用 | |||||
await _recorder.stop(); | |||||
await _recorder.cancel(); | |||||
xunfei.stoptranslate(); | |||||
state.isRecorderReady.value = false; | |||||
state.isRecording.value = false; | |||||
_log('录音停止'); | |||||
} catch (e) { | |||||
_log('录音停止 异常: $e'); | |||||
} | |||||
} | |||||
void _handleRecognaitionData(result) { | |||||
KDXFSentenceModel model; | |||||
try { | |||||
final index = state.kdxfSentenceList.indexWhere((KDXFSentenceModel e) { | |||||
return e.sid == result.header?.sid; | |||||
}); | |||||
if (index != -1) { | |||||
model = state.kdxfSentenceList[index]; | |||||
} else { | |||||
final recogContextStr = utf8.decode( | |||||
base64Decode(result.payload?.recognitionResults?.text ?? '')); | |||||
final model = RecognitionContent.fromJson(jsonDecode(recogContextStr)); | |||||
model = KDXFSentenceModel( | |||||
content: "", | |||||
sid: result.header?.sid ?? '', | |||||
transResult: '', | |||||
audioPath: '', | |||||
perviousWs: model.ws ?? []); | |||||
} | |||||
} catch (e) { | |||||
print("接收识别结果异常 $e"); | |||||
} | |||||
} | |||||
void _handleTranslateData(result) {} | |||||
void _handleAudioData(AudioModel model) {} | |||||
void _log(String msg) { | |||||
Logger().f("LIWEI---------------:$msg"); | |||||
} | |||||
} |
@@ -0,0 +1,105 @@ | |||||
import 'package:get/get.dart'; | |||||
import 'package:flutter/material.dart'; | |||||
import 'TranslateLogic.dart'; | |||||
import 'TranslateState.dart'; | |||||
/* | |||||
录音测试场景 | |||||
*/ | |||||
class TranslateScene extends StatelessWidget { | |||||
final TranslateLogic logic = Get.put(TranslateLogic()); | |||||
final TranslateState state = Get.find<TranslateLogic>().state; | |||||
TranslateScene({super.key}); | |||||
@override | |||||
Widget build(BuildContext context) { | |||||
return Scaffold( | |||||
appBar: AppBar(title: Text("录音测试")), | |||||
// body: ListView.builder( | |||||
// itemCount: _records.length, | |||||
// itemBuilder: (context, index) { | |||||
// var audio = _records[index]; | |||||
// return _buildAudioMessage(audio); | |||||
// }, | |||||
// ), | |||||
bottomNavigationBar: Padding( | |||||
padding: const EdgeInsets.all(20.0), | |||||
child: InkWell( | |||||
onTap: logic.toggleCallStatus, | |||||
child: Obx(() => Container( | |||||
decoration: BoxDecoration( | |||||
borderRadius: BorderRadius.circular(30), // 圆角按钮 | |||||
color: state.isRecording.value | |||||
? Colors.red | |||||
: Colors.green, // 通话状态红色,非通话状态绿色 | |||||
), | |||||
padding: EdgeInsets.symmetric( | |||||
vertical: 15, horizontal: 40), // 调整按钮大小 | |||||
child: Row( | |||||
mainAxisAlignment: MainAxisAlignment.center, | |||||
children: [ | |||||
Icon( | |||||
state.isRecording.value | |||||
? Icons.call_end | |||||
: Icons.mic, // 图标变化 | |||||
color: Colors.white, | |||||
size: 30, | |||||
), | |||||
SizedBox(width: 10), | |||||
Text( | |||||
state.isRecording.value ? '挂断' : '开始通话', // 状态文字变化 | |||||
style: TextStyle( | |||||
color: Colors.white, | |||||
fontSize: 18, | |||||
), | |||||
), | |||||
], | |||||
), | |||||
)))), | |||||
); | |||||
} | |||||
// 构建语音消息 | |||||
// Widget _buildAudioMessage(RecordData data) { | |||||
// Color buttColor = data.state == 0 ? Colors.red : Colors.green; | |||||
// return Padding( | |||||
// padding: const EdgeInsets.symmetric(vertical: 10, horizontal: 15), | |||||
// child: Column( | |||||
// crossAxisAlignment: CrossAxisAlignment.start, | |||||
// children: [ | |||||
// // 音频播放按钮 | |||||
// GestureDetector( | |||||
// onTap: () { | |||||
// // _playRecording(data); | |||||
// }, | |||||
// child: Container( | |||||
// padding: EdgeInsets.symmetric(vertical: 10, horizontal: 20), | |||||
// decoration: BoxDecoration( | |||||
// color: buttColor, | |||||
// borderRadius: BorderRadius.circular(30), | |||||
// ), | |||||
// child: Row( | |||||
// children: [ | |||||
// Icon( | |||||
// Icons.play_arrow, | |||||
// color: Colors.white, | |||||
// ), | |||||
// SizedBox(width: 10), | |||||
// Text( | |||||
// '播放音频', | |||||
// style: TextStyle(color: Colors.white), | |||||
// ), | |||||
// ], | |||||
// ), | |||||
// ), | |||||
// ), | |||||
// SizedBox(height: 5), | |||||
// // 文字内容 | |||||
// // Text( | |||||
// // message['text'], | |||||
// // style: TextStyle(fontSize: 16), | |||||
// // ), | |||||
// ], | |||||
// ), | |||||
// ); | |||||
// } | |||||
} |
@@ -0,0 +1,38 @@ | |||||
import 'dart:typed_data'; | |||||
import 'package:audio_waveforms/audio_waveforms.dart'; | |||||
import 'package:demo001/xunfei/phonetic_dictation/phonetic_dictaion_model/w.dart'; | |||||
import 'package:demo001/xunfei/recognition_result/recognition_content/recognition_content.dart'; | |||||
import 'package:get/get_rx/src/rx_types/rx_types.dart'; | |||||
class TranslateState { | |||||
RxBool isRecorderReady = false.obs; //是否录音已准备 | |||||
RxBool isRecording = false.obs; //是否录音中 | |||||
RxList<KDXFSentenceModel> kdxfSentenceList = <KDXFSentenceModel>[].obs; | |||||
} | |||||
class KDXFSentenceModel { | |||||
String content = ''; | |||||
String sid = ''; | |||||
String transResult = ''; | |||||
String audioPath = ''; | |||||
Uint8List audioBytes = Uint8List(0); | |||||
///已经释放好的最终文本 | |||||
List<String> isFinalTransString = []; | |||||
///临时翻译文件 | |||||
// String isTempTransString = ''; | |||||
List<W> perviousWs = []; | |||||
List<RecognitionContent> contentList = []; | |||||
int audioDuration = 0; | |||||
final PlayerController playerController = PlayerController(); | |||||
KDXFSentenceModel({ | |||||
required this.content, | |||||
required this.sid, | |||||
required this.transResult, | |||||
required this.audioPath, | |||||
required this.perviousWs, | |||||
}); | |||||
} |
@@ -0,0 +1,116 @@ | |||||
import 'dart:async'; | |||||
import 'dart:io'; | |||||
import 'dart:typed_data'; | |||||
import 'package:audioplayers/audioplayers.dart'; | |||||
import 'package:get/get.dart'; | |||||
import 'package:logger/logger.dart'; | |||||
import 'package:path_provider/path_provider.dart'; | |||||
class AudioTool { | |||||
AudioTool._(); | |||||
static final AudioTool share = AudioTool._(); | |||||
factory AudioTool() => share; | |||||
///所有的音频数据 | |||||
List<Uint8List> _audioChunks = []; | |||||
///分断合并的数组,达到一定数量后合并去播放 | |||||
List<Uint8List> _playTemps = []; | |||||
///存放合并后的音频数组用于播放,播放完一个删除一个直到播放全部 | |||||
// List<Uint8List> _playBuff = []; | |||||
///是否已经播放了,play只被主动调用一次,然后根据_playBuff的数组递归 | |||||
bool isPlaying = false; | |||||
final player = AudioPlayer(); | |||||
void dispose() async { | |||||
await player.stop(); | |||||
await player.dispose(); | |||||
} | |||||
void addAudioChunk({required AudioModel model, required Function(String) onPath, required Function() onPlaying, required Function() onPlayEnd}) async { | |||||
if (model.status == 0 || model.status == 1) { | |||||
_audioChunks.add(model.data); | |||||
_playTemps.add(model.data); | |||||
} else if (model.status == 2) { | |||||
_audioChunks.add(model.data); | |||||
_playTemps.add(model.data); | |||||
final path = await mergeAudioChunks(sid: model.sid, chunks: _playTemps, onPlaying: onPlaying, onPlayEnd: onPlayEnd); | |||||
onPath(path); | |||||
} | |||||
} | |||||
Future<String> mergeAudioChunks({required String sid, required List<Uint8List> chunks, required Function() onPlaying, required Function() onPlayEnd}) async { | |||||
// 计算总长度 | |||||
int totalLength = chunks.fold(0, (sum, chunk) => sum + chunk.length); | |||||
// 创建合并后的 Uint8List | |||||
final mergedData = Uint8List(totalLength); | |||||
int offset = 0; | |||||
for (var chunk in chunks) { | |||||
mergedData.setRange(offset, offset + chunk.length, chunk); | |||||
offset += chunk.length; | |||||
} | |||||
///保存到文件或上传 | |||||
// Logger().f('------isFinal--------保存文件'); | |||||
_audioChunks = []; | |||||
_playTemps = []; | |||||
// _playBuff.add(mergedData); | |||||
// if (!isPlaying) { | |||||
// isPlaying = true; | |||||
// play(bytes: mergedData, onPlaying: onPlaying, onPlayEnd: onPlayEnd); | |||||
// } | |||||
final dir = await getApplicationSupportDirectory(); | |||||
final path = dir.path + '/$sid.mp3'; | |||||
File file = File(path); | |||||
await file.writeAsBytes(mergedData); | |||||
return path; | |||||
} | |||||
void play({required Uint8List bytes, required Function() onPlaying, required Function() onPlayEnd}) async { | |||||
// Logger().f('------_playBuff--------${_playBuff.length}'); | |||||
// if (_playBuff.isNotEmpty) { | |||||
await player.onPlayerStateChanged.listen((sta) async { | |||||
if (sta == PlayerState.completed) { | |||||
isPlaying = false; | |||||
// if (_playBuff.isNotEmpty) { | |||||
// _playBuff.removeAt(0); | |||||
// } | |||||
onPlayEnd(); | |||||
} | |||||
}); | |||||
final source = BytesSource(bytes, mimeType: 'audio/mp3'); | |||||
onPlaying(); | |||||
await player.play(source); | |||||
// } else { | |||||
// isPlaying = false; | |||||
// } | |||||
} | |||||
static Uint8List mergeAudio({required List<Uint8List> chunks}) { | |||||
// 计算总长度 | |||||
int totalLength = chunks.fold(0, (sum, chunk) => sum + chunk.length); | |||||
// 创建合并后的 Uint8List | |||||
final mergedData = Uint8List(totalLength); | |||||
int offset = 0; | |||||
for (var chunk in chunks) { | |||||
mergedData.setRange(offset, offset + chunk.length, chunk); | |||||
offset += chunk.length; | |||||
} | |||||
return mergedData; | |||||
} | |||||
} | |||||
class AudioModel { | |||||
int status; | |||||
String sid; | |||||
Uint8List data; | |||||
AudioModel({required this.status, required this.sid, required this.data}); | |||||
} |
@@ -0,0 +1,15 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'cw.g.dart'; | |||||
@JsonSerializable() | |||||
class Cw { | |||||
int? sc; | |||||
String? w; | |||||
Cw({this.sc, this.w}); | |||||
factory Cw.fromJson(Map<String, dynamic> json) => _$CwFromJson(json); | |||||
Map<String, dynamic> toJson() => _$CwToJson(this); | |||||
} |
@@ -0,0 +1,17 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'cw.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Cw _$CwFromJson(Map<String, dynamic> json) => Cw( | |||||
sc: (json['sc'] as num?)?.toInt(), | |||||
w: json['w'] as String?, | |||||
); | |||||
Map<String, dynamic> _$CwToJson(Cw instance) => <String, dynamic>{ | |||||
'sc': instance.sc, | |||||
'w': instance.w, | |||||
}; |
@@ -0,0 +1,17 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'result.dart'; | |||||
part 'data.g.dart'; | |||||
@JsonSerializable() | |||||
class Data { | |||||
Result? result; | |||||
int? status; | |||||
Data({this.result, this.status}); | |||||
factory Data.fromJson(Map<String, dynamic> json) => _$DataFromJson(json); | |||||
Map<String, dynamic> toJson() => _$DataToJson(this); | |||||
} |
@@ -0,0 +1,19 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'data.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Data _$DataFromJson(Map<String, dynamic> json) => Data( | |||||
result: json['result'] == null | |||||
? null | |||||
: Result.fromJson(json['result'] as Map<String, dynamic>), | |||||
status: (json['status'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$DataToJson(Data instance) => <String, dynamic>{ | |||||
'result': instance.result, | |||||
'status': instance.status, | |||||
}; |
@@ -0,0 +1,21 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'data.dart'; | |||||
part 'phonetic_dictaion_model.g.dart'; | |||||
@JsonSerializable() | |||||
class PhoneticDictaionModel { | |||||
int? code; | |||||
String? message; | |||||
String? sid; | |||||
Data? data; | |||||
PhoneticDictaionModel({this.code, this.message, this.sid, this.data}); | |||||
factory PhoneticDictaionModel.fromJson(Map<String, dynamic> json) { | |||||
return _$PhoneticDictaionModelFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$PhoneticDictaionModelToJson(this); | |||||
} |
@@ -0,0 +1,27 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'phonetic_dictaion_model.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
PhoneticDictaionModel _$PhoneticDictaionModelFromJson( | |||||
Map<String, dynamic> json) => | |||||
PhoneticDictaionModel( | |||||
code: (json['code'] as num?)?.toInt(), | |||||
message: json['message'] as String?, | |||||
sid: json['sid'] as String?, | |||||
data: json['data'] == null | |||||
? null | |||||
: Data.fromJson(json['data'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$PhoneticDictaionModelToJson( | |||||
PhoneticDictaionModel instance) => | |||||
<String, dynamic>{ | |||||
'code': instance.code, | |||||
'message': instance.message, | |||||
'sid': instance.sid, | |||||
'data': instance.data, | |||||
}; |
@@ -0,0 +1,24 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'w.dart'; | |||||
part 'result.g.dart'; | |||||
@JsonSerializable() | |||||
class Result { | |||||
int? sn; | |||||
bool? ls; | |||||
int? bg; | |||||
int? ed; | |||||
String? pgs; | |||||
List<int>? rg; | |||||
List<W>? ws; | |||||
Result({this.sn, this.ls, this.bg, this.ed, this.pgs, this.rg, this.ws}); | |||||
factory Result.fromJson(Map<String, dynamic> json) { | |||||
return _$ResultFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$ResultToJson(this); | |||||
} |
@@ -0,0 +1,31 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'result.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Result _$ResultFromJson(Map<String, dynamic> json) => Result( | |||||
sn: (json['sn'] as num?)?.toInt(), | |||||
ls: json['ls'] as bool?, | |||||
bg: (json['bg'] as num?)?.toInt(), | |||||
ed: (json['ed'] as num?)?.toInt(), | |||||
pgs: json['pgs'] as String?, | |||||
rg: (json['rg'] as List<dynamic>?) | |||||
?.map((e) => (e as num).toInt()) | |||||
.toList(), | |||||
ws: (json['ws'] as List<dynamic>?) | |||||
?.map((e) => W.fromJson(e as Map<String, dynamic>)) | |||||
.toList(), | |||||
); | |||||
Map<String, dynamic> _$ResultToJson(Result instance) => <String, dynamic>{ | |||||
'sn': instance.sn, | |||||
'ls': instance.ls, | |||||
'bg': instance.bg, | |||||
'ed': instance.ed, | |||||
'pgs': instance.pgs, | |||||
'rg': instance.rg, | |||||
'ws': instance.ws, | |||||
}; |
@@ -0,0 +1,17 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'cw.dart'; | |||||
part 'w.g.dart'; | |||||
@JsonSerializable() | |||||
class W { | |||||
int? bg; | |||||
List<Cw>? cw; | |||||
W({this.bg, this.cw}); | |||||
factory W.fromJson(Map<String, dynamic> json) => _$WFromJson(json); | |||||
Map<String, dynamic> toJson() => _$WToJson(this); | |||||
} |
@@ -0,0 +1,19 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'w.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
W _$WFromJson(Map<String, dynamic> json) => W( | |||||
bg: (json['bg'] as num?)?.toInt(), | |||||
cw: (json['cw'] as List<dynamic>?) | |||||
?.map((e) => Cw.fromJson(e as Map<String, dynamic>)) | |||||
.toList(), | |||||
); | |||||
Map<String, dynamic> _$WToJson(W instance) => <String, dynamic>{ | |||||
'bg': instance.bg, | |||||
'cw': instance.cw, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'header.g.dart'; | |||||
@JsonSerializable() | |||||
class Header { | |||||
int? code; | |||||
String? message; | |||||
String? sid; | |||||
int? status; | |||||
Header({this.code, this.message, this.sid, this.status}); | |||||
factory Header.fromJson(Map<String, dynamic> json) { | |||||
return _$HeaderFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$HeaderToJson(this); | |||||
} |
@@ -0,0 +1,21 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'header.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Header _$HeaderFromJson(Map<String, dynamic> json) => Header( | |||||
code: (json['code'] as num?)?.toInt(), | |||||
message: json['message'] as String?, | |||||
sid: json['sid'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$HeaderToJson(Header instance) => <String, dynamic>{ | |||||
'code': instance.code, | |||||
'message': instance.message, | |||||
'sid': instance.sid, | |||||
'status': instance.status, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'recognition_results.dart'; | |||||
part 'payload.g.dart'; | |||||
@JsonSerializable() | |||||
class Payload { | |||||
@JsonKey(name: 'recognition_results') | |||||
RecognitionResults? recognitionResults; | |||||
Payload({this.recognitionResults}); | |||||
factory Payload.fromJson(Map<String, dynamic> json) { | |||||
return _$PayloadFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$PayloadToJson(this); | |||||
} |
@@ -0,0 +1,18 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'payload.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Payload _$PayloadFromJson(Map<String, dynamic> json) => Payload( | |||||
recognitionResults: json['recognition_results'] == null | |||||
? null | |||||
: RecognitionResults.fromJson( | |||||
json['recognition_results'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$PayloadToJson(Payload instance) => <String, dynamic>{ | |||||
'recognition_results': instance.recognitionResults, | |||||
}; |
@@ -0,0 +1,20 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'cw.g.dart'; | |||||
@JsonSerializable() | |||||
class Cw { | |||||
int? rl; | |||||
int? sc; | |||||
String? w; | |||||
int? wb; | |||||
int? wc; | |||||
int? we; | |||||
String? wp; | |||||
Cw({this.rl, this.sc, this.w, this.wb, this.wc, this.we, this.wp}); | |||||
factory Cw.fromJson(Map<String, dynamic> json) => _$CwFromJson(json); | |||||
Map<String, dynamic> toJson() => _$CwToJson(this); | |||||
} |
@@ -0,0 +1,27 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'cw.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Cw _$CwFromJson(Map<String, dynamic> json) => Cw( | |||||
rl: (json['rl'] as num?)?.toInt(), | |||||
sc: (json['sc'] as num?)?.toInt(), | |||||
w: json['w'] as String?, | |||||
wb: (json['wb'] as num?)?.toInt(), | |||||
wc: (json['wc'] as num?)?.toInt(), | |||||
we: (json['we'] as num?)?.toInt(), | |||||
wp: json['wp'] as String?, | |||||
); | |||||
Map<String, dynamic> _$CwToJson(Cw instance) => <String, dynamic>{ | |||||
'rl': instance.rl, | |||||
'sc': instance.sc, | |||||
'w': instance.w, | |||||
'wb': instance.wb, | |||||
'wc': instance.wc, | |||||
'we': instance.we, | |||||
'wp': instance.wp, | |||||
}; |
@@ -0,0 +1,35 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'w.dart'; | |||||
part 'recognition_content.g.dart'; | |||||
@JsonSerializable() | |||||
class RecognitionContent { | |||||
int? bg; | |||||
int? ed; | |||||
bool? ls; | |||||
String? pgs; | |||||
List<int>? rg; | |||||
int? sn; | |||||
@JsonKey(name: 'sub_end') | |||||
bool? subEnd; | |||||
List<W>? ws; | |||||
RecognitionContent({ | |||||
this.bg, | |||||
this.ed, | |||||
this.ls, | |||||
this.pgs, | |||||
this.rg, | |||||
this.sn, | |||||
this.subEnd, | |||||
this.ws, | |||||
}); | |||||
factory RecognitionContent.fromJson(Map<String, dynamic> json) { | |||||
return _$RecognitionContentFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$RecognitionContentToJson(this); | |||||
} |
@@ -0,0 +1,35 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'recognition_content.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
RecognitionContent _$RecognitionContentFromJson(Map<String, dynamic> json) => | |||||
RecognitionContent( | |||||
bg: (json['bg'] as num?)?.toInt(), | |||||
ed: (json['ed'] as num?)?.toInt(), | |||||
ls: json['ls'] as bool?, | |||||
pgs: json['pgs'] as String?, | |||||
rg: (json['rg'] as List<dynamic>?) | |||||
?.map((e) => (e as num).toInt()) | |||||
.toList(), | |||||
sn: (json['sn'] as num?)?.toInt(), | |||||
subEnd: json['sub_end'] as bool?, | |||||
ws: (json['ws'] as List<dynamic>?) | |||||
?.map((e) => W.fromJson(e as Map<String, dynamic>)) | |||||
.toList(), | |||||
); | |||||
Map<String, dynamic> _$RecognitionContentToJson(RecognitionContent instance) => | |||||
<String, dynamic>{ | |||||
'bg': instance.bg, | |||||
'ed': instance.ed, | |||||
'ls': instance.ls, | |||||
'pgs': instance.pgs, | |||||
'rg': instance.rg, | |||||
'sn': instance.sn, | |||||
'sub_end': instance.subEnd, | |||||
'ws': instance.ws, | |||||
}; |
@@ -0,0 +1,17 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'cw.dart'; | |||||
part 'w.g.dart'; | |||||
@JsonSerializable() | |||||
class W { | |||||
int? bg; | |||||
List<Cw>? cw; | |||||
W({this.bg, this.cw}); | |||||
factory W.fromJson(Map<String, dynamic> json) => _$WFromJson(json); | |||||
Map<String, dynamic> toJson() => _$WToJson(this); | |||||
} |
@@ -0,0 +1,19 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'w.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
W _$WFromJson(Map<String, dynamic> json) => W( | |||||
bg: (json['bg'] as num?)?.toInt(), | |||||
cw: (json['cw'] as List<dynamic>?) | |||||
?.map((e) => Cw.fromJson(e as Map<String, dynamic>)) | |||||
.toList(), | |||||
); | |||||
Map<String, dynamic> _$WToJson(W instance) => <String, dynamic>{ | |||||
'bg': instance.bg, | |||||
'cw': instance.cw, | |||||
}; |
@@ -0,0 +1,20 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'header.dart'; | |||||
import 'payload.dart'; | |||||
part 'recognition_result.g.dart'; | |||||
@JsonSerializable() | |||||
class RecognitionResult { | |||||
Header? header; | |||||
Payload? payload; | |||||
RecognitionResult({this.header, this.payload}); | |||||
factory RecognitionResult.fromJson(Map<String, dynamic> json) { | |||||
return _$RecognitionResultFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$RecognitionResultToJson(this); | |||||
} |
@@ -0,0 +1,23 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'recognition_result.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
RecognitionResult _$RecognitionResultFromJson(Map<String, dynamic> json) => | |||||
RecognitionResult( | |||||
header: json['header'] == null | |||||
? null | |||||
: Header.fromJson(json['header'] as Map<String, dynamic>), | |||||
payload: json['payload'] == null | |||||
? null | |||||
: Payload.fromJson(json['payload'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$RecognitionResultToJson(RecognitionResult instance) => | |||||
<String, dynamic>{ | |||||
'header': instance.header, | |||||
'payload': instance.payload, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'recognition_results.g.dart'; | |||||
@JsonSerializable() | |||||
class RecognitionResults { | |||||
String? encoding; | |||||
String? format; | |||||
int? status; | |||||
String? text; | |||||
RecognitionResults({this.encoding, this.format, this.status, this.text}); | |||||
factory RecognitionResults.fromJson(Map<String, dynamic> json) { | |||||
return _$RecognitionResultsFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$RecognitionResultsToJson(this); | |||||
} |
@@ -0,0 +1,23 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'recognition_results.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
RecognitionResults _$RecognitionResultsFromJson(Map<String, dynamic> json) => | |||||
RecognitionResults( | |||||
encoding: json['encoding'] as String?, | |||||
format: json['format'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
text: json['text'] as String?, | |||||
); | |||||
Map<String, dynamic> _$RecognitionResultsToJson(RecognitionResults instance) => | |||||
<String, dynamic>{ | |||||
'encoding': instance.encoding, | |||||
'format': instance.format, | |||||
'status': instance.status, | |||||
'text': instance.text, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'header.g.dart'; | |||||
@JsonSerializable() | |||||
class Header { | |||||
int? code; | |||||
String? message; | |||||
String? sid; | |||||
int? status; | |||||
Header({this.code, this.message, this.sid, this.status}); | |||||
factory Header.fromJson(Map<String, dynamic> json) { | |||||
return _$HeaderFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$HeaderToJson(this); | |||||
} |
@@ -0,0 +1,21 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'header.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Header _$HeaderFromJson(Map<String, dynamic> json) => Header( | |||||
code: (json['code'] as num?)?.toInt(), | |||||
message: json['message'] as String?, | |||||
sid: json['sid'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$HeaderToJson(Header instance) => <String, dynamic>{ | |||||
'code': instance.code, | |||||
'message': instance.message, | |||||
'sid': instance.sid, | |||||
'status': instance.status, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'streamtrans_results.dart'; | |||||
part 'payload.g.dart'; | |||||
@JsonSerializable() | |||||
class Payload { | |||||
@JsonKey(name: 'streamtrans_results') | |||||
StreamtransResults? streamtransResults; | |||||
Payload({this.streamtransResults}); | |||||
factory Payload.fromJson(Map<String, dynamic> json) { | |||||
return _$PayloadFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$PayloadToJson(this); | |||||
} |
@@ -0,0 +1,18 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'payload.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Payload _$PayloadFromJson(Map<String, dynamic> json) => Payload( | |||||
streamtransResults: json['streamtrans_results'] == null | |||||
? null | |||||
: StreamtransResults.fromJson( | |||||
json['streamtrans_results'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$PayloadToJson(Payload instance) => <String, dynamic>{ | |||||
'streamtrans_results': instance.streamtransResults, | |||||
}; |
@@ -0,0 +1,20 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'header.dart'; | |||||
import 'payload.dart'; | |||||
part 'streamtrans_result.g.dart'; | |||||
@JsonSerializable() | |||||
class StreamtransResult { | |||||
Header? header; | |||||
Payload? payload; | |||||
StreamtransResult({this.header, this.payload}); | |||||
factory StreamtransResult.fromJson(Map<String, dynamic> json) { | |||||
return _$StreamtransResultFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$StreamtransResultToJson(this); | |||||
} |
@@ -0,0 +1,23 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'streamtrans_result.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
StreamtransResult _$StreamtransResultFromJson(Map<String, dynamic> json) => | |||||
StreamtransResult( | |||||
header: json['header'] == null | |||||
? null | |||||
: Header.fromJson(json['header'] as Map<String, dynamic>), | |||||
payload: json['payload'] == null | |||||
? null | |||||
: Payload.fromJson(json['payload'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$StreamtransResultToJson(StreamtransResult instance) => | |||||
<String, dynamic>{ | |||||
'header': instance.header, | |||||
'payload': instance.payload, | |||||
}; |
@@ -0,0 +1,28 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'streamtrans_results.g.dart'; | |||||
@JsonSerializable() | |||||
class StreamtransResults { | |||||
String? compress; | |||||
String? encoding; | |||||
String? format; | |||||
String? seq; | |||||
int? status; | |||||
String? text; | |||||
StreamtransResults({ | |||||
this.compress, | |||||
this.encoding, | |||||
this.format, | |||||
this.seq, | |||||
this.status, | |||||
this.text, | |||||
}); | |||||
factory StreamtransResults.fromJson(Map<String, dynamic> json) { | |||||
return _$StreamtransResultsFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$StreamtransResultsToJson(this); | |||||
} |
@@ -0,0 +1,27 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'streamtrans_results.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
StreamtransResults _$StreamtransResultsFromJson(Map<String, dynamic> json) => | |||||
StreamtransResults( | |||||
compress: json['compress'] as String?, | |||||
encoding: json['encoding'] as String?, | |||||
format: json['format'] as String?, | |||||
seq: json['seq'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
text: json['text'] as String?, | |||||
); | |||||
Map<String, dynamic> _$StreamtransResultsToJson(StreamtransResults instance) => | |||||
<String, dynamic>{ | |||||
'compress': instance.compress, | |||||
'encoding': instance.encoding, | |||||
'format': instance.format, | |||||
'seq': instance.seq, | |||||
'status': instance.status, | |||||
'text': instance.text, | |||||
}; |
@@ -0,0 +1,21 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'trans_content.g.dart'; | |||||
@JsonSerializable() | |||||
class TransContent { | |||||
String? src; | |||||
String? dst; | |||||
int? wb; | |||||
int? we; | |||||
@JsonKey(name: 'is_final') | |||||
int? isFinal; | |||||
TransContent({this.src, this.dst, this.wb, this.we, this.isFinal}); | |||||
factory TransContent.fromJson(Map<String, dynamic> json) { | |||||
return _$TransContentFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$TransContentToJson(this); | |||||
} |
@@ -0,0 +1,24 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'trans_content.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
TransContent _$TransContentFromJson(Map<String, dynamic> json) => TransContent( | |||||
src: json['src'] as String?, | |||||
dst: json['dst'] as String?, | |||||
wb: (json['wb'] as num?)?.toInt(), | |||||
we: (json['we'] as num?)?.toInt(), | |||||
isFinal: (json['is_final'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$TransContentToJson(TransContent instance) => | |||||
<String, dynamic>{ | |||||
'src': instance.src, | |||||
'dst': instance.dst, | |||||
'wb': instance.wb, | |||||
'we': instance.we, | |||||
'is_final': instance.isFinal, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'header.g.dart'; | |||||
@JsonSerializable() | |||||
class Header { | |||||
int? code; | |||||
String? message; | |||||
String? sid; | |||||
int? status; | |||||
Header({this.code, this.message, this.sid, this.status}); | |||||
factory Header.fromJson(Map<String, dynamic> json) { | |||||
return _$HeaderFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$HeaderToJson(this); | |||||
} |
@@ -0,0 +1,21 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'header.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Header _$HeaderFromJson(Map<String, dynamic> json) => Header( | |||||
code: (json['code'] as num?)?.toInt(), | |||||
message: json['message'] as String?, | |||||
sid: json['sid'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$HeaderToJson(Header instance) => <String, dynamic>{ | |||||
'code': instance.code, | |||||
'message': instance.message, | |||||
'sid': instance.sid, | |||||
'status': instance.status, | |||||
}; |
@@ -0,0 +1,19 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'tts_results.dart'; | |||||
part 'payload.g.dart'; | |||||
@JsonSerializable() | |||||
class Payload { | |||||
@JsonKey(name: 'tts_results') | |||||
TtsResults? ttsResults; | |||||
Payload({this.ttsResults}); | |||||
factory Payload.fromJson(Map<String, dynamic> json) { | |||||
return _$PayloadFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$PayloadToJson(this); | |||||
} |
@@ -0,0 +1,17 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'payload.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Payload _$PayloadFromJson(Map<String, dynamic> json) => Payload( | |||||
ttsResults: json['tts_results'] == null | |||||
? null | |||||
: TtsResults.fromJson(json['tts_results'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$PayloadToJson(Payload instance) => <String, dynamic>{ | |||||
'tts_results': instance.ttsResults, | |||||
}; |
@@ -0,0 +1,20 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'header.dart'; | |||||
import 'payload.dart'; | |||||
part 'tts_result.g.dart'; | |||||
@JsonSerializable() | |||||
class TtsResult { | |||||
Header? header; | |||||
Payload? payload; | |||||
TtsResult({this.header, this.payload}); | |||||
factory TtsResult.fromJson(Map<String, dynamic> json) { | |||||
return _$TtsResultFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$TtsResultToJson(this); | |||||
} |
@@ -0,0 +1,21 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'tts_result.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
TtsResult _$TtsResultFromJson(Map<String, dynamic> json) => TtsResult( | |||||
header: json['header'] == null | |||||
? null | |||||
: Header.fromJson(json['header'] as Map<String, dynamic>), | |||||
payload: json['payload'] == null | |||||
? null | |||||
: Payload.fromJson(json['payload'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$TtsResultToJson(TtsResult instance) => <String, dynamic>{ | |||||
'header': instance.header, | |||||
'payload': instance.payload, | |||||
}; |
@@ -0,0 +1,16 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'tts_results.g.dart'; | |||||
@JsonSerializable() | |||||
class TtsResults { | |||||
String? audio; | |||||
TtsResults({this.audio}); | |||||
factory TtsResults.fromJson(Map<String, dynamic> json) { | |||||
return _$TtsResultsFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$TtsResultsToJson(this); | |||||
} |
@@ -0,0 +1,16 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'tts_results.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
TtsResults _$TtsResultsFromJson(Map<String, dynamic> json) => TtsResults( | |||||
audio: json['audio'] as String?, | |||||
); | |||||
Map<String, dynamic> _$TtsResultsToJson(TtsResults instance) => | |||||
<String, dynamic>{ | |||||
'audio': instance.audio, | |||||
}; |
@@ -0,0 +1,16 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
part 'data.g.dart'; | |||||
@JsonSerializable() | |||||
class Data { | |||||
String? audio; | |||||
String? ced; | |||||
int? status; | |||||
Data({this.audio, this.ced, this.status}); | |||||
factory Data.fromJson(Map<String, dynamic> json) => _$DataFromJson(json); | |||||
Map<String, dynamic> toJson() => _$DataToJson(this); | |||||
} |
@@ -0,0 +1,19 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'data.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
Data _$DataFromJson(Map<String, dynamic> json) => Data( | |||||
audio: json['audio'] as String?, | |||||
ced: json['ced'] as String?, | |||||
status: (json['status'] as num?)?.toInt(), | |||||
); | |||||
Map<String, dynamic> _$DataToJson(Data instance) => <String, dynamic>{ | |||||
'audio': instance.audio, | |||||
'ced': instance.ced, | |||||
'status': instance.status, | |||||
}; |
@@ -0,0 +1,21 @@ | |||||
import 'package:json_annotation/json_annotation.dart'; | |||||
import 'data.dart'; | |||||
part 'xftts_datamodel.g.dart'; | |||||
@JsonSerializable() | |||||
class XfttsDatamodel { | |||||
int? code; | |||||
String? message; | |||||
String? sid; | |||||
Data? data; | |||||
XfttsDatamodel({this.code, this.message, this.sid, this.data}); | |||||
factory XfttsDatamodel.fromJson(Map<String, dynamic> json) { | |||||
return _$XfttsDatamodelFromJson(json); | |||||
} | |||||
Map<String, dynamic> toJson() => _$XfttsDatamodelToJson(this); | |||||
} |
@@ -0,0 +1,25 @@ | |||||
// GENERATED CODE - DO NOT MODIFY BY HAND | |||||
part of 'xftts_datamodel.dart'; | |||||
// ************************************************************************** | |||||
// JsonSerializableGenerator | |||||
// ************************************************************************** | |||||
XfttsDatamodel _$XfttsDatamodelFromJson(Map<String, dynamic> json) => | |||||
XfttsDatamodel( | |||||
code: (json['code'] as num?)?.toInt(), | |||||
message: json['message'] as String?, | |||||
sid: json['sid'] as String?, | |||||
data: json['data'] == null | |||||
? null | |||||
: Data.fromJson(json['data'] as Map<String, dynamic>), | |||||
); | |||||
Map<String, dynamic> _$XfttsDatamodelToJson(XfttsDatamodel instance) => | |||||
<String, dynamic>{ | |||||
'code': instance.code, | |||||
'message': instance.message, | |||||
'sid': instance.sid, | |||||
'data': instance.data, | |||||
}; |
@@ -2,6 +2,9 @@ import 'dart:async'; | |||||
import 'dart:convert'; | import 'dart:convert'; | ||||
import 'dart:math'; | import 'dart:math'; | ||||
import 'dart:typed_data'; | import 'dart:typed_data'; | ||||
import 'package:demo001/tools/audio_tool.dart'; | |||||
import 'package:demo001/xunfei/recognition_result/recognition_result.dart'; | |||||
import 'package:demo001/xunfei/streamtrans_result/streamtrans_result.dart'; | |||||
import 'package:intl/intl.dart'; | import 'package:intl/intl.dart'; | ||||
import 'package:demo001/xunfei/utils.dart'; | import 'package:demo001/xunfei/utils.dart'; | ||||
import 'package:web_socket_channel/web_socket_channel.dart'; | import 'package:web_socket_channel/web_socket_channel.dart'; | ||||
@@ -22,6 +25,9 @@ class XunFeiTranslate { | |||||
Timer? _timer; | Timer? _timer; | ||||
XunFeiTranslateTask? currtask; | XunFeiTranslateTask? currtask; | ||||
late Function(RecognitionResult) onRecognitionResult; | |||||
late Function(StreamtransResult) onStreamtransResult; | |||||
late Function(AudioModel) onAudioResult; | |||||
final String appId; | final String appId; | ||||
final String apiKey; | final String apiKey; | ||||
@@ -30,22 +36,30 @@ class XunFeiTranslate { | |||||
final String requestUri = "/v1/private/simult_interpretation"; | final String requestUri = "/v1/private/simult_interpretation"; | ||||
//静态变量保存唯一实例 | //静态变量保存唯一实例 | ||||
static XunFeiTranslate? _instance; | static XunFeiTranslate? _instance; | ||||
XunFeiTranslate._internal({ | |||||
required this.appId, | |||||
required this.apiKey, | |||||
required this.apiSecret, | |||||
}); | |||||
XunFeiTranslate._internal( | |||||
{required this.appId, | |||||
required this.apiKey, | |||||
required this.apiSecret, | |||||
required this.onRecognitionResult, | |||||
required this.onStreamtransResult, | |||||
required this.onAudioResult}); | |||||
//工厂构造函数 | //工厂构造函数 | ||||
factory XunFeiTranslate({ | factory XunFeiTranslate({ | ||||
required String appId, | required String appId, | ||||
required String apiKey, | required String apiKey, | ||||
required String apiSecret, | required String apiSecret, | ||||
required Function(RecognitionResult) onRecognitionResult, | |||||
required Function(StreamtransResult) onStreamtransResult, | |||||
required Function(AudioModel) onAudioResult, | |||||
}) { | }) { | ||||
_instance ??= XunFeiTranslate._internal( | _instance ??= XunFeiTranslate._internal( | ||||
appId: appId, | appId: appId, | ||||
apiKey: apiKey, | apiKey: apiKey, | ||||
apiSecret: apiSecret, | apiSecret: apiSecret, | ||||
onRecognitionResult: onRecognitionResult, | |||||
onStreamtransResult: onStreamtransResult, | |||||
onAudioResult: onAudioResult, | |||||
); | ); | ||||
return _instance!; | return _instance!; | ||||
} | } | ||||
@@ -132,14 +146,16 @@ class XunFeiTranslate { | |||||
var state = _checkSpeakingStatus(); | var state = _checkSpeakingStatus(); | ||||
if (state == 1) { | if (state == 1) { | ||||
//开始说话 | //开始说话 | ||||
currtask = XunFeiTranslateTask(_geturl()); | |||||
currtask = XunFeiTranslateTask(_geturl(), _handleData); | |||||
currtask?.sendaudio(_createParams(0, frame)); | currtask?.sendaudio(_createParams(0, frame)); | ||||
print("发送第一帧---------------------------"); | |||||
} else if (state == 2) { | } else if (state == 2) { | ||||
//结束说话 | //结束说话 | ||||
currtask?.sendaudio(_createParams(1, frame)); | currtask?.sendaudio(_createParams(1, frame)); | ||||
} else if (state == 3) { | } else if (state == 3) { | ||||
//结束说话 | //结束说话 | ||||
currtask?.sendaudio(_createParams(2, frame)); | currtask?.sendaudio(_createParams(2, frame)); | ||||
print("发送最后一帧---------------------------"); | |||||
} | } | ||||
}); | }); | ||||
return; | return; | ||||
@@ -148,12 +164,17 @@ class XunFeiTranslate { | |||||
//结束翻译 | //结束翻译 | ||||
Future<void> stoptranslate() async { | Future<void> stoptranslate() async { | ||||
_isrecord = false; | _isrecord = false; | ||||
_timer?.cancel(); | |||||
_timer = null; | _timer = null; | ||||
if (currtask != null) { | if (currtask != null) { | ||||
var _frame = _getAudioData(); | var _frame = _getAudioData(); | ||||
currtask?.sendaudio(_createParams(2, _frame)); | currtask?.sendaudio(_createParams(2, _frame)); | ||||
print("发送最后一帧---------------------------"); | |||||
currtask = null; | currtask = null; | ||||
} | } | ||||
_isspeaking = false; | |||||
_lastBelowThresholdTime = null; | |||||
_buff = Uint8List(0); | |||||
return; | return; | ||||
} | } | ||||
@@ -224,14 +245,44 @@ class XunFeiTranslate { | |||||
return 2; | return 2; | ||||
} | } | ||||
} | } | ||||
//处理返回结果 | |||||
void _handleData(dynamic json) { | |||||
final status = json['header']['status']; | |||||
final sid = json['header']['sid']; | |||||
var payload = json['payload']; | |||||
if (payload != null) { | |||||
payload = json['payload'] as Map<String, dynamic>; | |||||
//转文字的结果 | |||||
if (payload.containsKey('recognition_results')) { | |||||
final model = RecognitionResult.fromJson(json); | |||||
if (model.payload?.recognitionResults?.text == null || | |||||
model.payload?.recognitionResults?.text?.trim() == '') return; | |||||
onRecognitionResult(model); | |||||
//翻译好的结果 | |||||
} else if (payload.containsKey('streamtrans_results')) { | |||||
final model = StreamtransResult.fromJson(json); | |||||
if (model.payload?.streamtransResults?.text == null || | |||||
model.payload?.streamtransResults?.text?.trim() == '') return; | |||||
onStreamtransResult(model); | |||||
//合成语音 | |||||
} else if (payload.containsKey('tts_results')) { | |||||
final bytes = base64Decode(payload['tts_results']['audio']); | |||||
if (bytes.isEmpty) return; | |||||
onAudioResult(AudioModel(status: status, sid: sid, data: bytes)); | |||||
} | |||||
} | |||||
if (status == 2) {} | |||||
} | |||||
} | } | ||||
//讯飞翻译任务 | //讯飞翻译任务 | ||||
class XunFeiTranslateTask { | class XunFeiTranslateTask { | ||||
late WebSocketChannel _channel; | late WebSocketChannel _channel; | ||||
bool isconnected = false; | bool isconnected = false; | ||||
late Function(dynamic) handle; | |||||
XunFeiTranslateTask(String url) { | |||||
XunFeiTranslateTask(String url, Function(dynamic) handle) { | |||||
_channel = WebSocketChannel.connect(Uri.parse(url)); | _channel = WebSocketChannel.connect(Uri.parse(url)); | ||||
_channel.stream.timeout(Duration(seconds: 10)); //设置超时时间 | _channel.stream.timeout(Duration(seconds: 10)); //设置超时时间 | ||||
_channel.stream.listen( | _channel.stream.listen( | ||||
@@ -251,6 +302,7 @@ class XunFeiTranslateTask { | |||||
cancelOnError: true, | cancelOnError: true, | ||||
); | ); | ||||
isconnected = true; | isconnected = true; | ||||
handle = handle; | |||||
} | } | ||||
Future<void> sendaudio(Map<String, dynamic> data) async { | Future<void> sendaudio(Map<String, dynamic> data) async { | ||||
@@ -261,32 +313,13 @@ class XunFeiTranslateTask { | |||||
Future<void> onMessage(String message) async { | Future<void> onMessage(String message) async { | ||||
try { | try { | ||||
print("收到的消息:$message"); | |||||
// print("收到的消息:$message"); | |||||
// 对结果进行解析 | // 对结果进行解析 | ||||
var messageMap = json.decode(message); | var messageMap = json.decode(message); | ||||
var status = messageMap["header"]["status"]; | var status = messageMap["header"]["status"]; | ||||
var sid = messageMap["header"]["sid"]; | |||||
// 接收到的识别结果写到文本 | |||||
if (messageMap.containsKey('payload') && | |||||
messageMap['payload'].containsKey('recognition_results')) { | |||||
var result = messageMap['payload']['recognition_results']['text']; | |||||
var asrresult = utf8.decode(base64.decode(result)); | |||||
} | |||||
//接收到的翻译结果写到文本 | |||||
if (messageMap.containsKey('payload') && | |||||
messageMap['payload'].containsKey('streamtrans_results')) { | |||||
var result = messageMap['payload']['streamtrans_results']['text']; | |||||
var transresult = utf8.decode(base64.decode(result)); | |||||
print("收到翻译结果:$transresult"); | |||||
} | |||||
if (messageMap.containsKey('payload') && | |||||
messageMap['payload'].containsKey('tts_results')) { | |||||
var audio = messageMap['payload']['tts_results']['audio']; | |||||
var audioData = base64.decode(audio); | |||||
print("收到音频结果:${audioData.length}"); | |||||
} | |||||
handle(messageMap); | |||||
if (status == 2) { | if (status == 2) { | ||||
print("任务已结束!"); | |||||
print("任务已结束!------------------------------------------"); | |||||
_channel.sink.close(); | _channel.sink.close(); | ||||
} | } | ||||
} catch (e) { | } catch (e) { | ||||
@@ -6,9 +6,13 @@ | |||||
#include "generated_plugin_registrant.h" | #include "generated_plugin_registrant.h" | ||||
#include <audioplayers_linux/audioplayers_linux_plugin.h> | |||||
#include <record_linux/record_linux_plugin.h> | #include <record_linux/record_linux_plugin.h> | ||||
void fl_register_plugins(FlPluginRegistry* registry) { | void fl_register_plugins(FlPluginRegistry* registry) { | ||||
g_autoptr(FlPluginRegistrar) audioplayers_linux_registrar = | |||||
fl_plugin_registry_get_registrar_for_plugin(registry, "AudioplayersLinuxPlugin"); | |||||
audioplayers_linux_plugin_register_with_registrar(audioplayers_linux_registrar); | |||||
g_autoptr(FlPluginRegistrar) record_linux_registrar = | g_autoptr(FlPluginRegistrar) record_linux_registrar = | ||||
fl_plugin_registry_get_registrar_for_plugin(registry, "RecordLinuxPlugin"); | fl_plugin_registry_get_registrar_for_plugin(registry, "RecordLinuxPlugin"); | ||||
record_linux_plugin_register_with_registrar(record_linux_registrar); | record_linux_plugin_register_with_registrar(record_linux_registrar); | ||||
@@ -3,6 +3,7 @@ | |||||
# | # | ||||
list(APPEND FLUTTER_PLUGIN_LIST | list(APPEND FLUTTER_PLUGIN_LIST | ||||
audioplayers_linux | |||||
record_linux | record_linux | ||||
) | ) | ||||
@@ -6,11 +6,13 @@ import FlutterMacOS | |||||
import Foundation | import Foundation | ||||
import audio_session | import audio_session | ||||
import audioplayers_darwin | |||||
import path_provider_foundation | import path_provider_foundation | ||||
import record_darwin | import record_darwin | ||||
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) { | func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) { | ||||
AudioSessionPlugin.register(with: registry.registrar(forPlugin: "AudioSessionPlugin")) | AudioSessionPlugin.register(with: registry.registrar(forPlugin: "AudioSessionPlugin")) | ||||
AudioplayersDarwinPlugin.register(with: registry.registrar(forPlugin: "AudioplayersDarwinPlugin")) | |||||
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin")) | PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin")) | ||||
RecordPlugin.register(with: registry.registrar(forPlugin: "RecordPlugin")) | RecordPlugin.register(with: registry.registrar(forPlugin: "RecordPlugin")) | ||||
} | } |
@@ -17,6 +17,70 @@ packages: | |||||
url: "https://pub.dev" | url: "https://pub.dev" | ||||
source: hosted | source: hosted | ||||
version: "0.1.24" | version: "0.1.24" | ||||
audio_waveforms: | |||||
dependency: "direct main" | |||||
description: | |||||
name: audio_waveforms | |||||
sha256: "26531204e539708a51a33096a9d509a68f9a748dd1fe1582c5da25add8daa041" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "1.2.0" | |||||
audioplayers: | |||||
dependency: "direct main" | |||||
description: | |||||
name: audioplayers | |||||
sha256: "4ca57fd24594af04e93b9b9f1b1739ffb9204dbab7ce8d9b28a02f464456dcca" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "6.1.1" | |||||
audioplayers_android: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_android | |||||
sha256: "6c9443ce0a99b29a840f14bc2d0f7b25eb0fd946dc592a1b8a697807d5b195f3" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "5.0.1" | |||||
audioplayers_darwin: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_darwin | |||||
sha256: e507887f3ff18d8e5a10a668d7bedc28206b12e10b98347797257c6ae1019c3b | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "6.0.0" | |||||
audioplayers_linux: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_linux | |||||
sha256: "9d3cb4e9533a12a462821e3f18bd282e0fa52f67ff96a06301d48dd48b82c2d1" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "4.0.1" | |||||
audioplayers_platform_interface: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_platform_interface | |||||
sha256: "6834dd48dfb7bc6c2404998ebdd161f79cd3774a7e6779e1348d54a3bfdcfaa5" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "7.0.0" | |||||
audioplayers_web: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_web | |||||
sha256: "3609bdf0e05e66a3d9750ee40b1e37f2a622c4edb796cc600b53a90a30a2ace4" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "5.0.1" | |||||
audioplayers_windows: | |||||
dependency: transitive | |||||
description: | |||||
name: audioplayers_windows | |||||
sha256: "8605762dddba992138d476f6a0c3afd9df30ac5b96039929063eceed416795c2" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "4.0.0" | |||||
boolean_selector: | boolean_selector: | ||||
dependency: transitive | dependency: transitive | ||||
description: | description: | ||||
@@ -89,6 +153,14 @@ packages: | |||||
url: "https://pub.dev" | url: "https://pub.dev" | ||||
source: hosted | source: hosted | ||||
version: "2.1.3" | version: "2.1.3" | ||||
file: | |||||
dependency: transitive | |||||
description: | |||||
name: file | |||||
sha256: a3b4f84adafef897088c160faf7dfffb7696046cb13ae90b508c2cbc95d3b8d4 | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "7.0.1" | |||||
fixnum: | fixnum: | ||||
dependency: transitive | dependency: transitive | ||||
description: | description: | ||||
@@ -144,6 +216,14 @@ packages: | |||||
description: flutter | description: flutter | ||||
source: sdk | source: sdk | ||||
version: "0.0.0" | version: "0.0.0" | ||||
get: | |||||
dependency: "direct main" | |||||
description: | |||||
name: get | |||||
sha256: e4e7335ede17452b391ed3b2ede016545706c01a02292a6c97619705e7d2a85e | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "4.6.6" | |||||
http: | http: | ||||
dependency: "direct main" | dependency: "direct main" | ||||
description: | description: | ||||
@@ -176,6 +256,14 @@ packages: | |||||
url: "https://pub.dev" | url: "https://pub.dev" | ||||
source: hosted | source: hosted | ||||
version: "0.7.1" | version: "0.7.1" | ||||
json_annotation: | |||||
dependency: "direct main" | |||||
description: | |||||
name: json_annotation | |||||
sha256: "1ce844379ca14835a50d2f019a3099f419082cfdd231cd86a142af94dd5c6bb1" | |||||
url: "https://pub.dev" | |||||
source: hosted | |||||
version: "4.9.0" | |||||
leak_tracker: | leak_tracker: | ||||
dependency: transitive | dependency: transitive | ||||
description: | description: | ||||
@@ -43,6 +43,10 @@ dependencies: | |||||
intl: ^0.20.2 | intl: ^0.20.2 | ||||
web_socket_channel: ^3.0.2 | web_socket_channel: ^3.0.2 | ||||
http: ^1.3.0 | http: ^1.3.0 | ||||
get: ^4.6.6 | |||||
json_annotation: ^4.9.0 | |||||
audioplayers: ^6.1.1 | |||||
audio_waveforms: ^1.2.0 | |||||
dev_dependencies: | dev_dependencies: | ||||
flutter_test: | flutter_test: | ||||
@@ -6,10 +6,13 @@ | |||||
#include "generated_plugin_registrant.h" | #include "generated_plugin_registrant.h" | ||||
#include <audioplayers_windows/audioplayers_windows_plugin.h> | |||||
#include <permission_handler_windows/permission_handler_windows_plugin.h> | #include <permission_handler_windows/permission_handler_windows_plugin.h> | ||||
#include <record_windows/record_windows_plugin_c_api.h> | #include <record_windows/record_windows_plugin_c_api.h> | ||||
void RegisterPlugins(flutter::PluginRegistry* registry) { | void RegisterPlugins(flutter::PluginRegistry* registry) { | ||||
AudioplayersWindowsPluginRegisterWithRegistrar( | |||||
registry->GetRegistrarForPlugin("AudioplayersWindowsPlugin")); | |||||
PermissionHandlerWindowsPluginRegisterWithRegistrar( | PermissionHandlerWindowsPluginRegisterWithRegistrar( | ||||
registry->GetRegistrarForPlugin("PermissionHandlerWindowsPlugin")); | registry->GetRegistrarForPlugin("PermissionHandlerWindowsPlugin")); | ||||
RecordWindowsPluginCApiRegisterWithRegistrar( | RecordWindowsPluginCApiRegisterWithRegistrar( | ||||
@@ -3,6 +3,7 @@ | |||||
# | # | ||||
list(APPEND FLUTTER_PLUGIN_LIST | list(APPEND FLUTTER_PLUGIN_LIST | ||||
audioplayers_windows | |||||
permission_handler_windows | permission_handler_windows | ||||
record_windows | record_windows | ||||
) | ) | ||||