record_list.dart 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194
  1. import 'dart:io';
  2. import 'package:audioplayers/audioplayers.dart';
  3. import 'package:flutter/material.dart';
  4. import 'package:fluttertoast/fluttertoast.dart';
  5. // 录音列表
  6. class RecordList extends StatefulWidget {
  7. final List<String> records; //audio列表
  8. const RecordList({
  9. Key? key,
  10. required this.records,
  11. }) : super(key: key);
  12. @override
  13. _RecordListState createState() => _RecordListState();
  14. }
  15. class _RecordListState extends State<RecordList> {
  16. late int _totalTime; // 总时常
  17. late int _currentTime; // 当前播放位置
  18. double _percent = 0.0;
  19. int _selected = -1;
  20. bool isPlay = false;
  21. AudioPlayer advancedPlayer = AudioPlayer();
  22. @override
  23. Widget build(BuildContext context) {
  24. return ListView.builder(
  25. itemCount: widget.records.length,
  26. //滚动条
  27. shrinkWrap: true,
  28. reverse: true,
  29. itemBuilder: (BuildContext context, int i) {
  30. return Card(
  31. elevation: 5,
  32. child: ExpansionTile(
  33. title: Text(
  34. 'Record ${widget.records.length - i}',
  35. style: TextStyle(color: Colors.black),
  36. ),
  37. subtitle: Text(
  38. _getTime(filePath: widget.records.elementAt(i)),
  39. style: TextStyle(color: Colors.black38),
  40. ),
  41. onExpansionChanged: ((newState) {
  42. if (newState) {
  43. setState(() {
  44. _selected = i;
  45. });
  46. }
  47. }),
  48. children: [
  49. Container(
  50. height: 100,
  51. padding: const EdgeInsets.all(10),
  52. child: Column(
  53. mainAxisAlignment: MainAxisAlignment.center,
  54. children: [
  55. LinearProgressIndicator(
  56. minHeight: 5,
  57. backgroundColor: Colors.black,
  58. valueColor: AlwaysStoppedAnimation<Color>(Colors.green),
  59. value: _selected == i ? _percent : 0,
  60. ),
  61. Row(
  62. children: [
  63. (isPlay)
  64. ? _Presso(
  65. ico: Icons.pause,
  66. onPressed: () {
  67. setState(() {
  68. isPlay = false;
  69. });
  70. advancedPlayer.pause();
  71. })
  72. : _Presso(
  73. ico: Icons.play_arrow,
  74. onPressed: () {
  75. setState(() {
  76. isPlay = true;
  77. });
  78. advancedPlayer.play(
  79. widget.records.elementAt(i),
  80. isLocal: true);
  81. setState(() {});
  82. setState(() {
  83. _selected = i;
  84. _percent = 0.0;
  85. });
  86. advancedPlayer.onPlayerCompletion.listen((_) {
  87. setState(() {
  88. _percent = 0.0;
  89. });
  90. });
  91. advancedPlayer.onDurationChanged
  92. .listen((duration) {
  93. setState(() {
  94. _totalTime = duration.inMicroseconds;
  95. });
  96. });
  97. advancedPlayer.onAudioPositionChanged
  98. .listen((duration) {
  99. setState(() {
  100. _currentTime = duration.inMicroseconds;
  101. _percent = _currentTime.toDouble() /
  102. _totalTime.toDouble();
  103. });
  104. });
  105. }),
  106. _Presso(
  107. ico: Icons.stop,
  108. onPressed: () {
  109. advancedPlayer.stop();
  110. setState(() {
  111. _percent = 0.0;
  112. });
  113. }),
  114. _Presso(
  115. ico: Icons.delete,
  116. onPressed: () {
  117. Directory appDirec =
  118. Directory(widget.records.elementAt(i));
  119. appDirec.delete(recursive: true);
  120. Fluttertoast.showToast(msg: "File Deleted");
  121. setState(() {
  122. widget.records
  123. .remove(widget.records.elementAt(i));
  124. });
  125. }),
  126. _Presso(
  127. ico: Icons.share,
  128. onPressed: () {
  129. Directory appDirec =
  130. Directory(widget.records.elementAt(i));
  131. List<String> list = List.empty(growable: true);
  132. list.add(appDirec.path);
  133. // Share.shareFiles(list);
  134. }),
  135. ],
  136. mainAxisAlignment: MainAxisAlignment.spaceEvenly,
  137. ),
  138. ],
  139. ),
  140. ),
  141. ],
  142. ),
  143. );
  144. },
  145. );
  146. }
  147. // 获取文件创建的时间(根据文件名)
  148. String _getTime({required String filePath}) {
  149. String fromPath = filePath.substring(
  150. filePath.lastIndexOf('/') + 1, filePath.lastIndexOf('.'));
  151. if (fromPath.startsWith("1", 0)) {
  152. DateTime dateTime =
  153. DateTime.fromMillisecondsSinceEpoch(int.parse(fromPath));
  154. int year = dateTime.year;
  155. int month = dateTime.month;
  156. int day = dateTime.day;
  157. int hour = dateTime.hour;
  158. int min = dateTime.minute;
  159. String dato = '$year-$month-$day--$hour:$min';
  160. return dato;
  161. } else {
  162. return "No Date";
  163. }
  164. }
  165. }
  166. /// 按钮
  167. class _Presso extends StatelessWidget {
  168. final IconData ico; // 图标
  169. final VoidCallback onPressed; //执行事件
  170. const _Presso({Key? key, required this.ico, required this.onPressed})
  171. : super(key: key);
  172. @override
  173. Widget build(BuildContext context) {
  174. return ButtonTheme(
  175. minWidth: 48.0,
  176. child: ElevatedButton(
  177. child: Icon(
  178. ico,
  179. color: Colors.white,
  180. ),
  181. onPressed: onPressed),
  182. );
  183. }
  184. }