fix: TTS read-aloud downloads audio via OkHttp before playing
MediaPlayer.setDataSource(url) with HTTPS URLs can silently fail due to certificate issues, redirect handling, or listener race conditions (listeners were set after prepareAsync). Fix: download the WAV file via OkHttp (same client as all other network calls) to a temp file, set listeners before prepareAsync, play from local path. Temp file cleaned up on completion/error.
This commit is contained in:
parent
287cdb4c6b
commit
bb53b24655
1 changed files with 32 additions and 16 deletions
|
|
@ -370,26 +370,42 @@ fun ChatScreen(
|
||||||
}
|
}
|
||||||
|
|
||||||
fun playTtsUrl(url: String, messageId: Long) {
|
fun playTtsUrl(url: String, messageId: Long) {
|
||||||
try {
|
scope.launch {
|
||||||
val player = MediaPlayer().apply {
|
try {
|
||||||
setDataSource(url)
|
val tmpFile = kotlinx.coroutines.withContext(kotlinx.coroutines.Dispatchers.IO) {
|
||||||
prepareAsync()
|
val req = okhttp3.Request.Builder().url(url).build()
|
||||||
setOnPreparedListener { start() }
|
KaizenApi.imageClient.newCall(req).execute().use { resp ->
|
||||||
setOnCompletionListener {
|
if (!resp.isSuccessful) return@withContext null
|
||||||
release()
|
val bytes = resp.body!!.bytes()
|
||||||
ttsPlayerRef.value = null
|
java.io.File.createTempFile("tts_", ".wav", context.cacheDir).also { it.writeBytes(bytes) }
|
||||||
playingTtsForId = null
|
}
|
||||||
}
|
}
|
||||||
setOnErrorListener { _, _, _ ->
|
if (tmpFile == null) {
|
||||||
release()
|
|
||||||
ttsPlayerRef.value = null
|
|
||||||
playingTtsForId = null
|
playingTtsForId = null
|
||||||
true
|
return@launch
|
||||||
}
|
}
|
||||||
|
val player = MediaPlayer().apply {
|
||||||
|
setOnPreparedListener { start() }
|
||||||
|
setOnCompletionListener {
|
||||||
|
release()
|
||||||
|
ttsPlayerRef.value = null
|
||||||
|
playingTtsForId = null
|
||||||
|
tmpFile.delete()
|
||||||
|
}
|
||||||
|
setOnErrorListener { _, _, _ ->
|
||||||
|
release()
|
||||||
|
ttsPlayerRef.value = null
|
||||||
|
playingTtsForId = null
|
||||||
|
tmpFile.delete()
|
||||||
|
true
|
||||||
|
}
|
||||||
|
setDataSource(tmpFile.absolutePath)
|
||||||
|
prepareAsync()
|
||||||
|
}
|
||||||
|
ttsPlayerRef.value = player
|
||||||
|
} catch (_: Exception) {
|
||||||
|
playingTtsForId = null
|
||||||
}
|
}
|
||||||
ttsPlayerRef.value = player
|
|
||||||
} catch (_: Exception) {
|
|
||||||
playingTtsForId = null
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue