feat(core): opera media quick info

- add creation timestamp to MediaDownloader instead of current timestamp
This commit is contained in:
rhunk
2023-11-22 22:22:15 +01:00
parent 15c56b705f
commit 752f87179f
4 changed files with 90 additions and 10 deletions

View File

@ -72,8 +72,8 @@ class SnapChapterInfo(
@OptIn(ExperimentalEncodingApi::class)
class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleType.AUTO_DOWNLOAD, loadParams = FeatureLoadParams.ACTIVITY_CREATE_ASYNC) {
private var lastSeenMediaInfoMap: MutableMap<SplitMediaAssetType, MediaInfo>? = null
private var lastSeenMapParams: ParamMap? = null
var lastSeenMapParams: ParamMap? = null
private set
private val translations by lazy {
context.translation.getCategory("download_processor")
}
@ -81,6 +81,7 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
private fun provideDownloadManagerClient(
mediaIdentifier: String,
mediaAuthor: String,
creationTimestamp: Long? = null,
downloadSource: MediaDownloadSource,
friendInfo: FriendInfo? = null
): DownloadManagerClient {
@ -93,7 +94,7 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
context.shortToast(translations["download_started_toast"])
}
val outputPath = createNewFilePath(generatedHash, downloadSource, mediaAuthor)
val outputPath = createNewFilePath(generatedHash, downloadSource, mediaAuthor, creationTimestamp)
return DownloadManagerClient(
context = context,
@ -133,11 +134,16 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
}
private fun createNewFilePath(hexHash: String, downloadSource: MediaDownloadSource, mediaAuthor: String): String {
private fun createNewFilePath(
hexHash: String,
downloadSource: MediaDownloadSource,
mediaAuthor: String,
creationTimestamp: Long?
): String {
val pathFormat by context.config.downloader.pathFormat
val sanitizedMediaAuthor = mediaAuthor.sanitizeForPath().ifEmpty { hexHash }
val currentDateTime = SimpleDateFormat("yyyy-MM-dd_HH-mm-ss", Locale.ENGLISH).format(System.currentTimeMillis())
val currentDateTime = SimpleDateFormat("yyyy-MM-dd_HH-mm-ss", Locale.ENGLISH).format(creationTimestamp ?: System.currentTimeMillis())
val finalPath = StringBuilder()
@ -299,6 +305,7 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
downloadOperaMedia(provideDownloadManagerClient(
mediaIdentifier = "$conversationId$senderId${conversationMessage.serverMessageId}$mediaId",
mediaAuthor = authorUsername,
creationTimestamp = conversationMessage.creationTimestamp,
downloadSource = MediaDownloadSource.CHAT_MEDIA,
friendInfo = author
), mediaInfoMap)
@ -343,6 +350,8 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
downloadOperaMedia(provideDownloadManagerClient(
mediaIdentifier = paramMap["MEDIA_ID"].toString(),
mediaAuthor = authorName,
creationTimestamp = paramMap["PLAYABLE_STORY_SNAP_RECORD"]?.toString()?.substringAfter("timestamp=")
?.substringBefore(",")?.toLongOrNull(),
downloadSource = MediaDownloadSource.STORY,
friendInfo = author
), mediaInfoMap)
@ -360,6 +369,7 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
mediaIdentifier = paramMap["SNAP_ID"].toString(),
mediaAuthor = userDisplayName,
downloadSource = MediaDownloadSource.PUBLIC_STORY,
creationTimestamp = paramMap["SNAP_TIMESTAMP"]?.toString()?.toLongOrNull(),
), mediaInfoMap)
return
}
@ -369,7 +379,8 @@ class MediaDownloader : MessagingRuleFeature("MediaDownloader", MessagingRuleTyp
downloadOperaMedia(provideDownloadManagerClient(
mediaIdentifier = paramMap["SNAP_ID"].toString(),
downloadSource = MediaDownloadSource.SPOTLIGHT,
mediaAuthor = paramMap["TIME_STAMP"].toString()
mediaAuthor = paramMap["CREATOR_DISPLAY_NAME"].toString(),
creationTimestamp = paramMap["SNAP_TIMESTAMP"]?.toString()?.toLongOrNull(),
), mediaInfoMap)
return
}

View File

@ -7,11 +7,15 @@ import android.view.ViewGroup
import android.widget.Button
import android.widget.LinearLayout
import android.widget.ScrollView
import android.widget.TextView
import me.rhunk.snapenhance.core.features.impl.downloader.MediaDownloader
import me.rhunk.snapenhance.core.ui.applyTheme
import me.rhunk.snapenhance.core.ui.menu.AbstractMenu
import me.rhunk.snapenhance.core.ui.triggerCloseTouchEvent
import me.rhunk.snapenhance.core.util.ktx.getId
import me.rhunk.snapenhance.core.wrapper.impl.ScSize
import java.text.DateFormat
import java.util.Date
@SuppressLint("DiscouragedApi")
class OperaContextActionMenu : AbstractMenu() {
@ -67,11 +71,65 @@ class OperaContextActionMenu : AbstractMenu() {
ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT
)
val translation = context.translation
val translation = context.translation.getCategory("opera_context_menu")
val mediaDownloader = context.feature(MediaDownloader::class)
val paramMap = mediaDownloader.lastSeenMapParams
if (paramMap != null && context.config.userInterface.operaMediaQuickInfo.get()) {
val playableStorySnapRecord = paramMap["PLAYABLE_STORY_SNAP_RECORD"]?.toString()
val sentTimestamp = playableStorySnapRecord?.substringAfter("timestamp=")
?.substringBefore(",")?.toLongOrNull()
?: paramMap["MESSAGE_ID"]?.toString()?.let { messageId ->
context.database.getConversationMessageFromId(
messageId.substring(messageId.lastIndexOf(":") + 1)
.toLong()
)?.creationTimestamp
}
?: paramMap["SNAP_TIMESTAMP"]?.toString()?.toLongOrNull()
val dateFormat = DateFormat.getDateTimeInstance()
val creationTimestamp = playableStorySnapRecord?.substringAfter("creationTimestamp=")
?.substringBefore(",")?.toLongOrNull()
val expirationTimestamp = playableStorySnapRecord?.substringAfter("expirationTimestamp=")
?.substringBefore(",")?.toLongOrNull()
?: paramMap["SNAP_EXPIRATION_TIMESTAMP_MILLIS"]?.toString()?.toLongOrNull()
val mediaSize = paramMap["snap_size"]?.let { ScSize(it) }
val durationMs = paramMap["media_duration_ms"]?.toString()
val stringBuilder = StringBuilder().apply {
if (sentTimestamp != null) {
append(translation.format("sent_at", "date" to dateFormat.format(Date(sentTimestamp))))
append("\n")
}
if (creationTimestamp != null) {
append(translation.format("created_at", "date" to dateFormat.format(Date(creationTimestamp))))
append("\n")
}
if (expirationTimestamp != null) {
append(translation.format("expires_at", "date" to dateFormat.format(Date(expirationTimestamp))))
append("\n")
}
if (mediaSize != null) {
append(translation.format("media_size", "size" to "${mediaSize.first}x${mediaSize.second}"))
append("\n")
}
if (durationMs != null) {
append(translation.format("media_duration", "duration" to durationMs))
append("\n")
}
if (last() == '\n') deleteCharAt(length - 1)
}
if (stringBuilder.isNotEmpty()) {
linearLayout.addView(TextView(view.context).apply {
text = stringBuilder.toString()
setPadding(40, 10, 0, 0)
})
}
}
linearLayout.addView(Button(view.context).apply {
text = translation["opera_context_menu.download"]
text = translation["download"]
setOnClickListener {
mediaDownloader.downloadLastOperaMediaAsync()
parentView.triggerCloseTouchEvent()
@ -81,7 +139,7 @@ class OperaContextActionMenu : AbstractMenu() {
if (context.isDeveloper) {
linearLayout.addView(Button(view.context).apply {
text = "Show debug info"
text = translation["show_debug_info"]
setOnClickListener { mediaDownloader.showLastOperaDebugMediaInfo() }
applyTheme(isAmoled = false)
})