diff --git a/app/src/main/java/org/thoughtcrime/securesms/conversation/BodyBubbleLayoutTransition.kt b/app/src/main/java/org/thoughtcrime/securesms/conversation/BodyBubbleLayoutTransition.kt index b65a48b7e2..6238aea391 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/conversation/BodyBubbleLayoutTransition.kt +++ b/app/src/main/java/org/thoughtcrime/securesms/conversation/BodyBubbleLayoutTransition.kt @@ -1,15 +1,8 @@ package org.thoughtcrime.securesms.conversation import android.animation.LayoutTransition -import android.animation.ValueAnimator -import androidx.core.animation.addListener -import androidx.recyclerview.widget.RecyclerView -import java.lang.IllegalStateException - -class BodyBubbleLayoutTransition(bodyBubble: ConversationItemBodyBubble) : LayoutTransition() { - - private val animator: ValueAnimator = ValueAnimator.ofFloat(0f, 1f) +class BodyBubbleLayoutTransition : LayoutTransition() { init { disableTransitionType(APPEARING) disableTransitionType(DISAPPEARING) @@ -17,25 +10,5 @@ class BodyBubbleLayoutTransition(bodyBubble: ConversationItemBodyBubble) : Layou disableTransitionType(CHANGING) setDuration(100L) - - animator.duration = getAnimator(CHANGE_DISAPPEARING).duration - animator.addUpdateListener { - val parentRecycler: RecyclerView? = bodyBubble.parent?.parent as? RecyclerView - - try { - parentRecycler?.invalidate() - } catch (e: IllegalStateException) { - // In scroll or layout. Skip this frame. - } - } - - getAnimator(CHANGE_DISAPPEARING).addListener( - onStart = { - animator.start() - }, - onEnd = { - animator.end() - } - ) } } diff --git a/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationFragment.java b/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationFragment.java index 20116a8199..ede3fe6419 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationFragment.java +++ b/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationFragment.java @@ -17,6 +17,9 @@ package org.thoughtcrime.securesms.conversation; import android.Manifest; +import android.animation.Animator; +import android.animation.LayoutTransition; +import android.animation.ValueAnimator; import android.annotation.SuppressLint; import android.app.Activity; import android.content.Context; @@ -215,6 +218,8 @@ public class ConversationFragment extends LoggingFragment implements Multiselect private View toolbarShadow; private Stopwatch startupStopwatch; private View reactionsShade; + private LayoutTransition layoutTransition; + private TransitionListener transitionListener; private GiphyMp4ProjectionRecycler giphyMp4ProjectionRecycler; private Colorizer colorizer; @@ -248,6 +253,9 @@ public class ConversationFragment extends LoggingFragment implements Multiselect list = view.findViewById(android.R.id.list); composeDivider = view.findViewById(R.id.compose_divider); + layoutTransition = new LayoutTransition(); + transitionListener = new TransitionListener(list); + scrollToBottomButton = view.findViewById(R.id.scroll_to_bottom); scrollToMentionButton = view.findViewById(R.id.scroll_to_mention); scrollDateHeader = view.findViewById(R.id.scroll_date_header); @@ -412,6 +420,7 @@ public class ConversationFragment extends LoggingFragment implements Multiselect super.onStart(); initializeTypingObserver(); SignalProxyUtil.startListeningToWebsocket(); + layoutTransition.getAnimator(LayoutTransition.CHANGE_DISAPPEARING).addListener(transitionListener); } @Override @@ -435,6 +444,7 @@ public class ConversationFragment extends LoggingFragment implements Multiselect public void onStop() { super.onStop(); ApplicationDependencies.getTypingStatusRepository().getTypists(threadId).removeObservers(getViewLifecycleOwner()); + layoutTransition.getAnimator(LayoutTransition.CHANGE_DISAPPEARING).removeListener(transitionListener); } @Override @@ -1905,4 +1915,34 @@ public class ConversationFragment extends LoggingFragment implements Multiselect } } } + + private static final class TransitionListener implements Animator.AnimatorListener { + + private final ValueAnimator animator = ValueAnimator.ofFloat(0f, 1f); + + TransitionListener(RecyclerView recyclerView) { + animator.addUpdateListener(unused -> recyclerView.invalidate()); + animator.setDuration(100L); + } + + @Override + public void onAnimationStart(Animator animation) { + animator.start(); + } + + @Override + public void onAnimationEnd(Animator animation) { + animator.end(); + } + + @Override + public void onAnimationCancel(Animator animation) { + // Do Nothing + } + + @Override + public void onAnimationRepeat(Animator animation) { + // Do Nothing + } + } } diff --git a/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationItemBodyBubble.java b/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationItemBodyBubble.java index 3b23701abc..811a54d5e1 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationItemBodyBubble.java +++ b/app/src/main/java/org/thoughtcrime/securesms/conversation/ConversationItemBodyBubble.java @@ -33,17 +33,17 @@ public class ConversationItemBodyBubble extends LinearLayout { public ConversationItemBodyBubble(Context context) { super(context); - setLayoutTransition(new BodyBubbleLayoutTransition(this)); + setLayoutTransition(new BodyBubbleLayoutTransition()); } public ConversationItemBodyBubble(Context context, @Nullable AttributeSet attrs) { super(context, attrs); - setLayoutTransition(new BodyBubbleLayoutTransition(this)); + setLayoutTransition(new BodyBubbleLayoutTransition()); } public ConversationItemBodyBubble(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); - setLayoutTransition(new BodyBubbleLayoutTransition(this)); + setLayoutTransition(new BodyBubbleLayoutTransition()); } public void setOutliners(@NonNull List outliners) { diff --git a/app/src/main/java/org/thoughtcrime/securesms/conversationlist/ConversationListItem.java b/app/src/main/java/org/thoughtcrime/securesms/conversationlist/ConversationListItem.java index 8b7330714d..3dc4b3f8ed 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/conversationlist/ConversationListItem.java +++ b/app/src/main/java/org/thoughtcrime/securesms/conversationlist/ConversationListItem.java @@ -358,7 +358,7 @@ public final class ConversationListItem extends ConstraintLayout } private void observeDisplayBody(@Nullable LiveData displayBody) { - if (displayBody == null) { + if (displayBody == null && glideRequests != null) { glideRequests.clear(thumbTarget); }