This commit is contained in:
Horis
2023-06-20 18:11:45 +08:00
parent c621e3a670
commit 883a0bea4e
@@ -26,13 +26,14 @@ import io.legado.app.utils.printOnDebug
import io.legado.app.utils.servicePendingIntent
import io.legado.app.utils.toastOnUi
import kotlinx.coroutines.CancellationException
import kotlinx.coroutines.Dispatchers.IO
import kotlinx.coroutines.Dispatchers.Main
import kotlinx.coroutines.Job
import kotlinx.coroutines.delay
import kotlinx.coroutines.ensureActive
import kotlinx.coroutines.launch
import kotlinx.coroutines.sync.Mutex
import kotlinx.coroutines.sync.withLock
import kotlinx.coroutines.withContext
import okhttp3.Response
import org.mozilla.javascript.WrappedException
import java.io.File
@@ -68,32 +69,22 @@ class HttpReadAloudService : BaseReadAloudService(),
super.onDestroy()
downloadTask?.cancel()
exoPlayer.release()
Coroutine.async {
removeCacheFile()
}
}
override fun play() {
pageChanged = false
exoPlayer.stop()
exoPlayer.clearMediaItems()
if (!requestFocus()) return
if (contentList.isEmpty()) {
AppLog.putDebug("朗读列表为空")
ReadBook.readAloud()
} else {
super.play()
kotlin.runCatching {
if (nowSpeak == 0) {
downloadAudio()
} else {
val fileName = md5SpeakFileName(contentList[nowSpeak])
val file = getSpeakFileAsMd5(fileName)
if (file.exists()) {
playAudio(file)
} else if (!downloadTaskActiveLock.isLocked) {
downloadAudio()
}
}
}.onFailure {
toastOnUi("朗读出错:${it.localizedMessage}")
AppLog.put("朗读出错:${it.localizedMessage}", it)
}
downloadAndPlayAudios()
}
}
@@ -105,21 +96,20 @@ class HttpReadAloudService : BaseReadAloudService(),
readAloudNumber += contentList[nowSpeak].length + 1
if (nowSpeak < contentList.lastIndex) {
nowSpeak++
play()
} else {
nextChapter()
}
}
private fun downloadAudio() {
private fun downloadAndPlayAudios() {
downloadTask?.cancel()
downloadTask = execute {
downloadTaskActiveLock.withLock {
ensureActive()
removeCacheFile()
val httpTts = ReadAloud.httpTTS ?: throw NoStackTraceException("tts is null")
contentList.forEachIndexed { index, content ->
ensureActive()
if (index < nowSpeak) return@forEachIndexed
val fileName = md5SpeakFileName(content)
val speakText = content.replace(AppPattern.notReadAloudRegex, "")
if (speakText.isEmpty()) {
@@ -141,13 +131,19 @@ class HttpReadAloudService : BaseReadAloudService(),
return@execute
}
}
if (index == nowSpeak) {
val file = getSpeakFileAsMd5(fileName)
playAudio(file)
val file = getSpeakFileAsMd5(fileName)
val mediaItem = MediaItem.fromUri(Uri.fromFile(file))
launch(Main) {
exoPlayer.addMediaItem(mediaItem)
if (!exoPlayer.isPlaying && nowSpeak == index) {
exoPlayer.playWhenReady = true
exoPlayer.prepare()
}
}
}
}
}.onError(IO) {
}.onError {
toastOnUi("朗读出错:${it.localizedMessage}")
AppLog.put("朗读下载出错\n${it.localizedMessage}", it)
}
}
@@ -193,6 +189,7 @@ class HttpReadAloudService : BaseReadAloudService(),
e.printOnDebug()
throw e
}
is SocketTimeoutException, is ConnectException -> {
downloadErrorNo++
if (downloadErrorNo > 5) {
@@ -202,6 +199,7 @@ class HttpReadAloudService : BaseReadAloudService(),
throw e
}
}
else -> {
downloadErrorNo++
val msg = "tts下载错误\n${e.localizedMessage}"
@@ -223,22 +221,6 @@ class HttpReadAloudService : BaseReadAloudService(),
return null
}
@Synchronized
private fun playAudio(file: File) {
if (requestFocus()) {
launch {
kotlin.runCatching {
val mediaItem = MediaItem.fromUri(Uri.fromFile(file))
exoPlayer.setMediaItem(mediaItem)
exoPlayer.playWhenReady = true
exoPlayer.prepare()
}.onFailure {
it.printOnDebug()
}
}
}
}
private fun md5SpeakFileName(content: String): String {
return MD5Utils.md5Encode16(textChapter?.title ?: "") + "_" +
MD5Utils.md5Encode16("${ReadAloud.httpTTS?.url}-|-$speechRate-|-$content")
@@ -338,7 +320,7 @@ class HttpReadAloudService : BaseReadAloudService(),
downloadTask?.cancel()
exoPlayer.stop()
speechRate = AppConfig.speechRatePlay + 5
downloadAudio()
downloadAndPlayAudios()
}
override fun onPlaybackStateChanged(playbackState: Int) {
@@ -347,15 +329,18 @@ class HttpReadAloudService : BaseReadAloudService(),
Player.STATE_IDLE -> {
// 空闲
}
Player.STATE_BUFFERING -> {
// 缓冲中
}
Player.STATE_READY -> {
// 准备好
if (pause) return
exoPlayer.play()
upPlayPos()
}
Player.STATE_ENDED -> {
// 结束
playErrorNo = 0
@@ -364,6 +349,12 @@ class HttpReadAloudService : BaseReadAloudService(),
}
}
override fun onMediaItemTransition(mediaItem: MediaItem?, reason: Int) {
if (reason == Player.MEDIA_ITEM_TRANSITION_REASON_PLAYLIST_CHANGED) return
upPlayPos()
playNext()
}
override fun onPlayerError(error: PlaybackException) {
super.onPlayerError(error)
AppLog.put("朗读错误\n${contentList[nowSpeak]}", error)