mirror of
https://gitlab.futo.org/videostreaming/grayjay.git
synced 2025-08-03 14:50:49 +00:00
Fixed case where device fails to acquire audio focus.
This commit is contained in:
parent
0510d34ed3
commit
eb8b02756b
1 changed files with 42 additions and 23 deletions
|
@ -58,6 +58,8 @@ class MediaPlaybackService : Service() {
|
||||||
private var _focusRequest: AudioFocusRequest? = null;
|
private var _focusRequest: AudioFocusRequest? = null;
|
||||||
private var _audioFocusLossTime_ms: Long? = null
|
private var _audioFocusLossTime_ms: Long? = null
|
||||||
private var _playbackState = PlaybackStateCompat.STATE_NONE;
|
private var _playbackState = PlaybackStateCompat.STATE_NONE;
|
||||||
|
private val _handler = Handler(Looper.getMainLooper())
|
||||||
|
private val _audioFocusRunnable = Runnable { setAudioFocus(false) }
|
||||||
|
|
||||||
override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
|
override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
|
||||||
Logger.v(TAG, "onStartCommand");
|
Logger.v(TAG, "onStartCommand");
|
||||||
|
@ -161,6 +163,8 @@ class MediaPlaybackService : Service() {
|
||||||
|
|
||||||
val focusRequest = _focusRequest;
|
val focusRequest = _focusRequest;
|
||||||
if (focusRequest != null) {
|
if (focusRequest != null) {
|
||||||
|
Logger.i(TAG, "Audio focus abandoned")
|
||||||
|
_handler.removeCallbacks(_audioFocusRunnable)
|
||||||
_audioManager?.abandonAudioFocusRequest(focusRequest);
|
_audioManager?.abandonAudioFocusRequest(focusRequest);
|
||||||
_focusRequest = null;
|
_focusRequest = null;
|
||||||
}
|
}
|
||||||
|
@ -342,8 +346,19 @@ class MediaPlaybackService : Service() {
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO: (TBD) This code probably more fitting inside FutoVideoPlayer, as this service is generally only used for global events
|
//TODO: (TBD) This code probably more fitting inside FutoVideoPlayer, as this service is generally only used for global events
|
||||||
private fun setAudioFocus() {
|
private fun setAudioFocus(createFocusRequest: Boolean = true) {
|
||||||
Log.i(TAG, "Requested audio focus.");
|
_handler.removeCallbacks(_audioFocusRunnable)
|
||||||
|
|
||||||
|
if (_hasFocus) {
|
||||||
|
Log.i(TAG, "Skipped trying to get audio focus because audio focus is already obtained.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_focusRequest == null) {
|
||||||
|
if (!createFocusRequest) {
|
||||||
|
Log.i(TAG, "Skipped trying to get audio focus because createFocusRequest = false and no focus request exists.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
val focusRequest = AudioFocusRequest.Builder(AudioManager.AUDIOFOCUS_GAIN)
|
val focusRequest = AudioFocusRequest.Builder(AudioManager.AUDIOFOCUS_GAIN)
|
||||||
.setAcceptsDelayedFocusGain(true)
|
.setAcceptsDelayedFocusGain(true)
|
||||||
|
@ -351,13 +366,26 @@ class MediaPlaybackService : Service() {
|
||||||
.build()
|
.build()
|
||||||
|
|
||||||
_focusRequest = focusRequest;
|
_focusRequest = focusRequest;
|
||||||
val result = _audioManager?.requestAudioFocus(focusRequest)
|
Log.i(TAG, "Created audio focus request.");
|
||||||
|
}
|
||||||
|
|
||||||
|
Log.i(TAG, "Requesting audio focus.");
|
||||||
|
|
||||||
|
val result = _audioManager?.requestAudioFocus(_focusRequest!!)
|
||||||
Log.i(TAG, "Audio focus request result $result");
|
Log.i(TAG, "Audio focus request result $result");
|
||||||
if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
|
if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
|
||||||
//TODO: Handle when not possible to get audio focus
|
|
||||||
_hasFocus = true;
|
_hasFocus = true;
|
||||||
Log.i(TAG, "Audio focus received");
|
Log.i(TAG, "Audio focus received");
|
||||||
|
} else if (result == AudioManager.AUDIOFOCUS_REQUEST_DELAYED) {
|
||||||
|
_hasFocus = false
|
||||||
|
Log.i(TAG, "Audio focus delayed, waiting for focus")
|
||||||
|
} else {
|
||||||
|
_hasFocus = false
|
||||||
|
Log.i(TAG, "Audio focus not granted, retrying in 1 second")
|
||||||
|
_handler.postDelayed(_audioFocusRunnable, 1000)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Log.i(TAG, "Audio focus requested.");
|
||||||
}
|
}
|
||||||
|
|
||||||
private val _audioFocusChangeListener =
|
private val _audioFocusChangeListener =
|
||||||
|
@ -365,8 +393,7 @@ class MediaPlaybackService : Service() {
|
||||||
try {
|
try {
|
||||||
when (focusChange) {
|
when (focusChange) {
|
||||||
AudioManager.AUDIOFOCUS_GAIN -> {
|
AudioManager.AUDIOFOCUS_GAIN -> {
|
||||||
//Do not start playing on gaining audo focus
|
_handler.removeCallbacks(_audioFocusRunnable)
|
||||||
//MediaControlReceiver.onPlayReceived.emit();
|
|
||||||
_hasFocus = true;
|
_hasFocus = true;
|
||||||
Log.i(TAG, "Audio focus gained (restartPlaybackAfterLoss = ${Settings.instance.playback.restartPlaybackAfterLoss}, _audioFocusLossTime_ms = $_audioFocusLossTime_ms)");
|
Log.i(TAG, "Audio focus gained (restartPlaybackAfterLoss = ${Settings.instance.playback.restartPlaybackAfterLoss}, _audioFocusLossTime_ms = $_audioFocusLossTime_ms)");
|
||||||
|
|
||||||
|
@ -385,7 +412,6 @@ class MediaPlaybackService : Service() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
AudioManager.AUDIOFOCUS_LOSS_TRANSIENT -> {
|
AudioManager.AUDIOFOCUS_LOSS_TRANSIENT -> {
|
||||||
MediaControlReceiver.onPauseReceived.emit();
|
|
||||||
if (_playbackState != PlaybackStateCompat.STATE_PAUSED &&
|
if (_playbackState != PlaybackStateCompat.STATE_PAUSED &&
|
||||||
_playbackState != PlaybackStateCompat.STATE_STOPPED &&
|
_playbackState != PlaybackStateCompat.STATE_STOPPED &&
|
||||||
_playbackState != PlaybackStateCompat.STATE_NONE &&
|
_playbackState != PlaybackStateCompat.STATE_NONE &&
|
||||||
|
@ -393,10 +419,13 @@ class MediaPlaybackService : Service() {
|
||||||
_audioFocusLossTime_ms = System.currentTimeMillis()
|
_audioFocusLossTime_ms = System.currentTimeMillis()
|
||||||
}
|
}
|
||||||
|
|
||||||
Log.i(TAG, "Audio focus transient loss");
|
_hasFocus = false;
|
||||||
|
MediaControlReceiver.onPauseReceived.emit();
|
||||||
|
Log.i(TAG, "Audio focus transient loss (_audioFocusLossTime_ms = ${_audioFocusLossTime_ms})");
|
||||||
}
|
}
|
||||||
AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK -> {
|
AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK -> {
|
||||||
Log.i(TAG, "Audio focus transient loss, can duck");
|
Log.i(TAG, "Audio focus transient loss, can duck");
|
||||||
|
_hasFocus = true;
|
||||||
}
|
}
|
||||||
AudioManager.AUDIOFOCUS_LOSS -> {
|
AudioManager.AUDIOFOCUS_LOSS -> {
|
||||||
if (_playbackState != PlaybackStateCompat.STATE_PAUSED &&
|
if (_playbackState != PlaybackStateCompat.STATE_PAUSED &&
|
||||||
|
@ -409,16 +438,6 @@ class MediaPlaybackService : Service() {
|
||||||
_hasFocus = false;
|
_hasFocus = false;
|
||||||
MediaControlReceiver.onPauseReceived.emit();
|
MediaControlReceiver.onPauseReceived.emit();
|
||||||
Log.i(TAG, "Audio focus lost");
|
Log.i(TAG, "Audio focus lost");
|
||||||
|
|
||||||
val activityManager = getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager
|
|
||||||
val runningAppProcesses = activityManager.runningAppProcesses
|
|
||||||
for (processInfo in runningAppProcesses) {
|
|
||||||
// Check the importance of the running app process
|
|
||||||
if (processInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) {
|
|
||||||
// This app is in the foreground, which might have caused the loss of audio focus
|
|
||||||
Log.i("AudioFocus", "App ${processInfo.processName} might have caused the loss of audio focus")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch(ex: Throwable) {
|
} catch(ex: Throwable) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue