Skip to content

Commit 1409e16

Browse files
author
Chenhe
authored
Merge pull request #10 from liangchenhe55/feat/qqhd
新增 QQ HD 支持
2 parents 23980a6 + b367550 commit 1409e16

File tree

11 files changed

+75
-73
lines changed

11 files changed

+75
-73
lines changed

app/build.gradle

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -50,22 +50,15 @@ dependencies {
5050
implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version"
5151

5252
implementation fileTree(include: ['*.jar'], dir: 'libs')
53-
androidTestImplementation('androidx.test.espresso:espresso-core:3.1.0', {
54-
exclude group: 'com.android.support', module: 'support-annotations'
55-
})
56-
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
53+
54+
implementation 'androidx.constraintlayout:constraintlayout:2.0.1'
5755
implementation "androidx.preference:preference-ktx:1.1.1"
5856
implementation "androidx.core:core-ktx:1.3.1"
59-
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
6057
implementation 'com.oasisfeng.nevo:sdk:2.0.0-rc01'
6158
implementation "com.jakewharton.timber:timber:4.7.1"
6259

6360
testImplementation 'junit:junit:4.13'
6461
testImplementation 'org.amshove.kluent:kluent-android:1.61'
65-
66-
}
67-
repositories {
68-
mavenCentral()
6962
}
7063

7164

app/src/main/AndroidManifest.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@
5555

5656
<meta-data
5757
android:name="packages"
58-
android:value="com.tencent.mobileqq|com.tencent.tim|com.tencent.qqlite" />
58+
android:value="com.tencent.mobileqq|com.tencent.tim|com.tencent.qqlite|com.tencent.minihd.qq" />
5959
<meta-data
6060
android:name="settings.activity"
6161
android:value="cc.chenhe.qqnotifyevo.preference.PreferenceAty" />

app/src/main/java/cc/chenhe/qqnotifyevo/core/InnerNotificationProcessor.kt

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import android.content.Context
55
import android.service.notification.StatusBarNotification
66
import androidx.core.app.NotificationManagerCompat
77
import cc.chenhe.qqnotifyevo.utils.NotifyChannel
8+
import cc.chenhe.qqnotifyevo.utils.Tag
89
import timber.log.Timber
910
import java.util.*
1011

@@ -31,24 +32,20 @@ class InnerNotificationProcessor(
3132
// 储存所有通知的 id 以便清除
3233
private val qqNotifyIds: MutableSet<Int> = HashSet()
3334
private val qqLiteNotifyIds: MutableSet<Int> = HashSet()
35+
private val qqHdNotifyIds: MutableSet<Int> = HashSet()
3436
private val timNotifyIds: MutableSet<Int> = HashSet()
3537

3638
/**
3739
* 清空对应来源的通知与历史记录,内部调用了单参 [clearHistory].
3840
*/
39-
fun clearHistory(context: Context, tag: Int) {
41+
fun clearHistory(context: Context, tag: Tag) {
4042
clearHistory(tag)
4143
val ids = when (tag) {
42-
TAG_QQ -> {
43-
qqNotifyIds
44-
}
45-
TAG_QQ_LITE -> {
46-
qqLiteNotifyIds
47-
}
48-
TAG_TIM -> {
49-
timNotifyIds
50-
}
51-
else -> null
44+
Tag.QQ -> qqNotifyIds
45+
Tag.QQ_LITE -> qqLiteNotifyIds
46+
Tag.TIM -> timNotifyIds
47+
Tag.QQ_HD -> qqHdNotifyIds
48+
Tag.UNKNOWN -> null
5249
}
5350
Timber.tag(TAG).v("Clear all evolutionary notifications.")
5451
NotificationManagerCompat.from(context).apply {
@@ -57,13 +54,13 @@ class InnerNotificationProcessor(
5754
}
5855
}
5956

60-
private fun sendNotification(context: Context, @NotificationProcessor.Companion.SourceTag tag: Int, id: Int,
57+
private fun sendNotification(context: Context, tag: Tag, id: Int,
6158
notification: Notification) {
6259
NotificationManagerCompat.from(context).notify(id, notification)
6360
addNotifyId(tag, id)
6461
}
6562

66-
override fun renewQzoneNotification(context: Context, tag: Int, conversation: Conversation,
63+
override fun renewQzoneNotification(context: Context, tag: Tag, conversation: Conversation,
6764
sbn: StatusBarNotification, original: Notification): Notification {
6865

6966
val notification = createQZoneNotification(context, tag, conversation, original).apply {
@@ -76,7 +73,7 @@ class InnerNotificationProcessor(
7673
return notification
7774
}
7875

79-
override fun renewConversionNotification(context: Context, tag: Int, channel: NotifyChannel,
76+
override fun renewConversionNotification(context: Context, tag: Tag, channel: NotifyChannel,
8077
conversation: Conversation, sbn: StatusBarNotification,
8178
original: Notification): Notification {
8279
val history = getHistoryMessage(tag)
@@ -97,11 +94,14 @@ class InnerNotificationProcessor(
9794
return notification ?: Notification() // 此处返回值没有实际意义
9895
}
9996

100-
private fun addNotifyId(@NotificationProcessor.Companion.SourceTag tag: Int, ids: Int) {
97+
private fun addNotifyId(tag: Tag, ids: Int) {
10198
when (tag) {
102-
TAG_QQ -> qqNotifyIds.add(ids)
103-
TAG_TIM -> timNotifyIds.add(ids)
104-
TAG_QQ_LITE -> qqLiteNotifyIds.add(ids)
99+
Tag.QQ -> qqNotifyIds.add(ids)
100+
Tag.QQ_HD -> qqHdNotifyIds.add(ids)
101+
Tag.QQ_LITE -> qqLiteNotifyIds.add(ids)
102+
Tag.TIM -> timNotifyIds.add(ids)
103+
Tag.UNKNOWN -> {
104+
}
105105
}
106106
}
107107
}

app/src/main/java/cc/chenhe/qqnotifyevo/core/NevoNotificationProcessor.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,12 +22,12 @@ class NevoNotificationProcessor(context: Context) : NotificationProcessor(contex
2222
private const val REQ_MULTI_MSG_DONT_SHOW = 2
2323
}
2424

25-
override fun renewQzoneNotification(context: Context, tag: Int, conversation: Conversation,
25+
override fun renewQzoneNotification(context: Context, tag: Tag, conversation: Conversation,
2626
sbn: StatusBarNotification, original: Notification): Notification {
2727
return createQZoneNotification(context, tag, conversation, original)
2828
}
2929

30-
override fun renewConversionNotification(context: Context, tag: Int, channel: NotifyChannel,
30+
override fun renewConversionNotification(context: Context, tag: Tag, channel: NotifyChannel,
3131
conversation: Conversation, sbn: StatusBarNotification,
3232
original: Notification): Notification {
3333
return createConversationNotification(context, tag, channel, conversation, original)

app/src/main/java/cc/chenhe/qqnotifyevo/core/NotificationProcessor.kt

Lines changed: 32 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import android.app.PendingIntent
55
import android.content.Context
66
import android.graphics.Bitmap
77
import android.service.notification.StatusBarNotification
8-
import androidx.annotation.IntDef
98
import androidx.annotation.VisibleForTesting
109
import androidx.core.app.NotificationCompat
1110
import androidx.core.app.Person
@@ -27,36 +26,29 @@ abstract class NotificationProcessor(context: Context) {
2726
/**
2827
* 用于在优化后的通知中保留原始来源标记。通过 [Notification.extras] 提取。
2928
*
30-
* 值为 [Int] 类型,TAG_* 常量。
29+
* 值为 [String] 类型,关联于 [Tag].
3130
*/
3231
const val NOTIFICATION_EXTRA_TAG = "qqevo.tag"
3332

3433
private const val CONVERSATION_NAME_QZONE = "QZone"
3534
private const val CONVERSATION_NAME_QZONE_SPECIAL = "QZoneSpecial" // 特别关心空间动态推送
3635

37-
@Retention(AnnotationRetention.SOURCE)
38-
@IntDef(TAG_UNKNOWN, TAG_QQ, TAG_QQ_LITE, TAG_TIM)
39-
annotation class SourceTag
4036

41-
const val TAG_UNKNOWN = 0
42-
const val TAG_QQ = 1
43-
const val TAG_QQ_LITE = 2
44-
const val TAG_TIM = 3
45-
46-
@SourceTag
47-
fun getTagFromPackageName(packageName: String): Int {
37+
fun getTagFromPackageName(packageName: String): Tag {
4838
return when (packageName) {
49-
"com.tencent.mobileqq" -> TAG_QQ
50-
"com.tencent.tim" -> TAG_TIM
51-
"com.tencent.qqlite" -> TAG_QQ_LITE
52-
else -> TAG_UNKNOWN
39+
"com.tencent.mobileqq" -> Tag.QQ
40+
"com.tencent.tim" -> Tag.TIM
41+
"com.tencent.qqlite" -> Tag.QQ_LITE
42+
"com.tencent.minihd.qq" -> Tag.QQ_HD
43+
else -> Tag.UNKNOWN
5344
}
5445
}
5546

5647
// 群聊消息
5748
// title: 群名 | 群名 (x条新消息)
5849
// ticker: 昵称(群名):消息内容
5950
// text: 昵称: 消息内容 //特别关注前缀:[有关注的内容]
51+
// QQHD v5.8.8.3445 中群里特别关心前缀为 特别关注。
6052

6153
/**
6254
* 匹配群聊消息 Ticker.
@@ -72,9 +64,11 @@ abstract class NotificationProcessor(context: Context) {
7264
* 匹配群聊消息 Content.
7365
*
7466
* Group: 1[有关注的内容
67+
*
68+
* QQHD v5.8.8.3445 中群里特别关心前缀为 特别关注。
7569
*/
7670
@VisibleForTesting
77-
val groupMsgContentPattern: Pattern = Pattern.compile("^(\\[有关注的内容])?[\\s\\S]+")
71+
val groupMsgContentPattern: Pattern = Pattern.compile("^(\\[(?:有关注的内容|特别关注)])?[\\s\\S]+")
7872

7973
// 私聊消息
8074
// title: 昵称 | 昵称 (x条新消息) //特别关心前缀:[特别关心]
@@ -132,6 +126,7 @@ abstract class NotificationProcessor(context: Context) {
132126

133127
private val qqHistory = ArrayList<Conversation>()
134128
private val qqLiteHistory = ArrayList<Conversation>()
129+
private val qqHdHistory = ArrayList<Conversation>()
135130
private val timHistory = ArrayList<Conversation>()
136131

137132
private val avatarManager = AvatarManager.get(getAvatarDiskCacheDir(ctx), getAvatarCachePeriod(context))
@@ -145,7 +140,7 @@ abstract class NotificationProcessor(context: Context) {
145140
*
146141
* @param tag 来源标记。
147142
*/
148-
fun clearHistory(@SourceTag tag: Int) {
143+
fun clearHistory(tag: Tag) {
149144
Timber.tag(TAG).v("Clear history. tag=$tag")
150145
getHistoryMessage(tag).clear()
151146
}
@@ -155,7 +150,7 @@ abstract class NotificationProcessor(context: Context) {
155150
*
156151
* @param tag 来源标记。
157152
*/
158-
private fun clearQzoneSpecialHistory(@SourceTag tag: Int) {
153+
private fun clearQzoneSpecialHistory(tag: Tag) {
159154
Timber.tag(TAG).d("Clear QZone history. tag=$tag")
160155
getHistoryMessage(tag).removeIf {
161156
it.name == qzoneSpecialTitle
@@ -180,7 +175,7 @@ abstract class NotificationProcessor(context: Context) {
180175
*/
181176
protected abstract fun renewQzoneNotification(
182177
context: Context,
183-
@SourceTag tag: Int,
178+
tag: Tag,
184179
conversation: Conversation,
185180
sbn: StatusBarNotification,
186181
original: Notification
@@ -198,7 +193,7 @@ abstract class NotificationProcessor(context: Context) {
198193
*/
199194
protected abstract fun renewConversionNotification(
200195
context: Context,
201-
@SourceTag tag: Int,
196+
tag: Tag,
202197
channel: NotifyChannel,
203198
conversation: Conversation,
204199
sbn: StatusBarNotification,
@@ -216,7 +211,7 @@ abstract class NotificationProcessor(context: Context) {
216211
fun resolveNotification(context: Context, packageName: String, sbn: StatusBarNotification): Notification? {
217212
val original = sbn.notification ?: return null
218213
val tag = getTagFromPackageName(packageName)
219-
if (tag == TAG_UNKNOWN) {
214+
if (tag == Tag.UNKNOWN) {
220215
Timber.tag(TAG).d("Unknown tag, skip. pkgName=$packageName")
221216
return null
222217
}
@@ -329,8 +324,8 @@ abstract class NotificationProcessor(context: Context) {
329324
}
330325

331326
fun onNotificationRemoved(sbn: StatusBarNotification, reason: Int) {
332-
val tag = sbn.notification.extras.getInt(NOTIFICATION_EXTRA_TAG, TAG_UNKNOWN)
333-
if (tag == TAG_UNKNOWN) return
327+
val tag = Tag.valueOf(sbn.notification.extras.getString(NOTIFICATION_EXTRA_TAG, Tag.UNKNOWN.name))
328+
if (tag == Tag.UNKNOWN) return
334329
val title = sbn.notification.extras.getString(Notification.EXTRA_TITLE)
335330
Timber.tag(TAG).v("onNotificationRemoved: Tag=$tag, Reason=$reason, Title=$title")
336331
if (title == qzoneSpecialTitle) {
@@ -393,7 +388,7 @@ abstract class NotificationProcessor(context: Context) {
393388
*/
394389
private fun createNotification(
395390
context: Context,
396-
@SourceTag tag: Int,
391+
tag: Tag,
397392
channel: NotifyChannel,
398393
style: NotificationCompat.Style?,
399394
largeIcon: Bitmap?,
@@ -429,11 +424,11 @@ abstract class NotificationProcessor(context: Context) {
429424
setIcon(context, builder, tag, channel == NotifyChannel.QZONE)
430425

431426
return builder.build().apply {
432-
extras.putInt(NOTIFICATION_EXTRA_TAG, tag)
427+
extras.putString(NOTIFICATION_EXTRA_TAG, tag.name)
433428
}
434429
}
435430

436-
protected fun createQZoneNotification(context: Context, @SourceTag tag: Int, conversation: Conversation,
431+
protected fun createQZoneNotification(context: Context, tag: Tag, conversation: Conversation,
437432
original: Notification): Notification {
438433
val style = NotificationCompat.MessagingStyle(Person.Builder()
439434
.setName(context.getString(R.string.notify_qzone_title)).build())
@@ -454,7 +449,7 @@ abstract class NotificationProcessor(context: Context) {
454449
* @param tag 来源标记。
455450
* @param original 原始通知。
456451
*/
457-
protected fun createConversationNotification(context: Context, @SourceTag tag: Int, channel: NotifyChannel,
452+
protected fun createConversationNotification(context: Context, tag: Tag, channel: NotifyChannel,
458453
conversation: Conversation, original: Notification): Notification {
459454
val style = NotificationCompat.MessagingStyle(Person.Builder().setName(conversation.name).build())
460455
if (conversation.isGroup) {
@@ -522,15 +517,15 @@ abstract class NotificationProcessor(context: Context) {
522517
.build()
523518
}
524519

525-
private fun setIcon(context: Context, builder: NotificationCompat.Builder, tag: Int, isQzone: Boolean) {
520+
private fun setIcon(context: Context, builder: NotificationCompat.Builder, tag: Tag, isQzone: Boolean) {
526521
if (isQzone) {
527522
builder.setSmallIcon(R.drawable.ic_notify_qzone)
528523
return
529524
}
530525
when (getIconMode(context)) {
531526
ICON_AUTO -> when (tag) {
532-
TAG_QQ, TAG_QQ_LITE -> R.drawable.ic_notify_qq
533-
TAG_TIM -> R.drawable.ic_notify_tim
527+
Tag.QQ, Tag.QQ_HD, Tag.QQ_LITE -> R.drawable.ic_notify_qq
528+
Tag.TIM -> R.drawable.ic_notify_tim
534529
else -> R.drawable.ic_notify_qq
535530
}
536531
ICON_QQ -> R.drawable.ic_notify_qq
@@ -543,11 +538,12 @@ abstract class NotificationProcessor(context: Context) {
543538
/**
544539
* 获取历史消息。
545540
*/
546-
protected fun getHistoryMessage(@SourceTag tag: Int): ArrayList<Conversation> {
541+
protected fun getHistoryMessage(tag: Tag): ArrayList<Conversation> {
547542
return when (tag) {
548-
TAG_TIM -> timHistory
549-
TAG_QQ_LITE -> qqLiteHistory
550-
TAG_QQ -> qqHistory
543+
Tag.TIM -> timHistory
544+
Tag.QQ_LITE -> qqLiteHistory
545+
Tag.QQ -> qqHistory
546+
Tag.QQ_HD -> qqHdHistory
551547
else -> throw RuntimeException("Unknown tag: $tag.")
552548
}
553549
}
@@ -560,7 +556,7 @@ abstract class NotificationProcessor(context: Context) {
560556
* @param group 群组名。`null` 表示非群组消息。
561557
* @param special 是否来自特别关心或特别关注。
562558
*/
563-
private fun addMessage(@SourceTag tag: Int, name: String, content: String, group: String?, icon: Bitmap?,
559+
private fun addMessage(tag: Tag, name: String, content: String, group: String?, icon: Bitmap?,
564560
contentIntent: PendingIntent, deleteIntent: PendingIntent, special: Boolean): Conversation {
565561
var conversation: Conversation? = null
566562
// 以会话名为标准寻找已存在的会话

app/src/main/java/cc/chenhe/qqnotifyevo/service/AccessibilityMonitorService.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,9 @@ class AccessibilityMonitorService : AccessibilityService() {
3030
val className = event.className.toString()
3131
if ("com.tencent.mobileqq.activity.SplashActivity" == event.className ||
3232
"com.dataline.activities.LiteActivity" == event.className) {
33-
startService(Intent(this, NotificationMonitorService::class.java).putExtra("tag", tag))
33+
startService(Intent(this, NotificationMonitorService::class.java).putExtra("tag", tag.name))
3434
} else if (className.startsWith("cooperation.qzone.")) {
35-
startService(Intent(this, NotificationMonitorService::class.java).putExtra("tag", tag))
35+
startService(Intent(this, NotificationMonitorService::class.java).putExtra("tag", tag.name))
3636
}
3737
}
3838

app/src/main/java/cc/chenhe/qqnotifyevo/service/NotificationMonitorService.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,9 @@ import android.service.notification.StatusBarNotification
99
import androidx.lifecycle.Lifecycle
1010
import androidx.lifecycle.LifecycleOwner
1111
import androidx.lifecycle.LifecycleRegistry
12-
import androidx.lifecycle.observe
1312
import cc.chenhe.qqnotifyevo.core.InnerNotificationProcessor
1413
import cc.chenhe.qqnotifyevo.utils.MODE_LEGACY
14+
import cc.chenhe.qqnotifyevo.utils.Tag
1515
import cc.chenhe.qqnotifyevo.utils.fetchAvatarCachePeriod
1616
import cc.chenhe.qqnotifyevo.utils.getMode
1717
import timber.log.Timber
@@ -69,7 +69,7 @@ class NotificationMonitorService : NotificationListenerService(), InnerNotificat
6969
if (getMode(this) != MODE_LEGACY)
7070
return Service.START_STICKY
7171
if (intent?.hasExtra("tag") == true) {
72-
processor.clearHistory(ctx, intent.getIntExtra("tag", 0))
72+
processor.clearHistory(ctx, Tag.valueOf(intent.getStringExtra("tag") ?: Tag.UNKNOWN.name))
7373
}
7474
return Service.START_STICKY
7575
}
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
package cc.chenhe.qqnotifyevo.utils
2+
3+
/**
4+
* 用于标记通知的来源。
5+
*/
6+
enum class Tag {
7+
UNKNOWN,
8+
QQ,
9+
QQ_HD,
10+
QQ_LITE,
11+
TIM;
12+
}

app/src/main/java/cc/chenhe/qqnotifyevo/utils/Utils.kt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,8 @@ val packageNameList: List<String>
5151
get() = listOf(
5252
"com.tencent.mobileqq",
5353
"com.tencent.tim",
54-
"com.tencent.qqlite"
54+
"com.tencent.qqlite",
55+
"com.tencent.minihd.qq"
5556
)
5657

5758
/**

0 commit comments

Comments
 (0)