|
@@ -29,27 +29,26 @@ import android.annotation.SuppressLint
|
|
|
import android.content.Context
|
|
|
import android.content.res.ColorStateList
|
|
|
import android.graphics.Typeface
|
|
|
-import android.graphics.drawable.Drawable
|
|
|
-import android.graphics.drawable.LayerDrawable
|
|
|
import android.os.Build
|
|
|
import android.text.TextUtils
|
|
|
import android.text.format.DateUtils
|
|
|
import android.view.View
|
|
|
import androidx.core.content.ContextCompat
|
|
|
import androidx.core.content.res.ResourcesCompat
|
|
|
-import com.facebook.drawee.backends.pipeline.Fresco
|
|
|
-import com.facebook.drawee.interfaces.DraweeController
|
|
|
import com.nextcloud.talk.R
|
|
|
import com.nextcloud.talk.adapters.items.ConversationItem.ConversationItemViewHolder
|
|
|
import com.nextcloud.talk.application.NextcloudTalkApplication.Companion.sharedApplication
|
|
|
import com.nextcloud.talk.data.user.model.User
|
|
|
import com.nextcloud.talk.databinding.RvItemConversationWithLastMessageBinding
|
|
|
+import com.nextcloud.talk.extensions.loadAvatar
|
|
|
+import com.nextcloud.talk.extensions.loadGroupCallAvatar
|
|
|
+import com.nextcloud.talk.extensions.loadPublicCallAvatar
|
|
|
+import com.nextcloud.talk.extensions.loadSystemAvatar
|
|
|
import com.nextcloud.talk.models.json.chat.ChatMessage
|
|
|
import com.nextcloud.talk.models.json.conversations.Conversation
|
|
|
import com.nextcloud.talk.models.json.conversations.Conversation.ConversationType
|
|
|
import com.nextcloud.talk.ui.StatusDrawable
|
|
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
|
|
-import com.nextcloud.talk.utils.ApiUtils
|
|
|
import com.nextcloud.talk.utils.DisplayUtils
|
|
|
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.hasSpreedFeatureCapability
|
|
|
import eu.davidea.flexibleadapter.FlexibleAdapter
|
|
@@ -113,7 +112,6 @@ class ConversationItem(
|
|
|
payloads: List<Any>
|
|
|
) {
|
|
|
val appContext = sharedApplication!!.applicationContext
|
|
|
- holder.binding.dialogAvatar.controller = null
|
|
|
holder.binding.dialogName.setTextColor(
|
|
|
ResourcesCompat.getColor(
|
|
|
context.resources,
|
|
@@ -130,40 +128,7 @@ class ConversationItem(
|
|
|
holder.binding.dialogName.text = model.displayName
|
|
|
}
|
|
|
if (model.unreadMessages > 0) {
|
|
|
- holder.binding.dialogName.setTypeface(holder.binding.dialogName.typeface, Typeface.BOLD)
|
|
|
- holder.binding.dialogLastMessage.setTypeface(holder.binding.dialogLastMessage.typeface, Typeface.BOLD)
|
|
|
- holder.binding.dialogUnreadBubble.visibility = View.VISIBLE
|
|
|
- if (model.unreadMessages < 1000) {
|
|
|
- holder.binding.dialogUnreadBubble.text = model.unreadMessages.toLong().toString()
|
|
|
- } else {
|
|
|
- holder.binding.dialogUnreadBubble.setText(R.string.tooManyUnreadMessages)
|
|
|
- }
|
|
|
- val lightBubbleFillColor = ColorStateList.valueOf(
|
|
|
- ContextCompat.getColor(
|
|
|
- context,
|
|
|
- R.color.conversation_unread_bubble
|
|
|
- )
|
|
|
- )
|
|
|
- val lightBubbleTextColor = ContextCompat.getColor(
|
|
|
- context,
|
|
|
- R.color.conversation_unread_bubble_text
|
|
|
- )
|
|
|
- if (model.type === ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
|
|
- viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
- } else if (model.unreadMention) {
|
|
|
- if (hasSpreedFeatureCapability(user, "direct-mention-flag")) {
|
|
|
- if (model.unreadMentionDirect!!) {
|
|
|
- viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
- } else {
|
|
|
- viewThemeUtils.material.colorChipOutlined(holder.binding.dialogUnreadBubble, 6.0f)
|
|
|
- }
|
|
|
- } else {
|
|
|
- viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
- }
|
|
|
- } else {
|
|
|
- holder.binding.dialogUnreadBubble.chipBackgroundColor = lightBubbleFillColor
|
|
|
- holder.binding.dialogUnreadBubble.setTextColor(lightBubbleTextColor)
|
|
|
- }
|
|
|
+ showUnreadMessages(holder)
|
|
|
} else {
|
|
|
holder.binding.dialogName.setTypeface(null, Typeface.NORMAL)
|
|
|
holder.binding.dialogDate.setTypeface(null, Typeface.NORMAL)
|
|
@@ -175,13 +140,13 @@ class ConversationItem(
|
|
|
} else {
|
|
|
holder.binding.favoriteConversationImageView.visibility = View.GONE
|
|
|
}
|
|
|
- if (model != null && ConversationType.ROOM_SYSTEM !== model.type) {
|
|
|
+ if (ConversationType.ROOM_SYSTEM !== model.type) {
|
|
|
val size = DisplayUtils.convertDpToPixel(STATUS_SIZE_IN_DP, appContext)
|
|
|
holder.binding.userStatusImage.visibility = View.VISIBLE
|
|
|
holder.binding.userStatusImage.setImageDrawable(
|
|
|
StatusDrawable(
|
|
|
model.status,
|
|
|
- model.status,
|
|
|
+ model.statusIcon,
|
|
|
size,
|
|
|
context.resources.getColor(R.color.bg_default),
|
|
|
appContext
|
|
@@ -190,150 +155,163 @@ class ConversationItem(
|
|
|
} else {
|
|
|
holder.binding.userStatusImage.visibility = View.GONE
|
|
|
}
|
|
|
- if (model.lastMessage != null) {
|
|
|
- holder.binding.dialogDate.visibility = View.VISIBLE
|
|
|
- holder.binding.dialogDate.text = DateUtils.getRelativeTimeSpanString(
|
|
|
- model.lastActivity * 1000L,
|
|
|
- System.currentTimeMillis(),
|
|
|
- 0,
|
|
|
- DateUtils.FORMAT_ABBREV_RELATIVE
|
|
|
- )
|
|
|
- if (!TextUtils.isEmpty(model.lastMessage!!.systemMessage) ||
|
|
|
- ConversationType.ROOM_SYSTEM === model.type
|
|
|
- ) {
|
|
|
- holder.binding.dialogLastMessage.text = model.lastMessage!!.text
|
|
|
- } else {
|
|
|
- model.lastMessage!!.activeUser = user
|
|
|
- val text: String
|
|
|
- if (model.lastMessage!!.getCalculateMessageType() === ChatMessage.MessageType.REGULAR_TEXT_MESSAGE) {
|
|
|
- if (model.lastMessage!!.actorId == user.userId) {
|
|
|
- text = String.format(
|
|
|
- appContext.getString(R.string.nc_formatted_message_you),
|
|
|
- model.lastMessage!!.lastMessageDisplayText
|
|
|
- )
|
|
|
- } else {
|
|
|
- val authorDisplayName =
|
|
|
- if (!TextUtils.isEmpty(model.lastMessage!!.actorDisplayName)) {
|
|
|
- model.lastMessage!!.actorDisplayName
|
|
|
- } else if ("guests" == model.lastMessage!!.actorType) {
|
|
|
- appContext.getString(R.string.nc_guest)
|
|
|
- } else {
|
|
|
- ""
|
|
|
- }
|
|
|
- text = String.format(
|
|
|
- appContext.getString(R.string.nc_formatted_message),
|
|
|
- authorDisplayName,
|
|
|
- model.lastMessage!!.lastMessageDisplayText
|
|
|
- )
|
|
|
- }
|
|
|
+ setLastMessage(holder, appContext)
|
|
|
+ showAvatar(holder)
|
|
|
+ }
|
|
|
+
|
|
|
+ private fun showAvatar(holder: ConversationItemViewHolder) {
|
|
|
+ holder.binding.dialogAvatar.visibility = View.VISIBLE
|
|
|
+ var shouldLoadAvatar = shouldLoadAvatar(holder)
|
|
|
+ if (ConversationType.ROOM_SYSTEM == model.type) {
|
|
|
+ holder.binding.dialogAvatar.loadSystemAvatar()
|
|
|
+ shouldLoadAvatar = false
|
|
|
+ }
|
|
|
+ if (shouldLoadAvatar) {
|
|
|
+ when (model.type) {
|
|
|
+ ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL -> if (!TextUtils.isEmpty(model.name)) {
|
|
|
+ holder.binding.dialogAvatar.loadAvatar(user, model.name!!)
|
|
|
} else {
|
|
|
- text = model.lastMessage!!.lastMessageDisplayText
|
|
|
+ holder.binding.dialogAvatar.visibility = View.GONE
|
|
|
}
|
|
|
- holder.binding.dialogLastMessage.text = text
|
|
|
+ ConversationType.ROOM_GROUP_CALL ->
|
|
|
+ holder.binding.dialogAvatar.loadGroupCallAvatar(viewThemeUtils)
|
|
|
+ ConversationType.ROOM_PUBLIC_CALL ->
|
|
|
+ holder.binding.dialogAvatar.loadPublicCallAvatar(viewThemeUtils)
|
|
|
+ else -> holder.binding.dialogAvatar.visibility = View.GONE
|
|
|
}
|
|
|
- } else {
|
|
|
- holder.binding.dialogDate.visibility = View.GONE
|
|
|
- holder.binding.dialogLastMessage.setText(R.string.nc_no_messages_yet)
|
|
|
}
|
|
|
- holder.binding.dialogAvatar.visibility = View.VISIBLE
|
|
|
- var shouldLoadAvatar = true
|
|
|
+ }
|
|
|
+
|
|
|
+ private fun shouldLoadAvatar(
|
|
|
+ holder: ConversationItemViewHolder
|
|
|
+ ): Boolean {
|
|
|
var objectType: String?
|
|
|
+ var returnValue = true
|
|
|
if (!TextUtils.isEmpty(model.objectType.also { objectType = it })) {
|
|
|
when (objectType) {
|
|
|
"share:password" -> {
|
|
|
- shouldLoadAvatar = false
|
|
|
holder.binding.dialogAvatar.setImageDrawable(
|
|
|
ContextCompat.getDrawable(
|
|
|
context,
|
|
|
R.drawable.ic_circular_lock
|
|
|
)
|
|
|
)
|
|
|
+ returnValue = false
|
|
|
}
|
|
|
"file" -> {
|
|
|
- shouldLoadAvatar = false
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- DisplayUtils.getRoundedDrawable(
|
|
|
- viewThemeUtils.talk.themePlaceholderAvatar(
|
|
|
- holder.binding.dialogAvatar,
|
|
|
- R.drawable.ic_avatar_document
|
|
|
- )
|
|
|
+ holder.binding.dialogAvatar.loadAvatar(
|
|
|
+ viewThemeUtils.talk.themePlaceholderAvatar(
|
|
|
+ holder.binding.dialogAvatar,
|
|
|
+ R.drawable.ic_avatar_document
|
|
|
)
|
|
|
)
|
|
|
} else {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- ContextCompat.getDrawable(context, R.drawable.ic_circular_document)
|
|
|
+ holder.binding.dialogAvatar.loadAvatar(
|
|
|
+ R.drawable.ic_circular_document
|
|
|
)
|
|
|
}
|
|
|
+ returnValue = false
|
|
|
}
|
|
|
- else -> {}
|
|
|
}
|
|
|
}
|
|
|
- if (ConversationType.ROOM_SYSTEM == model.type) {
|
|
|
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
|
- val layers = arrayOfNulls<Drawable>(2)
|
|
|
- layers[0] = ContextCompat.getDrawable(context, R.drawable.ic_launcher_background)
|
|
|
- layers[1] = ContextCompat.getDrawable(context, R.drawable.ic_launcher_foreground)
|
|
|
- val layerDrawable = LayerDrawable(layers)
|
|
|
- holder.binding.dialogAvatar.hierarchy.setPlaceholderImage(
|
|
|
- DisplayUtils.getRoundedDrawable(layerDrawable)
|
|
|
- )
|
|
|
+ return returnValue
|
|
|
+ }
|
|
|
+
|
|
|
+ private fun setLastMessage(
|
|
|
+ holder: ConversationItemViewHolder,
|
|
|
+ appContext: Context
|
|
|
+ ) {
|
|
|
+ if (model.lastMessage != null) {
|
|
|
+ holder.binding.dialogDate.visibility = View.VISIBLE
|
|
|
+ holder.binding.dialogDate.text = DateUtils.getRelativeTimeSpanString(
|
|
|
+ model.lastActivity * MILLIES,
|
|
|
+ System.currentTimeMillis(),
|
|
|
+ 0,
|
|
|
+ DateUtils.FORMAT_ABBREV_RELATIVE
|
|
|
+ )
|
|
|
+ if (!TextUtils.isEmpty(model.lastMessage!!.systemMessage) ||
|
|
|
+ ConversationType.ROOM_SYSTEM === model.type
|
|
|
+ ) {
|
|
|
+ holder.binding.dialogLastMessage.text = model.lastMessage!!.text
|
|
|
} else {
|
|
|
- holder.binding.dialogAvatar.hierarchy.setPlaceholderImage(R.mipmap.ic_launcher)
|
|
|
- }
|
|
|
- shouldLoadAvatar = false
|
|
|
- }
|
|
|
- if (shouldLoadAvatar) {
|
|
|
- when (model.type) {
|
|
|
- ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL -> if (!TextUtils.isEmpty(model.name)) {
|
|
|
- val draweeController: DraweeController = Fresco.newDraweeControllerBuilder()
|
|
|
- .setOldController(holder.binding.dialogAvatar.controller)
|
|
|
- .setAutoPlayAnimations(true)
|
|
|
- .setImageRequest(
|
|
|
- DisplayUtils.getImageRequestForUrl(
|
|
|
- ApiUtils.getUrlForAvatar(
|
|
|
- user.baseUrl,
|
|
|
- model.name,
|
|
|
- true
|
|
|
- ),
|
|
|
- user
|
|
|
- )
|
|
|
- )
|
|
|
- .build()
|
|
|
- holder.binding.dialogAvatar.controller = draweeController
|
|
|
+ model.lastMessage!!.activeUser = user
|
|
|
+
|
|
|
+ val text = if (model.lastMessage!!.getCalculateMessageType() === ChatMessage.MessageType
|
|
|
+ .REGULAR_TEXT_MESSAGE
|
|
|
+ ) {
|
|
|
+ calculateRegularLastMessageText(appContext)
|
|
|
} else {
|
|
|
- holder.binding.dialogAvatar.visibility = View.GONE
|
|
|
+ model.lastMessage!!.lastMessageDisplayText
|
|
|
}
|
|
|
- ConversationType.ROOM_GROUP_CALL -> if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- DisplayUtils.getRoundedDrawable(
|
|
|
- viewThemeUtils.talk.themePlaceholderAvatar(
|
|
|
- holder.binding.dialogAvatar,
|
|
|
- R.drawable.ic_avatar_group
|
|
|
- )
|
|
|
- )
|
|
|
- )
|
|
|
+ holder.binding.dialogLastMessage.text = text
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ holder.binding.dialogDate.visibility = View.GONE
|
|
|
+ holder.binding.dialogLastMessage.setText(R.string.nc_no_messages_yet)
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private fun calculateRegularLastMessageText(appContext: Context): String {
|
|
|
+ return if (model.lastMessage!!.actorId == user.userId) {
|
|
|
+ String.format(
|
|
|
+ appContext.getString(R.string.nc_formatted_message_you),
|
|
|
+ model.lastMessage!!.lastMessageDisplayText
|
|
|
+ )
|
|
|
+ } else {
|
|
|
+ val authorDisplayName =
|
|
|
+ if (!TextUtils.isEmpty(model.lastMessage!!.actorDisplayName)) {
|
|
|
+ model.lastMessage!!.actorDisplayName
|
|
|
+ } else if ("guests" == model.lastMessage!!.actorType) {
|
|
|
+ appContext.getString(R.string.nc_guest)
|
|
|
} else {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- ContextCompat.getDrawable(context, R.drawable.ic_circular_group)
|
|
|
- )
|
|
|
+ ""
|
|
|
}
|
|
|
- ConversationType.ROOM_PUBLIC_CALL -> if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- DisplayUtils.getRoundedDrawable(
|
|
|
- viewThemeUtils.talk.themePlaceholderAvatar(
|
|
|
- holder.binding.dialogAvatar,
|
|
|
- R.drawable.ic_avatar_link
|
|
|
- )
|
|
|
- )
|
|
|
- )
|
|
|
+ String.format(
|
|
|
+ appContext.getString(R.string.nc_formatted_message),
|
|
|
+ authorDisplayName,
|
|
|
+ model.lastMessage!!.lastMessageDisplayText
|
|
|
+ )
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private fun showUnreadMessages(holder: ConversationItemViewHolder) {
|
|
|
+ holder.binding.dialogName.setTypeface(holder.binding.dialogName.typeface, Typeface.BOLD)
|
|
|
+ holder.binding.dialogLastMessage.setTypeface(holder.binding.dialogLastMessage.typeface, Typeface.BOLD)
|
|
|
+ holder.binding.dialogUnreadBubble.visibility = View.VISIBLE
|
|
|
+ if (model.unreadMessages < UNREAD_MESSAGES_TRESHOLD) {
|
|
|
+ holder.binding.dialogUnreadBubble.text = model.unreadMessages.toLong().toString()
|
|
|
+ } else {
|
|
|
+ holder.binding.dialogUnreadBubble.setText(R.string.tooManyUnreadMessages)
|
|
|
+ }
|
|
|
+ val lightBubbleFillColor = ColorStateList.valueOf(
|
|
|
+ ContextCompat.getColor(
|
|
|
+ context,
|
|
|
+ R.color.conversation_unread_bubble
|
|
|
+ )
|
|
|
+ )
|
|
|
+ val lightBubbleTextColor = ContextCompat.getColor(
|
|
|
+ context,
|
|
|
+ R.color.conversation_unread_bubble_text
|
|
|
+ )
|
|
|
+ if (model.type === ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
|
|
+ viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
+ } else if (model.unreadMention) {
|
|
|
+ if (hasSpreedFeatureCapability(user, "direct-mention-flag")) {
|
|
|
+ if (model.unreadMentionDirect!!) {
|
|
|
+ viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
} else {
|
|
|
- holder.binding.dialogAvatar.setImageDrawable(
|
|
|
- ContextCompat.getDrawable(context, R.drawable.ic_circular_link)
|
|
|
+ viewThemeUtils.material.colorChipOutlined(
|
|
|
+ holder.binding.dialogUnreadBubble,
|
|
|
+ UNREAD_BUBBLE_STROKE_WIDTH
|
|
|
)
|
|
|
}
|
|
|
- else -> holder.binding.dialogAvatar.visibility = View.GONE
|
|
|
+ } else {
|
|
|
+ viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
|
|
}
|
|
|
+ } else {
|
|
|
+ holder.binding.dialogUnreadBubble.chipBackgroundColor = lightBubbleFillColor
|
|
|
+ holder.binding.dialogUnreadBubble.setTextColor(lightBubbleTextColor)
|
|
|
}
|
|
|
}
|
|
|
|
|
@@ -363,6 +341,9 @@ class ConversationItem(
|
|
|
|
|
|
companion object {
|
|
|
const val VIEW_TYPE = R.layout.rv_item_conversation_with_last_message
|
|
|
+ private const val MILLIES = 1000L
|
|
|
private const val STATUS_SIZE_IN_DP = 9f
|
|
|
+ private const val UNREAD_BUBBLE_STROKE_WIDTH = 6.0f
|
|
|
+ private const val UNREAD_MESSAGES_TRESHOLD = 1000
|
|
|
}
|
|
|
}
|