Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

just_audio - Audio player after completer, start from the beginning

I created player audio and I used the just_audio plugin, I have a problem when the audio player completes and does not return to the beginning. I tried to use player.playerStateStream.listen() but when I click on the play icon it does not play the audio and the start duration does not change to 0, but when I manually move the slider it works, how can this problem be solved?

enter image description here

Edit:

What am I need?

I need after audio complete the slider back to the beginning and reset duration just like the first time I played the audio and pause the audio with onPressed play audio.

Code:

String currentTime = "", endTime = "";
double minDuration = 0, maxDuration = 0, currentDuration = 0;

void setAudio(String url) async {
    setState(() => isLoadAudio = true);
    await player.setUrl(url);
    currentDuration = minDuration;
    maxDuration = player.duration!.inMilliseconds.toDouble();
    setState(() {
      currentTime = getDuration(currentDuration);
      endTime = getDuration(maxDuration);
    });
    isPlaying = false;
    changeStatusPlaying();
    player.positionStream.listen((duration) {
      currentDuration = duration.inMilliseconds.toDouble();
      setState(() => currentTime = getDuration(currentDuration));
    });
    setState(() => isLoadAudio = false);
    player.playerStateStream.listen((state) {
      if (state.processingState == ProcessingState.completed) {
        setState(() {
          currentDuration = minDuration;
          if (isRepeating == true) {
            isPlaying = true;
          } else {
            isPlaying = false;
            isRepeating = false;
          }
        });
      }
    });
  }
void changeStatusPlaying() {
    setState(() => isPlaying = !isPlaying);
    isPlaying ? player.play() : player.pause();
    currentDuration == maxDuration ? isPlaying : !isPlaying;
  }

String getDuration(double value) {
    Duration duration = Duration(milliseconds: value.round());
    return [duration.inHours, duration.inMinutes, duration.inSeconds]
        .map((e) => e.remainder(60).toString().padLeft(2, "0"))
        .join(":");
  }

Slider(
   value: currentDuration,
   min: minDuration,
   max: maxDuration,
   onChanged: (v) {
     currentDuration = v;
     playAudio(currentDuration);
   },
),
like image 872
developer1996 Avatar asked Oct 19 '25 04:10

developer1996


1 Answers

Try this:
        
bool _isPlaying = false;
bool _isCompleted = false;
Duration? _duration = Duration.zero;
Duration? _position = Duration.zero; 
                
After player has completed, move position to Duration(seconds: 0)   
                        
            Init state  
                            
                            @override
                              void initState() {
                                _initLoadFile();
                                // Listen player states
                                _audioPlayer.playerStateStream.listen((event) async {
                                  setState(() {
                                    _isPlaying = event.playing;
                                  });
                                  if (event.processingState == ProcessingState.completed) {
                                    setState(() {
                                      _isPlaying = false;
                                      _position = const Duration(seconds: 0);
                                      _isCompleted = true;
                                    });
                                  }
                                });
                                // Listen audio duration
                                _audioPlayer.durationStream.listen((newDuration) {
                                  setState(() {
                                    _duration = newDuration;
                                  });
                                });
                                // Listen audio position
                                _audioPlayer.positionStream.listen((newPosition) {
                                  setState(() {
                                    _position = newPosition;
                                  });
                                });
                                super.initState();
                              }
                            
                            
                    In widget
                            
                    ElevatedButton(
                                  onPressed: () async {
                                    if (!_isPlaying) {
                                      setState(() {
                                        _isPlaying = true;
                                        _isCompleted = false;
                                      });
                                      await _audioPlayer.play();
                                      if (_isCompleted) {
                                        await _audioPlayer.seek(const Duration(seconds: 0));
                                        await _audioPlayer.pause();
                                      }
                                    }
                                    if (_isPlaying) {
                                      setState(() {
                                        _isPlaying = false;
                                      });
                                      await _audioPlayer.pause();
                                    }
                                  },
                                  child: Icon(
                                    _isPlaying ? Icons.pause : Icons.play_arrow,
                                  ),
                                ),
like image 78
jartos Avatar answered Oct 22 '25 06:10

jartos