From 77a5a7de580143c53aff8231e0be23d6804e6b2a Mon Sep 17 00:00:00 2001 From: tanlongsheng <252620078@qq.com> Date: Sun, 23 Mar 2025 11:59:03 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E4=BC=9A=E8=AE=AE=E5=8A=A9?= =?UTF-8?q?=E6=89=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/data/services/db/database_helper.dart | 49 ++++++++ lib/data/services/db/sqflite_api.dart | 111 ++++++++++++++++++ .../controllers/explore_controller.dart | 2 +- .../meeting_record_controller.dart | 23 +++- .../meeting/views/meeting_record_view.dart | 31 ++--- lib/modules/meeting/views/meeting_view.dart | 59 +--------- pubspec.yaml | 3 + 7 files changed, 202 insertions(+), 76 deletions(-) create mode 100644 lib/data/services/db/database_helper.dart create mode 100644 lib/data/services/db/sqflite_api.dart diff --git a/lib/data/services/db/database_helper.dart b/lib/data/services/db/database_helper.dart new file mode 100644 index 000000000..f8914fa37 --- /dev/null +++ b/lib/data/services/db/database_helper.dart @@ -0,0 +1,49 @@ +import 'dart:async'; +import 'package:path/path.dart'; +import 'package:sqflite/sqflite.dart'; + +class DatabaseHelper { + static final DatabaseHelper _instance = DatabaseHelper._internal(); + factory DatabaseHelper() => _instance; + static Database? _database; + + DatabaseHelper._internal(); + + Future get database async { + if (_database != null) return _database!; + _database = await _initDatabase(); + return _database!; + } + + Future _initDatabase() async { + String path = join( + await getDatabasesPath(), + 'database.db', + ); + return await openDatabase(path, version: 1, onCreate: _createDB); + } + + Future _createDB(Database db, int version) async { + final batch = db.batch(); + // 商务会议助手列表 + batch.execute(''' + CREATE TABLE IF NOT EXISTS meeting ( + id INTEGER PRIMARY KEY, + title TEXT, + content TEXT, + seconds INTEGER, + creationtime INTEGER + ) + '''); + // 商务会议助手详情内容 + batch.execute(''' + CREATE TABLE IF NOT EXISTS meetingdetails ( + id INTEGER PRIMARY KEY, + meetingid INTEGER, + audio BLOB, + content TEXT + ) + '''); + await batch.commit(); + } +} diff --git a/lib/data/services/db/sqflite_api.dart b/lib/data/services/db/sqflite_api.dart new file mode 100644 index 000000000..88543775d --- /dev/null +++ b/lib/data/services/db/sqflite_api.dart @@ -0,0 +1,111 @@ +import 'package:get/get.dart'; + +import 'database_helper.dart'; + +class SqfliteApi { + // 获取商务会议助手列表 + static Future getMeetingList(int page) async { + final db = await DatabaseHelper().database; + return await db.query( + 'meeting', + limit: 10, + offset: (page - 1) * 10, + orderBy: 'creationtime DESC', + ); + } + + // 获取商务会议助手详情 + static Future getMeetingDetails(id) async { + final db = await DatabaseHelper().database; + List meetingList = + await db.query('meeting', where: 'id = ?', whereArgs: [id]); + List detailsList = await db.query( + 'meetingdetails', + where: 'meetingid = ?', + whereArgs: [id], + ); + return { + ...meetingList.first, + 'details': detailsList.first + }; + } + + // 插入商务会议助手 + static Future insertMeeting(Map meeting) async { + final db = await DatabaseHelper().database; + try { + int id = 0; + await db.transaction((txn) async { + id = await txn.insert('meeting', { + 'title': meeting['title'], + 'content': meeting['firstContent'], + 'seconds': meeting['seconds'], + 'creationtime': meeting['creationTime'], + }); + await txn.insert('meetingdetails', { + 'meetingid': id, + 'audio': meeting['audio'], + 'content': meeting['content'], + }); + }); + return id; + } catch (e) { + Get.snackbar( + 'error'.tr, // 错误 + 'unknownError'.tr, + snackPosition: SnackPosition.TOP, + ); + return; + } + } + + // 修改商务会议助手 + static Future editMeeting(id, Map meeting) async { + final db = await DatabaseHelper().database; + try { + await db.transaction((txn) async { + await txn.update( + 'meeting', + { + 'title': meeting['title'], + 'content': meeting['firstContent'], + 'seconds': meeting['seconds'], + }, + where: 'id = ?', + whereArgs: [id], + ); + await txn.update( + 'meetingdetails', + {'content': meeting['content']}, + where: 'meetingid = ?', + whereArgs: [id], + ); + }); + return true; + } catch (e) { + Get.snackbar( + 'error'.tr, // 错误 + 'unknownError'.tr, + snackPosition: SnackPosition.TOP, + ); + return; + } + } + + // 修改商务会议助手标题 + static Future editMeetingTitle(id, title) async { + final db = await DatabaseHelper().database; + await db.update('meeting', {'title': title}, + where: 'id = ?', whereArgs: [id]); + } + + // 删除商务会议助手 + static Future deleteMeeting(id) async { + final db = await DatabaseHelper().database; + await db.transaction((txn) async { + await txn.delete('meeting', where: 'id = ?', whereArgs: [id]); + await txn + .delete('meetingdetails', where: 'meetingid = ?', whereArgs: [id]); + }); + } +} diff --git a/lib/modules/explore/controllers/explore_controller.dart b/lib/modules/explore/controllers/explore_controller.dart index 6c19c5f27..d7e78d624 100644 --- a/lib/modules/explore/controllers/explore_controller.dart +++ b/lib/modules/explore/controllers/explore_controller.dart @@ -66,7 +66,7 @@ class ExploreController extends GetxController { ), AIFeature( title: 'simultaneousTranslation'.tr, // 同声翻译 - description: 'simultaneousTranslationInfo.tr', // 实时翻译80+种语言 + description: 'simultaneousTranslationInfo'.tr, // 实时翻译80+种语言 icon: Icons.translate, startColor: const Color(0xFF4CAF50), endColor: const Color(0xFF009688), diff --git a/lib/modules/meeting/controllers/meeting_record_controller.dart b/lib/modules/meeting/controllers/meeting_record_controller.dart index d00b823c1..ba1c239ac 100644 --- a/lib/modules/meeting/controllers/meeting_record_controller.dart +++ b/lib/modules/meeting/controllers/meeting_record_controller.dart @@ -4,6 +4,7 @@ import 'package:flutter/material.dart'; import 'package:get/get.dart'; import '../../../data/services/asr_service.dart'; +import '../../../data/services/db/sqflite_api.dart'; class MeetingRecordController extends GetxController with GetSingleTickerProviderStateMixin { @@ -15,6 +16,9 @@ class MeetingRecordController extends GetxController RxBool isRecording = false.obs; //是否录音中 RxInt seconds = 0.obs; + String title = ''; + int creationTime = 0; + RxString intermediateContent = ''.obs; RxString finalContent = ''.obs; @@ -25,6 +29,9 @@ class MeetingRecordController extends GetxController super.onInit(); lottieController = AnimationController(vsync: this); _asrService = Get.find(); + final Map args = Get.arguments ?? {}; + title = args['title']; + creationTime = DateTime.now().millisecondsSinceEpoch; } @override @@ -93,6 +100,20 @@ class MeetingRecordController extends GetxController // 完成 void complete() async { - Get.back(); + String firstContent = finalContent.value.length >= 20 + ? finalContent.value.substring(0, 20) + : finalContent.value; + Map data = { + 'title': title, + 'firstContent': firstContent, + 'seconds': seconds.value, + 'creationTime': creationTime, + 'audio': [], + 'content': finalContent.value, + }; + final result = await SqfliteApi.insertMeeting(data); + if (result != null) { + Get.back(); + } } } diff --git a/lib/modules/meeting/views/meeting_record_view.dart b/lib/modules/meeting/views/meeting_record_view.dart index d83db0cc9..1079e699d 100644 --- a/lib/modules/meeting/views/meeting_record_view.dart +++ b/lib/modules/meeting/views/meeting_record_view.dart @@ -95,31 +95,20 @@ class MeetingRecordView extends GetView { child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ - Row( - children: [ - Expanded( - child: Text( - '2025-03-03 录音', - style: TextStyle( - color: isDarkMode ? Colors.white : Colors.black87, - fontSize: 17.sp, - ), - ), - ), - 10.horizontalSpace, - Text( - '中文', - style: TextStyle( - color: isDarkMode ? Colors.white : Colors.black87, - fontSize: 15.sp, - ), - ), - ], + Text( + controller.title, + style: TextStyle( + color: isDarkMode ? Colors.white : Colors.black87, + fontSize: 17.sp, + ), ), Padding( padding: EdgeInsets.symmetric(vertical: 5.w), child: Text( - '2025-03-03 16:18', + DateUtil.formatDateMs( + controller.creationTime, + format: DateFormats.y_mo_d_h_m, + ), style: TextStyle( color: isDarkMode ? Colors.grey[400] : Colors.grey[500], fontSize: 14.sp, diff --git a/lib/modules/meeting/views/meeting_view.dart b/lib/modules/meeting/views/meeting_view.dart index beebef661..88bedda58 100644 --- a/lib/modules/meeting/views/meeting_view.dart +++ b/lib/modules/meeting/views/meeting_view.dart @@ -180,56 +180,6 @@ class MeetingView extends GetView { crossAxisAlignment: CrossAxisAlignment.start, mainAxisSize: MainAxisSize.min, children: [ - Text( - '录音语言转换', - style: TextStyle( - color: isDarkMode ? Colors.white : Colors.black87, - fontSize: 17.sp, - ), - ), - Container( - height: 48.w, - margin: EdgeInsets.only(top: 10.w, bottom: 20.w), - decoration: BoxDecoration( - color: isDarkMode - ? Colors.white.withOpacity(0.05) - : Colors.white, - borderRadius: BorderRadius.circular(12.w), - boxShadow: [ - BoxShadow( - color: isDarkMode - ? Colors.black.withOpacity(0.2) - : Colors.black.withOpacity(0.05), - blurRadius: 10, - offset: const Offset(0, 2), - ), - ], - ), - child: GestureDetector( - onTap: () {}, - child: Padding( - padding: EdgeInsets.symmetric(horizontal: 10.w), - child: Row( - children: [ - Expanded( - child: Text( - '中文', - style: TextStyle( - color: - isDarkMode ? Colors.white : Colors.black87, - fontSize: 16.sp, - ), - ), - ), - Icon( - Icons.keyboard_arrow_right, - color: isDarkMode ? Colors.white : Colors.black87, - ), - ], - ), - ), - ), - ), Text( '录音标题(非必填)', style: TextStyle( @@ -308,12 +258,15 @@ class MeetingView extends GetView { GestureDetector( onTap: () { int time = DateTime.now().millisecondsSinceEpoch; - if (controller.titleController.text.isEmpty) { - controller.titleController.text = + String title = controller.titleController.text; + if (title.isEmpty) { + title = '${DateUtil.formatDateMs(time, format: DateFormats.y_mo_d)} 录音'; } Get.back(); - Get.toNamed(Routes.meetingRecord); + Get.toNamed(Routes.meetingRecord, arguments: { + 'title': title, + }); }, child: Container( width: 120.w, diff --git a/pubspec.yaml b/pubspec.yaml index b023e3efe..be5e1da8c 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -60,6 +60,9 @@ dependencies: # image_cropper: ^9.0.0 dio: ^5.8.0+1 flutter_easyloading: ^3.0.5 + sqflite: ^2.4.2 + path: ^1.9.1 + dev_dependencies: flutter_test: sdk: flutter