Added player for device default ringtone in settings

This commit is contained in:
Sylvain Berfini 2023-10-03 16:40:36 +02:00
parent 528855c5d5
commit 3bbccf6c89
2 changed files with 81 additions and 10 deletions

View file

@ -19,6 +19,11 @@
*/
package org.linphone.ui.main.settings.viewmodel
import android.content.Context
import android.media.AudioAttributes
import android.media.Ringtone
import android.media.RingtoneManager
import android.net.Uri
import android.os.Vibrator
import androidx.annotation.UiThread
import androidx.annotation.WorkerThread
@ -73,6 +78,7 @@ class SettingsViewModel @UiThread constructor() : ViewModel() {
// Other
private lateinit var ringtonePlayer: Player
private lateinit var deviceRingtonePlayer: Ringtone
private val playerListener = PlayerListener {
Log.i("[$TAG] End of ringtone reached")
@ -201,30 +207,66 @@ class SettingsViewModel @UiThread constructor() : ViewModel() {
fun playPauseRingtone() {
coreContext.postOnCoreThread { core ->
if (!::ringtonePlayer.isInitialized) {
// Also works for ringtone
val playbackDevice = AudioRouteUtils.getAudioPlaybackDeviceIdForCallRecordingOrVoiceMessage()
val player = core.createLocalPlayer(playbackDevice, null, null)
ringtonePlayer = player ?: return@postOnCoreThread
ringtonePlayer.addListener(playerListener)
}
if (ringtonePlayer.state == Player.State.Playing) {
stopRingtonePlayer()
} else {
val path = core.ring.orEmpty()
// TODO FIXME: play device default ringtone if selected
if (ringtonePlayer.open(path) == 0) {
if (ringtonePlayer.start() == 0) {
isRingtonePlaying.postValue(true)
val path = core.ring.orEmpty()
if (path.isEmpty()) {
if (::deviceRingtonePlayer.isInitialized) {
if (deviceRingtonePlayer.isPlaying) {
deviceRingtonePlayer.stop()
isRingtonePlaying.postValue(false)
} else {
Log.e("$TAG Failed to play ringtone [$path]")
playDeviceDefaultRingtone()
}
} else {
Log.e("$TAG Failed to open ringtone [$path]")
playDeviceDefaultRingtone()
}
} else {
if (ringtonePlayer.state == Player.State.Playing) {
stopRingtonePlayer()
} else {
if (ringtonePlayer.open(path) == 0) {
if (ringtonePlayer.start() == 0) {
isRingtonePlaying.postValue(true)
} else {
Log.e("$TAG Failed to play ringtone [$path]")
}
} else {
Log.e("$TAG Failed to open ringtone [$path]")
}
}
}
}
}
@WorkerThread
private fun playDeviceDefaultRingtone() {
val audioAttrs = AudioAttributes.Builder()
.setUsage(AudioAttributes.USAGE_MEDIA)
.setContentType(AudioAttributes.CONTENT_TYPE_MUSIC)
.build()
val defaultRingtoneUri = getDefaultRingtoneUri(coreContext.context)
try {
val ringtone = RingtoneManager.getRingtone(coreContext.context, defaultRingtoneUri)
if (ringtone != null) {
ringtone.audioAttributes = audioAttrs
ringtone.isLooping = true
ringtone.play()
deviceRingtonePlayer = ringtone
isRingtonePlaying.postValue(true)
} else {
Log.e("$TAG Couldn't retrieve Ringtone object from manager!")
}
} catch (e: Exception) {
Log.e("$TAG Failed to play ringtone [", defaultRingtoneUri, "] : ", e)
}
}
@UiThread
fun toggleVibrateOnIncomingCalls() {
val newValue = vibrateDuringIncomingCall.value == false
@ -303,4 +345,30 @@ class SettingsViewModel @UiThread constructor() : ViewModel() {
}
}
}
private fun getDefaultRingtoneUri(context: Context): Uri? {
var uri: Uri? = null
try {
uri =
RingtoneManager.getActualDefaultRingtoneUri(context, RingtoneManager.TYPE_RINGTONE)
} catch (exception: SecurityException) {
}
if (uri == null) {
Log.w("$TAG Failed to get actual default ringtone URI, trying to get a valid one")
uri = RingtoneManager.getValidRingtoneUri(context)
}
if (uri == null) {
Log.w("$TAG Failed to get a valid ringtone URI, trying the first one available")
val ringtoneManager = RingtoneManager(context)
ringtoneManager.setType(RingtoneManager.TYPE_RINGTONE)
val cursor = ringtoneManager.cursor
if (cursor.moveToFirst()) {
val idString = cursor.getString(RingtoneManager.ID_COLUMN_INDEX)
val uriString = cursor.getString(RingtoneManager.URI_COLUMN_INDEX)
uri = Uri.parse("$uriString/$idString")
}
cursor.close()
}
return uri
}
}

View file

@ -284,13 +284,16 @@
android:layout_height="50dp"
android:layout_marginEnd="16dp"
android:layout_marginStart="16dp"
android:layout_marginBottom="@dimen/screen_bottom_margin"
android:background="@drawable/edit_text_background"
android:paddingStart="20dp"
android:paddingEnd="20dp"
android:text="@={viewModel.expire}"
android:inputType="number"
app:layout_constraintVertical_bias="0"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintTop_toBottomOf="@id/expire_title"/>
</androidx.constraintlayout.widget.ConstraintLayout>