Skip to content

Commit

Permalink
feat: add ShowExactLastSeenTime
Browse files Browse the repository at this point in the history
  • Loading branch information
cinit committed Sep 3, 2023
1 parent 0160448 commit 51d25a1
Show file tree
Hide file tree
Showing 5 changed files with 94 additions and 0 deletions.
4 changes: 4 additions & 0 deletions app/src/main/java/cc/ioctl/tmoe/fragment/SettingsFragment.kt
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,10 @@ class SettingsFragment : BaseHierarchyFragment() {
HidePremiumStickerSetTab, "HidePremiumStickerSetTab", R.string.HidePremiumStickerSetTab,
"HidePremiumStickerSetTabDesc", R.string.HidePremiumStickerSetTabDesc
)
functionSwitch(
ShowExactLastSeenTime, "ShowExactLastSeenTime", R.string.ShowExactLastSeenTime,
"ShowExactLastSeenTimeDesc", R.string.ShowExactLastSeenTimeDesc
)
}
category("LostMsgMitigation", R.string.LostMsgMitigation) {
functionSwitch(
Expand Down
74 changes: 74 additions & 0 deletions app/src/main/java/cc/ioctl/tmoe/hook/func/ShowExactLastSeenTime.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
package cc.ioctl.tmoe.hook.func

import android.icu.text.SimpleDateFormat
import android.icu.util.Calendar
import cc.ioctl.tmoe.base.annotation.FunctionHookEntry
import cc.ioctl.tmoe.hook.base.CommonDynamicHook
import cc.ioctl.tmoe.ui.LocaleController
import cc.ioctl.tmoe.util.Initiator
import cc.ioctl.tmoe.util.hookBeforeIfEnabled
import java.util.Locale

@FunctionHookEntry
object ShowExactLastSeenTime : CommonDynamicHook() {

private val mFormatterTime = SimpleDateFormat("HH:mm:ss", Locale.ROOT)
private val mFormatterDateTime = SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.ROOT)

override fun initOnce(): Boolean {
// org.telegram.messenger.LocaleController#formatDateOnline
val kLocaleController = Initiator.loadClass("org.telegram.messenger.LocaleController")
val formatDateOnline = kLocaleController.declaredMethods.single {
it.name == "formatDateOnline" && it.parameterTypes.isNotEmpty() && it.parameterTypes[0] == Long::class.java
}
hookBeforeIfEnabled(formatDateOnline) {
val timeMillis = (it.args[0] as Long) * 1000L
val strLastSeenFormatted = LocaleController.getString("LastSeenFormatted")
val strYesterdayAtFormatted = LocaleController.getString("YesterdayAtFormatted")
val strLastSeenDateFormatted = LocaleController.getString("LastSeenDateFormatted")
val hasLocError =
strLastSeenFormatted.contains("LC_ERR") || strYesterdayAtFormatted.contains("LC_ERR") || strLastSeenDateFormatted.contains("LC_ERR")
it.result = when {
hasLocError -> mFormatterDateTime.format(timeMillis) // sigh...
isToday(timeMillis) -> strLastSeenFormatted.format(mFormatterTime.format(timeMillis))
isYesterday(timeMillis) -> {
var shouldBeShorter = false
if (formatDateOnline.parameterTypes.size == 2) {
val madeShort = it.args[1] as? BooleanArray
if (madeShort != null) {
shouldBeShorter = true
madeShort[0] = true
}
}
if (shouldBeShorter) {
strYesterdayAtFormatted.format(mFormatterTime.format(timeMillis))
} else {
strLastSeenFormatted.format(strYesterdayAtFormatted.format(mFormatterTime.format(timeMillis)))
}
}

else -> strLastSeenDateFormatted.format(mFormatterDateTime.format(timeMillis))
}
}
return true
}

private fun isToday(timeMillis: Long): Boolean {
val calendar = Calendar.getInstance()
calendar.timeInMillis = timeMillis
val year = calendar.get(Calendar.YEAR)
val dayOfYear = calendar.get(Calendar.DAY_OF_YEAR)
calendar.timeInMillis = System.currentTimeMillis()
return (year == calendar.get(Calendar.YEAR)) && (dayOfYear == calendar.get(Calendar.DAY_OF_YEAR))
}

private fun isYesterday(timeMillis: Long): Boolean {
val calendar = Calendar.getInstance()
calendar.timeInMillis = timeMillis
val year = calendar.get(Calendar.YEAR)
val dayOfYear = calendar.get(Calendar.DAY_OF_YEAR)
calendar.timeInMillis = System.currentTimeMillis()
return (year == calendar.get(Calendar.YEAR)) && (dayOfYear == calendar.get(Calendar.DAY_OF_YEAR) - 1)
}

}
12 changes: 12 additions & 0 deletions app/src/main/java/cc/ioctl/tmoe/util/HookUtils.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package cc.ioctl.tmoe.util

import cc.ioctl.tmoe.hook.base.CommonDynamicHook
import java.lang.reflect.Method

fun CommonDynamicHook.hookBeforeIfEnabled(method: Method, prior: Int = 50, callback: HookUtils.BeforeHookedMethod) {
HookUtils.hookBeforeIfEnabled(this, method, prior, callback)
}

fun CommonDynamicHook.hookAfterIfEnabled(method: Method, prior: Int = 50, callback: HookUtils.AfterHookedMethod) {
HookUtils.hookAfterIfEnabled(this, method, prior, callback)
}
2 changes: 2 additions & 0 deletions app/src/main/res/values-zh-rCN/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -60,4 +60,6 @@
<string name="DialogTitle_OperationCompleted">操作完成</string>
<string name="DialogTitle_OperationConfirmation">确认操作</string>
<string name="DialogButton_Confirm">确认</string>
<string name="ShowExactLastSeenTime">最后上线精确到秒</string>
<string name="ShowExactLastSeenTimeDesc">仅对有权限查看用户最后上线时间的用户有效</string>
</resources>
2 changes: 2 additions & 0 deletions app/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,8 @@
<string name="LostMsgMitigation">If you have lost messages</string>
<string name="AddReloadMsgBtn">Reload Message Button</string>
<string name="AddReloadMsgBtnDesc">Add Reload Message Button in chat menu</string>
<string name="ShowExactLastSeenTime">Show Exact Last Seen Time</string>
<string name="ShowExactLastSeenTimeDesc">This works if and only if you have permission to see the last seen time of the user.</string>
<string name="DatabaseCorruptionWarning">Database Corruption Warning</string>
<string name="DatabaseCorruptionWarningDesc">Show database corruption warning if detected.</string>
<string name="DumpGroupMember">Persist Access Hash</string>
Expand Down

0 comments on commit 51d25a1

Please sign in to comment.