ryanheise / just_audio

Audio Player
1.05k stars 674 forks source link

handleAudioSessionActivation: false not working on iOS #928

Open louisdeveseleer opened 1 year ago

louisdeveseleer commented 1 year ago

Thanks for this great package!

Which API doesn't behave as documented, and how does it misbehave? handleAudioSessionActivation: false does not seem to be working on iOS

Minimal reproduction project https://github.com/louisdeveseleer/just_audio.git Directory to run: just_audio/example

It is the example code, with the handleAudioSessionActivation option set to false when initializing the player:

  final _player = AudioPlayer(
    handleAudioSessionActivation: false,
  );

To Reproduce (i.e. user steps, not code)

Error messages /

Expected behavior Not activating the audio session should prevent the device music from ducking. It works as expected on Android, not on iOS.

Screenshots If applicable, add screenshots to help explain your problem.

Desktop (please complete the following information):

Smartphone (please complete the following information):

**Flutter SDK version 3.3.10

Doctor summary (to see all details, run flutter doctor -v):
[✓] Flutter (Channel stable, 3.3.10, on macOS 13.0.1 22A400 darwin-arm, locale en-US)
[✓] Android toolchain - develop for Android devices (Android SDK version 33.0.0)
[✓] Xcode - develop for iOS and macOS (Xcode 14.2)
[✓] Chrome - develop for the web
[✓] Android Studio (version 2021.2)
[✓] VS Code (version 1.74.3)
[✓] Connected device (4 available)
[✓] HTTP Host Availability

• No issues found!

Additional context /

ryanheise commented 1 year ago

Minimal reproduction project In the example code, simply add the handleAudioSessionActivation: false option when initializing the player:

  final _player = AudioPlayer(
    handleAudioSessionActivation: false,
  );

I think you ignored the two options presented for this section completely and then did something a bit more lazy which I can't act on. Please edit your report according to what was requested in the instructions, thanks.

louisdeveseleer commented 1 year ago

Hey, sorry about that, I added the forked repo containing the modification for testing.

louisdeveseleer commented 1 year ago

@ryanheise Did you get a chance to look into this issue?

ryanheise commented 1 year ago

The code path is the same on iOS and Android, and so you will be able to verify that setActive is not called in either case. Maybe this is just the iOS platform enforcing a policy?

BraveEvidence commented 1 year ago

This will help https://www.youtube.com/watch?v=IMQdSTlTXjA

louisdeveseleer commented 1 year ago

I think I figured it out. When I don't want to device music to duck when playing sounds in the app, I was not initializing a custom audio session. This worked fine on Android: no ducking happening when no audio session initialized. But on iOS it looks like the OS was defaulting to some audio session if the app was not starting one, hence the ducking still happening.

So the solution for iOS was to start an audio session in every case, whether I want to duck the device music or not, and instead change the parameter from AudioSessionConfiguration:

 avAudioSessionCategoryOptions: duckOthers
          ? AVAudioSessionCategoryOptions.duckOthers
          : AVAudioSessionCategoryOptions.mixWithOthers,

For Android, I haven't found how to change the AudioSessionConfiguration parameters to not duck the device music, so I am still using the workaround of simply not starting an audio session when I don't want to duck, and that works. If anyone knows how to configure the audio session on Android to not duck the music, please let me know :-)

nohli commented 1 year ago

@louisdeveseleer how do you make the audio not duck on Android exactly? How to not start an audio session?

I've tried with handleAudioSessionActivation: false, that still ducks Spotify.

ryanheise commented 1 year ago

@nohli Is it possible that even though you told just_audio not to activate the audio session with that option, you may have explicitly activated the audio session yourself by directly using the audio_session package? To use the approach @louisdeveseleer describes, you would need to use audio_session directly, but in order to only have that happen on iOS and not Android, you would need to write an if/block around that audio_session code so that you only do it if the platform is iOS, or else do nothing if it is Android.

nohli commented 1 year ago

Edit: Plugin works as expected.

ryanheise commented 1 year ago

Are you using any other audio plugins which may be activating the audio session? If so, you can't guarantee that calling setActive(false) will work if some other plugin will later set it to true.

I would suggest submitting your own separate bug report for the Android issue, and that way you can submit a minimal reproduction project where the plugin dependencies are also minimal to rule out the chance of interference by other plugins.

nohli commented 1 year ago

@ryanheise sorry it works now. Thanks for your quick support! 🤗

I forgot I had two players, and only changed it for one. 🙈

And kudos for the great plugins with so many customization options!