mirror of
https://github.com/SchildiChat/SchildiChat-android.git
synced 2024-11-23 01:45:52 +03:00
using a process state of keep/removed rather than mapping to an ignored event id
- this state will be used to diff the currently rendered events against the new ones
This commit is contained in:
parent
b7b4c01bde
commit
b27fb264fc
5 changed files with 56 additions and 43 deletions
|
@ -17,6 +17,8 @@
|
|||
package im.vector.app.features.notifications
|
||||
|
||||
import im.vector.app.features.invite.AutoAcceptInvites
|
||||
import im.vector.app.features.notifications.Processed.KEEP
|
||||
import im.vector.app.features.notifications.Processed.REMOVE
|
||||
import javax.inject.Inject
|
||||
|
||||
class NotifiableEventProcessor @Inject constructor(
|
||||
|
@ -24,20 +26,26 @@ class NotifiableEventProcessor @Inject constructor(
|
|||
private val autoAcceptInvites: AutoAcceptInvites
|
||||
) {
|
||||
|
||||
fun process(eventList: List<NotifiableEvent>, currentRoomId: String?): Map<String, NotifiableEvent?> {
|
||||
return eventList.associateBy { it.eventId }
|
||||
.mapValues { (_, value) ->
|
||||
when (value) {
|
||||
is InviteNotifiableEvent -> if (autoAcceptInvites.hideInvites) null else value
|
||||
is NotifiableMessageEvent -> if (shouldIgnoreMessageEventInRoom(currentRoomId, value.roomId) || outdatedDetector.isMessageOutdated(value)) {
|
||||
null
|
||||
} else value
|
||||
is SimpleNotifiableEvent -> value
|
||||
}
|
||||
}
|
||||
fun process(eventList: List<NotifiableEvent>, currentRoomId: String?): List<Pair<Processed, NotifiableEvent>> {
|
||||
return eventList.map {
|
||||
when (it) {
|
||||
is InviteNotifiableEvent -> if (autoAcceptInvites.hideInvites) REMOVE else KEEP
|
||||
is NotifiableMessageEvent -> if (shouldIgnoreMessageEventInRoom(currentRoomId, it.roomId) || outdatedDetector.isMessageOutdated(it)) {
|
||||
REMOVE
|
||||
} else KEEP
|
||||
is SimpleNotifiableEvent -> KEEP
|
||||
} to it
|
||||
}
|
||||
}
|
||||
|
||||
private fun shouldIgnoreMessageEventInRoom(currentRoomId: String?, roomId: String?): Boolean {
|
||||
return currentRoomId != null && roomId == currentRoomId
|
||||
}
|
||||
}
|
||||
|
||||
enum class Processed {
|
||||
KEEP,
|
||||
REMOVE
|
||||
}
|
||||
|
||||
fun List<Pair<Processed, NotifiableEvent>>.onlyKeptEvents() = filter { it.first == KEEP }.map { it.second }
|
||||
|
|
|
@ -56,7 +56,7 @@ class NotificationDrawerManager @Inject constructor(private val context: Context
|
|||
}
|
||||
|
||||
private val eventList = loadEventInfo()
|
||||
private var renderedEventsList = emptyMap<String, NotifiableEvent?>()
|
||||
private var renderedEventsList = emptyList<Pair<Processed, NotifiableEvent>>()
|
||||
private val avatarSize = context.resources.getDimensionPixelSize(R.dimen.profile_avatar_size)
|
||||
private var currentRoomId: String? = null
|
||||
|
||||
|
@ -236,10 +236,12 @@ class NotificationDrawerManager @Inject constructor(private val context: Context
|
|||
val eventsToRender = synchronized(eventList) {
|
||||
notifiableEventProcessor.process(eventList, currentRoomId).also {
|
||||
eventList.clear()
|
||||
eventList.addAll(it.values.filterNotNull())
|
||||
eventList.addAll(it.onlyKeptEvents())
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
if (renderedEventsList == eventsToRender) {
|
||||
Timber.d("Skipping notification update due to event list not changing")
|
||||
} else {
|
||||
|
|
|
@ -40,14 +40,14 @@ class NotificationFactory @Inject constructor(
|
|||
|
||||
private fun NotifiableMessageEvent.canNotBeDisplayed() = isRedacted
|
||||
|
||||
fun Map<String, InviteNotifiableEvent?>.toNotifications(myUserId: String): List<OneShotNotification> {
|
||||
return map { (roomId, event) ->
|
||||
when (event) {
|
||||
null -> OneShotNotification.Removed(key = roomId)
|
||||
else -> OneShotNotification.Append(
|
||||
fun List<Pair<Processed, InviteNotifiableEvent>>.toNotifications(myUserId: String): List<OneShotNotification> {
|
||||
return map { (processed, event) ->
|
||||
when (processed) {
|
||||
Processed.REMOVE -> OneShotNotification.Removed(key = event.roomId)
|
||||
Processed.KEEP -> OneShotNotification.Append(
|
||||
notificationUtils.buildRoomInvitationNotification(event, myUserId),
|
||||
OneShotNotification.Append.Meta(
|
||||
key = roomId,
|
||||
key = event.roomId,
|
||||
summaryLine = event.description,
|
||||
isNoisy = event.noisy,
|
||||
timestamp = event.timestamp
|
||||
|
@ -58,14 +58,14 @@ class NotificationFactory @Inject constructor(
|
|||
}
|
||||
|
||||
@JvmName("toNotificationsSimpleNotifiableEvent")
|
||||
fun Map<String, SimpleNotifiableEvent?>.toNotifications(myUserId: String): List<OneShotNotification> {
|
||||
return map { (eventId, event) ->
|
||||
when (event) {
|
||||
null -> OneShotNotification.Removed(key = eventId)
|
||||
else -> OneShotNotification.Append(
|
||||
fun List<Pair<Processed, SimpleNotifiableEvent>>.toNotifications(myUserId: String): List<OneShotNotification> {
|
||||
return map { (processed, event) ->
|
||||
when (processed) {
|
||||
Processed.REMOVE -> OneShotNotification.Removed(key = event.eventId)
|
||||
Processed.KEEP -> OneShotNotification.Append(
|
||||
notificationUtils.buildSimpleEventNotification(event, myUserId),
|
||||
OneShotNotification.Append.Meta(
|
||||
key = eventId,
|
||||
key = event.eventId,
|
||||
summaryLine = event.description,
|
||||
isNoisy = event.noisy,
|
||||
timestamp = event.timestamp
|
||||
|
|
|
@ -34,7 +34,7 @@ class NotificationRenderer @Inject constructor(private val notificationDisplayer
|
|||
myUserDisplayName: String,
|
||||
myUserAvatarUrl: String?,
|
||||
useCompleteNotificationFormat: Boolean,
|
||||
eventsToProcess: Map<String, NotifiableEvent?>) {
|
||||
eventsToProcess: List<Pair<Processed, NotifiableEvent>>) {
|
||||
val (roomEvents, simpleEvents, invitationEvents) = eventsToProcess.groupByType()
|
||||
with(notificationFactory) {
|
||||
val roomNotifications = roomEvents.toNotifications(myUserDisplayName, myUserAvatarUrl)
|
||||
|
@ -108,25 +108,28 @@ class NotificationRenderer @Inject constructor(private val notificationDisplayer
|
|||
}
|
||||
}
|
||||
|
||||
private fun Map<String, NotifiableEvent?>.groupByType(): GroupedNotificationEvents {
|
||||
private fun List<Pair<Processed, NotifiableEvent>>.groupByType(): GroupedNotificationEvents {
|
||||
val roomIdToEventMap: MutableMap<String, MutableList<NotifiableMessageEvent>> = LinkedHashMap()
|
||||
val simpleEvents: MutableMap<String, SimpleNotifiableEvent?> = LinkedHashMap()
|
||||
val invitationEvents: MutableMap<String, InviteNotifiableEvent?> = LinkedHashMap()
|
||||
forEach { (_, value) ->
|
||||
when (value) {
|
||||
is InviteNotifiableEvent -> invitationEvents[value.roomId]
|
||||
val simpleEvents: MutableList<Pair<Processed, SimpleNotifiableEvent>> = ArrayList()
|
||||
val invitationEvents: MutableList<Pair<Processed, InviteNotifiableEvent>> = ArrayList()
|
||||
forEach {
|
||||
when (val event = it.second) {
|
||||
is InviteNotifiableEvent -> invitationEvents.add(it.asPair())
|
||||
is NotifiableMessageEvent -> {
|
||||
val roomEvents = roomIdToEventMap.getOrPut(value.roomId) { ArrayList() }
|
||||
roomEvents.add(value)
|
||||
val roomEvents = roomIdToEventMap.getOrPut(event.roomId) { ArrayList() }
|
||||
roomEvents.add(event)
|
||||
}
|
||||
is SimpleNotifiableEvent -> simpleEvents[value.eventId] = value
|
||||
is SimpleNotifiableEvent -> simpleEvents.add(it.asPair())
|
||||
}
|
||||
}
|
||||
return GroupedNotificationEvents(roomIdToEventMap, simpleEvents, invitationEvents)
|
||||
}
|
||||
|
||||
@Suppress("UNCHECKED_CAST")
|
||||
private fun <T: NotifiableEvent> Pair<Processed, *>.asPair(): Pair<Processed, T> = this as Pair<Processed, T>
|
||||
|
||||
data class GroupedNotificationEvents(
|
||||
val roomEvents: Map<String, List<NotifiableMessageEvent>>,
|
||||
val simpleEvents: Map<String, SimpleNotifiableEvent?>,
|
||||
val invitationEvents: Map<String, InviteNotifiableEvent?>
|
||||
val simpleEvents: List<Pair<Processed, SimpleNotifiableEvent>>,
|
||||
val invitationEvents: List<Pair<Processed, InviteNotifiableEvent>>
|
||||
)
|
||||
|
|
|
@ -37,7 +37,7 @@ class NotifiableEventProcessorTest {
|
|||
aSimpleNotifiableEvent(eventId = "event-2")
|
||||
)
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM)
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM, renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
simpleEvents = mapOf(
|
||||
|
@ -56,7 +56,7 @@ class NotifiableEventProcessorTest {
|
|||
anInviteNotifiableEvent(roomId = "room-2")
|
||||
)
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM)
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM, renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
invitationEvents = mapOf(
|
||||
|
@ -75,7 +75,7 @@ class NotifiableEventProcessorTest {
|
|||
anInviteNotifiableEvent(roomId = "room-2")
|
||||
)
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM)
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM, renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
invitationEvents = mapOf(
|
||||
|
@ -91,7 +91,7 @@ class NotifiableEventProcessorTest {
|
|||
val (events) = createEventsList(aNotifiableMessageEvent(eventId = "event-1", roomId = "room-1"))
|
||||
outdatedDetector.givenEventIsOutOfDate(events[0])
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM)
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM, renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
roomEvents = mapOf(
|
||||
|
@ -106,7 +106,7 @@ class NotifiableEventProcessorTest {
|
|||
val (events, originalEvents) = createEventsList(aNotifiableMessageEvent(eventId = "event-1", roomId = "room-1"))
|
||||
outdatedDetector.givenEventIsInDate(events[0])
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM)
|
||||
val result = eventProcessor.process(events, currentRoomId = NOT_VIEWING_A_ROOM, renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
roomEvents = mapOf(
|
||||
|
@ -120,7 +120,7 @@ class NotifiableEventProcessorTest {
|
|||
fun `given viewing the same room as message event when processing then removes message`() {
|
||||
val (events) = createEventsList(aNotifiableMessageEvent(eventId = "event-1", roomId = "room-1"))
|
||||
|
||||
val result = eventProcessor.process(events, currentRoomId = "room-1")
|
||||
val result = eventProcessor.process(events, currentRoomId = "room-1", renderedEventsList = renderedEventsList)
|
||||
|
||||
result shouldBeEqualTo aProcessedNotificationEvents(
|
||||
roomEvents = mapOf(
|
||||
|
|
Loading…
Reference in a new issue