Reworked how Persons are used + fixed timestamp issue in chat message notification + fixed chat room being marked as read when answering in the notification
This commit is contained in:
parent
8a09115623
commit
01c8735caf
3 changed files with 65 additions and 65 deletions
|
@ -26,6 +26,7 @@ import android.content.ContentResolver
|
||||||
import android.content.ContentUris
|
import android.content.ContentUris
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.graphics.Bitmap
|
import android.graphics.Bitmap
|
||||||
|
import android.graphics.BitmapFactory
|
||||||
import android.graphics.drawable.Drawable
|
import android.graphics.drawable.Drawable
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import android.provider.ContactsContract
|
import android.provider.ContactsContract
|
||||||
|
@ -41,6 +42,7 @@ import org.linphone.R
|
||||||
import org.linphone.core.*
|
import org.linphone.core.*
|
||||||
import org.linphone.core.tools.Log
|
import org.linphone.core.tools.Log
|
||||||
import org.linphone.utils.ImageUtils
|
import org.linphone.utils.ImageUtils
|
||||||
|
import org.linphone.utils.LinphoneUtils
|
||||||
import org.linphone.utils.PermissionHelper
|
import org.linphone.utils.PermissionHelper
|
||||||
|
|
||||||
interface ContactsUpdatedListener {
|
interface ContactsUpdatedListener {
|
||||||
|
@ -70,6 +72,7 @@ class ContactsManager(private val context: Context) {
|
||||||
|
|
||||||
val contactAvatar: IconCompat
|
val contactAvatar: IconCompat
|
||||||
val groupAvatar: IconCompat
|
val groupAvatar: IconCompat
|
||||||
|
val groupBitmap: Bitmap
|
||||||
|
|
||||||
private val localFriends = arrayListOf<Friend>()
|
private val localFriends = arrayListOf<Friend>()
|
||||||
|
|
||||||
|
@ -93,6 +96,7 @@ class ContactsManager(private val context: Context) {
|
||||||
|
|
||||||
contactAvatar = IconCompat.createWithResource(context, R.drawable.voip_single_contact_avatar_alt)
|
contactAvatar = IconCompat.createWithResource(context, R.drawable.voip_single_contact_avatar_alt)
|
||||||
groupAvatar = IconCompat.createWithResource(context, R.drawable.voip_multiple_contacts_avatar_alt)
|
groupAvatar = IconCompat.createWithResource(context, R.drawable.voip_multiple_contacts_avatar_alt)
|
||||||
|
groupBitmap = BitmapFactory.decodeResource(context.resources, R.drawable.voip_multiple_contacts_avatar_alt)
|
||||||
|
|
||||||
val core = coreContext.core
|
val core = coreContext.core
|
||||||
for (list in core.friendsLists) {
|
for (list in core.friendsLists) {
|
||||||
|
@ -120,7 +124,7 @@ class ContactsManager(private val context: Context) {
|
||||||
|
|
||||||
for (account in coreContext.core.accountList) {
|
for (account in coreContext.core.accountList) {
|
||||||
val friend = coreContext.core.createFriend()
|
val friend = coreContext.core.createFriend()
|
||||||
friend.name = account.params.identityAddress?.displayName ?: account.params.identityAddress?.username
|
friend.name = LinphoneUtils.getDisplayName(account.params.identityAddress)
|
||||||
|
|
||||||
val address = account.params.identityAddress ?: continue
|
val address = account.params.identityAddress ?: continue
|
||||||
friend.address = address
|
friend.address = address
|
||||||
|
@ -137,6 +141,17 @@ class ContactsManager(private val context: Context) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Synchronized
|
||||||
|
fun getMePerson(localAddress: Address): Person {
|
||||||
|
val friend = localFriends.find { localFriend ->
|
||||||
|
localFriend.addresses.find { address ->
|
||||||
|
address.weakEqual(localAddress)
|
||||||
|
} != null
|
||||||
|
}
|
||||||
|
return friend?.getPerson()
|
||||||
|
?: Person.Builder().setName(LinphoneUtils.getDisplayName(localAddress)).build()
|
||||||
|
}
|
||||||
|
|
||||||
@Synchronized
|
@Synchronized
|
||||||
fun getAndroidContactIdFromUri(uri: Uri): String? {
|
fun getAndroidContactIdFromUri(uri: Uri): String? {
|
||||||
val projection = arrayOf(ContactsContract.Data.CONTACT_ID)
|
val projection = arrayOf(ContactsContract.Data.CONTACT_ID)
|
||||||
|
@ -381,14 +396,13 @@ fun Friend.getPerson(): Person {
|
||||||
coreContext.context,
|
coreContext.context,
|
||||||
getThumbnailUri()
|
getThumbnailUri()
|
||||||
)
|
)
|
||||||
val icon =
|
personBuilder.setIcon(
|
||||||
if (bm == null) {
|
if (bm == null) {
|
||||||
coreContext.contactsManager.contactAvatar
|
coreContext.contactsManager.contactAvatar
|
||||||
} else IconCompat.createWithAdaptiveBitmap(bm)
|
} else IconCompat.createWithAdaptiveBitmap(bm)
|
||||||
if (icon != null) {
|
)
|
||||||
personBuilder.setIcon(icon)
|
|
||||||
}
|
|
||||||
|
|
||||||
|
personBuilder.setKey(refKey)
|
||||||
personBuilder.setUri(nativeUri)
|
personBuilder.setUri(nativeUri)
|
||||||
personBuilder.setImportant(starred)
|
personBuilder.setImportant(starred)
|
||||||
return personBuilder.build()
|
return personBuilder.build()
|
||||||
|
|
|
@ -76,7 +76,6 @@ class NotificationBroadcastReceiver : BroadcastReceiver() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
room.markAsRead()
|
|
||||||
if (intent.action == NotificationsManager.INTENT_REPLY_NOTIF_ACTION) {
|
if (intent.action == NotificationsManager.INTENT_REPLY_NOTIF_ACTION) {
|
||||||
val reply = getMessageText(intent)?.toString()
|
val reply = getMessageText(intent)?.toString()
|
||||||
if (reply == null) {
|
if (reply == null) {
|
||||||
|
@ -90,6 +89,7 @@ class NotificationBroadcastReceiver : BroadcastReceiver() {
|
||||||
msg.send()
|
msg.send()
|
||||||
Log.i("[Notification Broadcast Receiver] Reply sent for notif id $notificationId")
|
Log.i("[Notification Broadcast Receiver] Reply sent for notif id $notificationId")
|
||||||
} else {
|
} else {
|
||||||
|
room.markAsRead()
|
||||||
if (!coreContext.notificationsManager.dismissChatNotification(room)) {
|
if (!coreContext.notificationsManager.dismissChatNotification(room)) {
|
||||||
Log.w("[Notification Broadcast Receiver] Notifications Manager failed to cancel notification")
|
Log.w("[Notification Broadcast Receiver] Notifications Manager failed to cancel notification")
|
||||||
val notificationManager = context.getSystemService(NotificationManager::class.java)
|
val notificationManager = context.getSystemService(NotificationManager::class.java)
|
||||||
|
|
|
@ -480,19 +480,18 @@ class NotificationsManager(private val context: Context) {
|
||||||
}
|
}
|
||||||
|
|
||||||
fun getPerson(friend: Friend?, displayName: String, picture: Bitmap?): Person {
|
fun getPerson(friend: Friend?, displayName: String, picture: Bitmap?): Person {
|
||||||
return if (friend != null) {
|
return friend?.getPerson()
|
||||||
friend.getPerson()
|
?: Person.Builder()
|
||||||
} else {
|
.setName(displayName)
|
||||||
val builder = Person.Builder().setName(displayName)
|
.setIcon(
|
||||||
val userIcon =
|
|
||||||
if (picture != null) {
|
if (picture != null) {
|
||||||
IconCompat.createWithAdaptiveBitmap(picture)
|
IconCompat.createWithAdaptiveBitmap(picture)
|
||||||
} else {
|
} else {
|
||||||
coreContext.contactsManager.contactAvatar
|
coreContext.contactsManager.contactAvatar
|
||||||
}
|
}
|
||||||
if (userIcon != null) builder.setIcon(userIcon)
|
)
|
||||||
builder.build()
|
.setKey(displayName)
|
||||||
}
|
.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun displayIncomingCallNotification(call: Call, useAsForeground: Boolean) {
|
fun displayIncomingCallNotification(call: Call, useAsForeground: Boolean) {
|
||||||
|
@ -665,41 +664,18 @@ class NotificationsManager(private val context: Context) {
|
||||||
)
|
)
|
||||||
|
|
||||||
val id = LinphoneUtils.getChatRoomId(room.localAddress, room.peerAddress)
|
val id = LinphoneUtils.getChatRoomId(room.localAddress, room.peerAddress)
|
||||||
val notification = createMessageNotification(notifiable, pendingIntent, bubbleIntent, id)
|
val me = coreContext.contactsManager.getMePerson(room.localAddress)
|
||||||
|
val notification = createMessageNotification(notifiable, pendingIntent, bubbleIntent, id, me)
|
||||||
notify(notifiable.notificationId, notification, CHAT_TAG)
|
notify(notifiable.notificationId, notification, CHAT_TAG)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun createChatNotifiable(room: ChatRoom, message: ChatMessage): Notifiable {
|
|
||||||
val notifiable = getNotifiableForRoom(room)
|
|
||||||
if (notifiable.messages.isNotEmpty() || room.unreadMessagesCount == 1) {
|
|
||||||
val friend = coreContext.contactsManager.findContactByAddress(message.fromAddress)
|
|
||||||
val notifiableMessage = getNotifiableMessage(message, friend)
|
|
||||||
notifiable.messages.add(notifiableMessage)
|
|
||||||
} else {
|
|
||||||
for (chatMessage in room.unreadHistory) {
|
|
||||||
val friend = coreContext.contactsManager.findContactByAddress(chatMessage.fromAddress)
|
|
||||||
val notifiableMessage = getNotifiableMessage(chatMessage, friend)
|
|
||||||
notifiable.messages.add(notifiableMessage)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (room.hasCapability(ChatRoomCapabilities.OneToOne.toInt())) {
|
|
||||||
notifiable.isGroup = false
|
|
||||||
} else {
|
|
||||||
notifiable.isGroup = true
|
|
||||||
notifiable.groupTitle = room.subject
|
|
||||||
}
|
|
||||||
|
|
||||||
return notifiable
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun createChatNotifiable(room: ChatRoom, messages: Array<out ChatMessage>): Notifiable {
|
private fun createChatNotifiable(room: ChatRoom, messages: Array<out ChatMessage>): Notifiable {
|
||||||
val notifiable = getNotifiableForRoom(room)
|
val notifiable = getNotifiableForRoom(room)
|
||||||
|
|
||||||
for (message in messages) {
|
for (message in messages) {
|
||||||
if (message.isRead || message.isOutgoing) continue
|
if (message.isRead || message.isOutgoing) continue
|
||||||
val friend = coreContext.contactsManager.findContactByAddress(message.fromAddress)
|
val friend = coreContext.contactsManager.findContactByAddress(message.fromAddress)
|
||||||
val notifiableMessage = getNotifiableMessage(message, friend)
|
val notifiableMessage = getNotifiableMessage(message, friend, notifiable)
|
||||||
notifiable.messages.add(notifiableMessage)
|
notifiable.messages.add(notifiableMessage)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -727,7 +703,7 @@ class NotificationsManager(private val context: Context) {
|
||||||
return notifiable
|
return notifiable
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getNotifiableMessage(message: ChatMessage, friend: Friend?): NotifiableMessage {
|
private fun getNotifiableMessage(message: ChatMessage, friend: Friend?, notifiable: Notifiable): NotifiableMessage {
|
||||||
val roundPicture = ImageUtils.getRoundBitmapFromUri(context, friend?.getThumbnailUri())
|
val roundPicture = ImageUtils.getRoundBitmapFromUri(context, friend?.getThumbnailUri())
|
||||||
val displayName = friend?.name ?: LinphoneUtils.getDisplayName(message.fromAddress)
|
val displayName = friend?.name ?: LinphoneUtils.getDisplayName(message.fromAddress)
|
||||||
var text = ""
|
var text = ""
|
||||||
|
@ -752,7 +728,7 @@ class NotificationsManager(private val context: Context) {
|
||||||
text,
|
text,
|
||||||
friend,
|
friend,
|
||||||
displayName,
|
displayName,
|
||||||
message.time,
|
message.time * 1000, /* Linphone timestamps are in seconds */
|
||||||
senderAvatar = roundPicture,
|
senderAvatar = roundPicture,
|
||||||
isOutgoing = message.isOutgoing
|
isOutgoing = message.isOutgoing
|
||||||
)
|
)
|
||||||
|
@ -784,10 +760,11 @@ class NotificationsManager(private val context: Context) {
|
||||||
Log.i("[Notifications Manager] Updating message notification with reply for notification ${notifiable.notificationId}")
|
Log.i("[Notifications Manager] Updating message notification with reply for notification ${notifiable.notificationId}")
|
||||||
|
|
||||||
val text = message.contents.find { content -> content.isText }?.utf8Text ?: ""
|
val text = message.contents.find { content -> content.isText }?.utf8Text ?: ""
|
||||||
|
val senderAddress = message.fromAddress
|
||||||
val reply = NotifiableMessage(
|
val reply = NotifiableMessage(
|
||||||
text,
|
text,
|
||||||
null,
|
null,
|
||||||
notifiable.myself ?: LinphoneUtils.getDisplayName(message.fromAddress),
|
notifiable.myself ?: LinphoneUtils.getDisplayName(senderAddress),
|
||||||
System.currentTimeMillis(),
|
System.currentTimeMillis(),
|
||||||
isOutgoing = true
|
isOutgoing = true
|
||||||
)
|
)
|
||||||
|
@ -836,38 +813,43 @@ class NotificationsManager(private val context: Context) {
|
||||||
notifiable: Notifiable,
|
notifiable: Notifiable,
|
||||||
pendingIntent: PendingIntent,
|
pendingIntent: PendingIntent,
|
||||||
bubbleIntent: PendingIntent,
|
bubbleIntent: PendingIntent,
|
||||||
id: String
|
id: String,
|
||||||
|
me: Person
|
||||||
): Notification {
|
): Notification {
|
||||||
val me = Person.Builder().setName(notifiable.myself).build()
|
|
||||||
val style = NotificationCompat.MessagingStyle(me)
|
val style = NotificationCompat.MessagingStyle(me)
|
||||||
val largeIcon: Bitmap? = notifiable.messages.lastOrNull()?.senderAvatar
|
val allPersons = arrayListOf<Person>()
|
||||||
|
|
||||||
|
var lastPersonAvatar: Bitmap? = null
|
||||||
var lastPerson: Person? = null
|
var lastPerson: Person? = null
|
||||||
for (message in notifiable.messages) {
|
for (message in notifiable.messages) {
|
||||||
val friend = message.friend
|
val friend = message.friend
|
||||||
val person = getPerson(friend, message.sender, message.senderAvatar)
|
val person = if (message.isOutgoing)
|
||||||
|
me
|
||||||
|
else
|
||||||
|
getPerson(friend, message.sender, message.senderAvatar)
|
||||||
|
|
||||||
// We don't want to see our own avatar
|
|
||||||
if (!message.isOutgoing) {
|
if (!message.isOutgoing) {
|
||||||
|
// We don't want to see our own avatar
|
||||||
lastPerson = person
|
lastPerson = person
|
||||||
|
lastPersonAvatar = message.senderAvatar
|
||||||
|
|
||||||
|
if (allPersons.find { it.key == person.key } == null) {
|
||||||
|
allPersons.add(person)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val msg = if (!corePreferences.hideChatMessageContentInNotification) {
|
val msg = if (corePreferences.hideChatMessageContentInNotification) {
|
||||||
NotificationCompat.MessagingStyle.Message(message.message, message.time, person)
|
|
||||||
} else {
|
|
||||||
NotificationCompat.MessagingStyle.Message(AppUtils.getString(R.string.chat_message_notification_hidden_content), message.time, person)
|
NotificationCompat.MessagingStyle.Message(AppUtils.getString(R.string.chat_message_notification_hidden_content), message.time, person)
|
||||||
}
|
} else {
|
||||||
|
val tmp = NotificationCompat.MessagingStyle.Message(message.message, message.time, person)
|
||||||
if (message.filePath != null && !corePreferences.hideChatMessageContentInNotification) {
|
if (message.filePath != null) tmp.setData(message.fileMime, message.filePath)
|
||||||
msg.setData(message.fileMime, message.filePath)
|
tmp
|
||||||
}
|
}
|
||||||
|
|
||||||
style.addMessage(msg)
|
style.addMessage(msg)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (notifiable.isGroup) {
|
style.conversationTitle = if (notifiable.isGroup) notifiable.groupTitle else lastPerson?.name
|
||||||
style.conversationTitle = notifiable.groupTitle
|
|
||||||
}
|
|
||||||
style.isGroupConversation = notifiable.isGroup
|
style.isGroupConversation = notifiable.isGroup
|
||||||
|
|
||||||
val icon = lastPerson?.icon ?: coreContext.contactsManager.contactAvatar
|
val icon = lastPerson?.icon ?: coreContext.contactsManager.contactAvatar
|
||||||
|
@ -875,11 +857,12 @@ class NotificationsManager(private val context: Context) {
|
||||||
.setDesiredHeightResId(R.dimen.chat_message_bubble_desired_height)
|
.setDesiredHeightResId(R.dimen.chat_message_bubble_desired_height)
|
||||||
.build()
|
.build()
|
||||||
|
|
||||||
|
val largeIcon = if (notifiable.isGroup) coreContext.contactsManager.groupBitmap else lastPersonAvatar
|
||||||
val notificationBuilder = NotificationCompat.Builder(context, context.getString(R.string.notification_channel_chat_id))
|
val notificationBuilder = NotificationCompat.Builder(context, context.getString(R.string.notification_channel_chat_id))
|
||||||
.addPerson(lastPerson)
|
|
||||||
.setSmallIcon(R.drawable.topbar_chat_notification)
|
.setSmallIcon(R.drawable.topbar_chat_notification)
|
||||||
.setAutoCancel(true)
|
.setAutoCancel(true)
|
||||||
.setLargeIcon(largeIcon)
|
.setLargeIcon(largeIcon)
|
||||||
|
.setColor(ContextCompat.getColor(context, R.color.primary_color))
|
||||||
.setCategory(NotificationCompat.CATEGORY_MESSAGE)
|
.setCategory(NotificationCompat.CATEGORY_MESSAGE)
|
||||||
.setGroup(CHAT_NOTIFICATIONS_GROUP)
|
.setGroup(CHAT_NOTIFICATIONS_GROUP)
|
||||||
.setVisibility(NotificationCompat.VISIBILITY_PRIVATE)
|
.setVisibility(NotificationCompat.VISIBILITY_PRIVATE)
|
||||||
|
@ -887,12 +870,15 @@ class NotificationsManager(private val context: Context) {
|
||||||
.setWhen(System.currentTimeMillis())
|
.setWhen(System.currentTimeMillis())
|
||||||
.setShowWhen(true)
|
.setShowWhen(true)
|
||||||
.setStyle(style)
|
.setStyle(style)
|
||||||
.setColor(ContextCompat.getColor(context, R.color.primary_color))
|
|
||||||
.addAction(getReplyMessageAction(notifiable))
|
.addAction(getReplyMessageAction(notifiable))
|
||||||
.addAction(getMarkMessageAsReadAction(notifiable))
|
.addAction(getMarkMessageAsReadAction(notifiable))
|
||||||
.setShortcutId(id)
|
.setShortcutId(id)
|
||||||
.setLocusId(LocusIdCompat(id))
|
.setLocusId(LocusIdCompat(id))
|
||||||
|
|
||||||
|
for (person in allPersons) {
|
||||||
|
notificationBuilder.addPerson(person)
|
||||||
|
}
|
||||||
|
|
||||||
if (!corePreferences.preventInterfaceFromShowingUp) {
|
if (!corePreferences.preventInterfaceFromShowingUp) {
|
||||||
notificationBuilder.setContentIntent(pendingIntent)
|
notificationBuilder.setContentIntent(pendingIntent)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue