mirror of
https://github.com/signalapp/Signal-Android.git
synced 2026-02-25 20:23:19 +00:00
Add payload support to CFv2.
This commit is contained in:
@@ -96,10 +96,6 @@ public class ConversationAdapter
|
||||
public static final int MESSAGE_TYPE_FOOTER = 6;
|
||||
private static final int MESSAGE_TYPE_PLACEHOLDER = 7;
|
||||
|
||||
private static final int PAYLOAD_TIMESTAMP = 0;
|
||||
public static final int PAYLOAD_NAME_COLORS = 1;
|
||||
public static final int PAYLOAD_SELECTED = 2;
|
||||
|
||||
private final ItemClickListener clickListener;
|
||||
private final Context context;
|
||||
private final LifecycleOwner lifecycleOwner;
|
||||
|
||||
@@ -12,6 +12,12 @@ import org.thoughtcrime.securesms.conversation.mutiselect.MultiselectPart
|
||||
* shared decorators and other utils.
|
||||
*/
|
||||
interface ConversationAdapterBridge {
|
||||
companion object {
|
||||
const val PAYLOAD_TIMESTAMP = 0
|
||||
const val PAYLOAD_NAME_COLORS = 1
|
||||
const val PAYLOAD_SELECTED = 2
|
||||
}
|
||||
|
||||
fun hasNoConversationMessages(): Boolean
|
||||
fun getConversationMessage(position: Int): ConversationMessage?
|
||||
fun consumePulseRequest(): PulseRequest?
|
||||
|
||||
@@ -18,6 +18,12 @@ class ConversationUpdateTick(
|
||||
private val handler = Handler(Looper.getMainLooper())
|
||||
private var isResumed = false
|
||||
|
||||
constructor(onTickListener: () -> Unit) : this(object : OnTickListener {
|
||||
override fun onTick() {
|
||||
onTickListener()
|
||||
}
|
||||
})
|
||||
|
||||
override fun onResume(owner: LifecycleOwner) {
|
||||
isResumed = true
|
||||
|
||||
|
||||
@@ -17,6 +17,7 @@ import org.thoughtcrime.securesms.R
|
||||
import org.thoughtcrime.securesms.components.FixedRoundedCornerBottomSheetDialogFragment
|
||||
import org.thoughtcrime.securesms.components.recyclerview.SmoothScrollingLinearLayoutManager
|
||||
import org.thoughtcrime.securesms.conversation.ConversationAdapter
|
||||
import org.thoughtcrime.securesms.conversation.ConversationAdapterBridge
|
||||
import org.thoughtcrime.securesms.conversation.ConversationBottomSheetCallback
|
||||
import org.thoughtcrime.securesms.conversation.ConversationItemDisplayMode
|
||||
import org.thoughtcrime.securesms.conversation.colors.Colorizer
|
||||
@@ -117,7 +118,7 @@ class MessageQuotesBottomSheet : FixedRoundedCornerBottomSheetDialogFragment() {
|
||||
|
||||
disposables += viewModel.getNameColorsMap().subscribe { map ->
|
||||
colorizer.onNameColorsChanged(map)
|
||||
messageAdapter.notifyItemRangeChanged(0, messageAdapter.itemCount, ConversationAdapter.PAYLOAD_NAME_COLORS)
|
||||
messageAdapter.notifyItemRangeChanged(0, messageAdapter.itemCount, ConversationAdapterBridge.PAYLOAD_NAME_COLORS)
|
||||
}
|
||||
|
||||
initializeGiphyMp4(view.findViewById(R.id.video_container) as ViewGroup, list)
|
||||
|
||||
@@ -18,6 +18,7 @@ import org.thoughtcrime.securesms.R
|
||||
import org.thoughtcrime.securesms.components.FixedRoundedCornerBottomSheetDialogFragment
|
||||
import org.thoughtcrime.securesms.components.ViewBinderDelegate
|
||||
import org.thoughtcrime.securesms.conversation.ConversationAdapter
|
||||
import org.thoughtcrime.securesms.conversation.ConversationAdapterBridge
|
||||
import org.thoughtcrime.securesms.conversation.ConversationBottomSheetCallback
|
||||
import org.thoughtcrime.securesms.conversation.ConversationItemDisplayMode
|
||||
import org.thoughtcrime.securesms.conversation.ConversationMessage
|
||||
@@ -113,7 +114,7 @@ class EditMessageHistoryDialog : FixedRoundedCornerBottomSheetDialogFragment() {
|
||||
|
||||
disposables += viewModel.getNameColorsMap().subscribe { map ->
|
||||
colorizer.onNameColorsChanged(map)
|
||||
messageAdapter.notifyItemRangeChanged(0, messageAdapter.itemCount, ConversationAdapter.PAYLOAD_NAME_COLORS)
|
||||
messageAdapter.notifyItemRangeChanged(0, messageAdapter.itemCount, ConversationAdapterBridge.PAYLOAD_NAME_COLORS)
|
||||
}
|
||||
|
||||
initializeGiphyMp4()
|
||||
|
||||
@@ -198,7 +198,7 @@ class ConversationAdapterV2(
|
||||
fun playInlineContent(conversationMessage: ConversationMessage?) {
|
||||
if (this.inlineContent !== conversationMessage) {
|
||||
this.inlineContent = conversationMessage
|
||||
notifyDataSetChanged()
|
||||
notifyItemRangeChanged(0, itemCount)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -234,8 +234,15 @@ class ConversationAdapterV2(
|
||||
return request
|
||||
}
|
||||
|
||||
fun onHasWallpaperChanged(hasChanged: Boolean) {
|
||||
// todo [cody] implement
|
||||
fun onHasWallpaperChanged(hasWallpaper: Boolean): Boolean {
|
||||
return if (this.hasWallpaper != hasWallpaper) {
|
||||
Log.d(TAG, "Resetting adapter due to wallpaper change.")
|
||||
this.hasWallpaper = hasWallpaper
|
||||
notifyItemRangeChanged(0, itemCount)
|
||||
true
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
fun onMessageRequestStateChanged(isMessageRequestAccepted: Boolean) {
|
||||
@@ -249,6 +256,7 @@ class ConversationAdapterV2(
|
||||
|
||||
fun clearSelection() {
|
||||
_selected.clear()
|
||||
updateSelected()
|
||||
}
|
||||
|
||||
fun toggleSelection(multiselectPart: MultiselectPart) {
|
||||
@@ -257,11 +265,34 @@ class ConversationAdapterV2(
|
||||
} else {
|
||||
_selected.add(multiselectPart)
|
||||
}
|
||||
updateSelected()
|
||||
}
|
||||
|
||||
fun removeFromSelection(expired: Set<MultiselectPart>) {
|
||||
_selected.removeAll(expired)
|
||||
updateSelected()
|
||||
}
|
||||
|
||||
fun updateTimestamps() {
|
||||
notifyItemRangeChanged(0, itemCount, ConversationAdapterBridge.PAYLOAD_TIMESTAMP)
|
||||
}
|
||||
|
||||
fun updateNameColors() {
|
||||
notifyItemRangeChanged(0, itemCount, ConversationAdapterBridge.PAYLOAD_NAME_COLORS)
|
||||
}
|
||||
|
||||
private fun updateSelected() {
|
||||
notifyItemRangeChanged(0, itemCount, ConversationAdapterBridge.PAYLOAD_SELECTED)
|
||||
}
|
||||
|
||||
private inner class ConversationUpdateViewHolder(itemView: View) : ConversationViewHolder<ConversationUpdate>(itemView) {
|
||||
override fun bind(model: ConversationUpdate) {
|
||||
bindable.setEventListener(clickListener)
|
||||
|
||||
if (bindPayloadsIfAvailable()) {
|
||||
return
|
||||
}
|
||||
|
||||
bindable.bind(
|
||||
lifecycleOwner,
|
||||
model.conversationMessage,
|
||||
@@ -274,7 +305,7 @@ class ConversationAdapterV2(
|
||||
searchQuery,
|
||||
false,
|
||||
hasWallpaper && displayMode.displayWallpaper(),
|
||||
true, // isMessageRequestAccepted,
|
||||
isMessageRequestAccepted,
|
||||
model.conversationMessage == inlineContent,
|
||||
colorizer,
|
||||
displayMode
|
||||
@@ -285,6 +316,11 @@ class ConversationAdapterV2(
|
||||
private inner class OutgoingTextOnlyViewHolder(itemView: View) : ConversationViewHolder<OutgoingTextOnly>(itemView) {
|
||||
override fun bind(model: OutgoingTextOnly) {
|
||||
bindable.setEventListener(clickListener)
|
||||
|
||||
if (bindPayloadsIfAvailable()) {
|
||||
return
|
||||
}
|
||||
|
||||
bindable.bind(
|
||||
lifecycleOwner,
|
||||
model.conversationMessage,
|
||||
@@ -297,7 +333,7 @@ class ConversationAdapterV2(
|
||||
searchQuery,
|
||||
false,
|
||||
hasWallpaper && displayMode.displayWallpaper(),
|
||||
true, // isMessageRequestAccepted,
|
||||
isMessageRequestAccepted,
|
||||
model.conversationMessage == inlineContent,
|
||||
colorizer,
|
||||
displayMode
|
||||
@@ -308,6 +344,11 @@ class ConversationAdapterV2(
|
||||
private inner class OutgoingMediaViewHolder(itemView: View) : ConversationViewHolder<OutgoingMedia>(itemView) {
|
||||
override fun bind(model: OutgoingMedia) {
|
||||
bindable.setEventListener(clickListener)
|
||||
|
||||
if (bindPayloadsIfAvailable()) {
|
||||
return
|
||||
}
|
||||
|
||||
bindable.bind(
|
||||
lifecycleOwner,
|
||||
model.conversationMessage,
|
||||
@@ -331,6 +372,11 @@ class ConversationAdapterV2(
|
||||
private inner class IncomingTextOnlyViewHolder(itemView: View) : ConversationViewHolder<IncomingTextOnly>(itemView) {
|
||||
override fun bind(model: IncomingTextOnly) {
|
||||
bindable.setEventListener(clickListener)
|
||||
|
||||
if (bindPayloadsIfAvailable()) {
|
||||
return
|
||||
}
|
||||
|
||||
bindable.bind(
|
||||
lifecycleOwner,
|
||||
model.conversationMessage,
|
||||
@@ -343,7 +389,7 @@ class ConversationAdapterV2(
|
||||
searchQuery,
|
||||
false,
|
||||
hasWallpaper && displayMode.displayWallpaper(),
|
||||
true, // isMessageRequestAccepted,
|
||||
isMessageRequestAccepted,
|
||||
model.conversationMessage == inlineContent,
|
||||
colorizer,
|
||||
displayMode
|
||||
@@ -354,6 +400,11 @@ class ConversationAdapterV2(
|
||||
private inner class IncomingMediaViewHolder(itemView: View) : ConversationViewHolder<IncomingMedia>(itemView) {
|
||||
override fun bind(model: IncomingMedia) {
|
||||
bindable.setEventListener(clickListener)
|
||||
|
||||
if (bindPayloadsIfAvailable()) {
|
||||
return
|
||||
}
|
||||
|
||||
bindable.bind(
|
||||
lifecycleOwner,
|
||||
model.conversationMessage,
|
||||
@@ -406,6 +457,27 @@ class ConversationAdapterV2(
|
||||
}
|
||||
}
|
||||
|
||||
fun bindPayloadsIfAvailable(): Boolean {
|
||||
var payloadApplied = false
|
||||
|
||||
if (payload.contains(ConversationAdapterBridge.PAYLOAD_TIMESTAMP)) {
|
||||
bindable.updateTimestamps()
|
||||
payloadApplied = true
|
||||
}
|
||||
|
||||
if (payload.contains(ConversationAdapterBridge.PAYLOAD_NAME_COLORS)) {
|
||||
bindable.updateContactNameColor()
|
||||
payloadApplied = true
|
||||
}
|
||||
|
||||
if (payload.contains(ConversationAdapterBridge.PAYLOAD_SELECTED)) {
|
||||
bindable.updateSelectedState()
|
||||
payloadApplied = true
|
||||
}
|
||||
|
||||
return payloadApplied
|
||||
}
|
||||
|
||||
override fun showProjectionArea() {
|
||||
bindable.showProjectionArea()
|
||||
}
|
||||
|
||||
@@ -147,6 +147,7 @@ import org.thoughtcrime.securesms.conversation.ConversationReactionOverlay
|
||||
import org.thoughtcrime.securesms.conversation.ConversationReactionOverlay.OnActionSelectedListener
|
||||
import org.thoughtcrime.securesms.conversation.ConversationReactionOverlay.OnHideListener
|
||||
import org.thoughtcrime.securesms.conversation.ConversationSearchViewModel
|
||||
import org.thoughtcrime.securesms.conversation.ConversationUpdateTick
|
||||
import org.thoughtcrime.securesms.conversation.MarkReadHelper
|
||||
import org.thoughtcrime.securesms.conversation.MenuState
|
||||
import org.thoughtcrime.securesms.conversation.MessageSendType
|
||||
@@ -820,7 +821,7 @@ class ConversationFragment :
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.subscribeBy(onNext = {
|
||||
colorizer.onNameColorsChanged(it)
|
||||
adapter.notifyItemRangeChanged(0, adapter.itemCount)
|
||||
adapter.updateNameColors()
|
||||
})
|
||||
|
||||
val disabledInputListener = DisabledInputListener()
|
||||
@@ -966,6 +967,9 @@ class ConversationFragment :
|
||||
}
|
||||
|
||||
getVoiceNoteMediaController().voiceNotePlaybackState.observe(viewLifecycleOwner, inputPanel.playbackStateObserver)
|
||||
|
||||
val conversationUpdateTick = ConversationUpdateTick { adapter.updateTimestamps() }
|
||||
viewLifecycleOwner.lifecycle.addObserver(conversationUpdateTick)
|
||||
}
|
||||
|
||||
private fun initializeInlineSearch() {
|
||||
@@ -1224,8 +1228,11 @@ class ConversationFragment :
|
||||
binding.conversationDisabledInput.setWallpaperEnabled(wallpaperEnabled)
|
||||
inputPanel.setWallpaperEnabled(wallpaperEnabled)
|
||||
|
||||
adapter.onHasWallpaperChanged(wallpaperEnabled)
|
||||
val stateChanged = adapter.onHasWallpaperChanged(wallpaperEnabled)
|
||||
conversationItemDecorations.hasWallpaper = wallpaperEnabled
|
||||
if (stateChanged) {
|
||||
binding.conversationItemRecycler.invalidateItemDecorations()
|
||||
}
|
||||
|
||||
val navColor = if (wallpaperEnabled) {
|
||||
R.color.conversation_navigation_wallpaper
|
||||
@@ -2295,6 +2302,25 @@ class ConversationFragment :
|
||||
layoutManager.scrollToPositionWithOffset(0, 0)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onItemRangeRemoved(positionStart: Int, itemCount: Int) {
|
||||
if (actionMode == null) {
|
||||
return
|
||||
}
|
||||
|
||||
val expired: Set<MultiselectPart> = adapter
|
||||
.selectedItems
|
||||
.filter { it.isExpired() }
|
||||
.toSet()
|
||||
|
||||
adapter.removeFromSelection(expired)
|
||||
|
||||
if (adapter.selectedItems.isEmpty()) {
|
||||
actionMode?.finish()
|
||||
} else {
|
||||
actionMode?.setTitle(calculateSelectedItemCount())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//endregion Scroll Handling
|
||||
|
||||
Reference in New Issue
Block a user