Matthias Nott
2026-03-22 15e79ece4127d8eb69e192927d7a65e3ab485354
fix: play/pause toggle - await stop before setting playing ID
1 files modified
changed files
lib/screens/chat_screen.dart patch | view | blame | history
lib/screens/chat_screen.dart
....@@ -71,11 +71,12 @@
7171 if (!mounted) return;
7272
7373 // Listen for playback state changes to reset play button UI
74
+ // Use a brief delay to avoid race between queue transitions
7475 AudioService.onPlaybackStateChanged = () {
75
- if (mounted) {
76
- setState(() {
77
- if (!AudioService.isPlaying) {
78
- _playingMessageId = null;
76
+ if (mounted && !AudioService.isPlaying) {
77
+ Future.delayed(const Duration(milliseconds: 100), () {
78
+ if (mounted && !AudioService.isPlaying) {
79
+ setState(() => _playingMessageId = null);
7980 }
8081 });
8182 }
....@@ -382,6 +383,7 @@
382383 _scrollToBottom();
383384
384385 if (audioData != null && !AudioService.isBackgrounded && !_isCatchingUp && !_isRecording) {
386
+ setState(() => _playingMessageId = storedMessage.id);
385387 AudioService.queueBase64(audioData);
386388 }
387389 }
....@@ -483,6 +485,11 @@
483485 String? _recordingSessionId; // Capture session at recording start
484486
485487 Future<void> _startRecording() async {
488
+ // Stop any playing audio before recording
489
+ if (AudioService.isPlaying) {
490
+ await AudioService.stopPlayback();
491
+ setState(() => _playingMessageId = null);
492
+ }
486493 _recordingSessionId = ref.read(activeSessionIdProvider);
487494 final path = await AudioService.startRecording();
488495 if (path != null) {
....@@ -554,21 +561,21 @@
554561 }
555562 }
556563
557
- void _playMessage(Message message) {
564
+ void _playMessage(Message message) async {
558565 if (message.audioUri == null) return;
559566
560567 // Toggle: if this message is already playing, stop it
561568 if (_playingMessageId == message.id) {
562
- AudioService.stopPlayback();
569
+ await AudioService.stopPlayback();
563570 setState(() => _playingMessageId = null);
564571 return;
565572 }
566573
567
- // Stop any current playback first
568
- if (_playingMessageId != null) {
569
- AudioService.stopPlayback();
570
- }
574
+ // Stop any current playback first, then set playing ID AFTER stop completes
575
+ // (stopPlayback triggers onPlaybackStateChanged which clears _playingMessageId)
576
+ await AudioService.stopPlayback();
571577
578
+ if (!mounted) return;
572579 setState(() => _playingMessageId = message.id);
573580
574581 if (message.audioUri!.startsWith('/')) {