make typing indicator two lines if necessary

Signed-off-by: Marcel Hibbe <dev@mhibbe.de>
This commit is contained in:
Marcel Hibbe 2023-05-22 17:27:49 +02:00
parent 7b12f27a1a
commit f0a9a302bb
No known key found for this signature in database
GPG Key ID: C793F8B59F43CE7B
3 changed files with 41 additions and 15 deletions

View File

@ -909,30 +909,38 @@ class ChatActivity :
} }
private fun updateTypingIndicator() { private fun updateTypingIndicator() {
fun ellipsize(text: String): String {
return DisplayUtils.ellipsize(text, TYPING_INDICATOR_MAX_NAME_LENGTH)
}
val participantNames = ArrayList(typingParticipants.values) val participantNames = ArrayList(typingParticipants.values)
val typingString: SpannableStringBuilder val typingString: SpannableStringBuilder
when (typingParticipants.size) { when (typingParticipants.size) {
0 -> typingString = SpannableStringBuilder().append(binding.typingIndicator.text) 0 -> typingString = SpannableStringBuilder().append(binding.typingIndicator.text)
// person1 is typing
1 -> typingString = SpannableStringBuilder() 1 -> typingString = SpannableStringBuilder()
.bold { append(participantNames[0]) } .bold { append(ellipsize(participantNames[0])) }
.append(WHITESPACE + context.resources?.getString(R.string.typing_is_typing)) .append(WHITESPACE + context.resources?.getString(R.string.typing_is_typing))
// person1 and person2 are typing
2 -> typingString = SpannableStringBuilder() 2 -> typingString = SpannableStringBuilder()
.bold { append(participantNames[0]) } .bold { append(ellipsize(participantNames[0])) }
.append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE) .append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE)
.bold { append(participantNames[1]) } .bold { append(ellipsize(participantNames[1])) }
.append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing)) .append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing))
// person1, person2 and person3 are typing
3 -> typingString = SpannableStringBuilder() 3 -> typingString = SpannableStringBuilder()
.bold { append(participantNames[0]) } .bold { append(ellipsize(participantNames[0])) }
.append(COMMA) .append(COMMA)
.bold { append(participantNames[1]) } .bold { append(ellipsize(participantNames[1])) }
.append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE) .append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE)
.bold { append(participantNames[2]) } .bold { append(ellipsize(participantNames[2])) }
.append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing)) .append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing))
// person1, person2, person3 and 1 other is typing
4 -> typingString = SpannableStringBuilder() 4 -> typingString = SpannableStringBuilder()
.bold { append(participantNames[0]) } .bold { append(participantNames[0]) }
.append(COMMA) .append(COMMA)
@ -941,6 +949,7 @@ class ChatActivity :
.bold { append(participantNames[2]) } .bold { append(participantNames[2]) }
.append(WHITESPACE + context.resources?.getString(R.string.typing_1_other)) .append(WHITESPACE + context.resources?.getString(R.string.typing_1_other))
// person1, person2, person3 and x others are typing
else -> { else -> {
val moreTypersAmount = typingParticipants.size - 3 val moreTypersAmount = typingParticipants.size - 3
val othersTyping = context.resources?.getString(R.string.typing_x_others)?.let { val othersTyping = context.resources?.getString(R.string.typing_x_others)?.let {
@ -957,19 +966,26 @@ class ChatActivity :
} }
runOnUiThread { runOnUiThread {
binding.typingIndicator.text = typingString
if (participantNames.size > 0) { if (participantNames.size > 0) {
binding.typingIndicatorWrapper.animate() binding.typingIndicatorWrapper.animate()
.translationY(binding.messageInputView.y - binding.typingIndicator.height) .translationY(binding.messageInputView.y - DisplayUtils.convertDpToPixel(20f, context))
.setInterpolator(AccelerateDecelerateInterpolator()) .setInterpolator(AccelerateDecelerateInterpolator())
.duration = TYPING_INDICATOR_ANIMATION_DURATION .duration = TYPING_INDICATOR_ANIMATION_DURATION
} else { } else {
binding.typingIndicatorWrapper.animate() if (binding.typingIndicator.lineCount == 1) {
.translationY(binding.messageInputView.y) binding.typingIndicatorWrapper.animate()
.setInterpolator(AccelerateDecelerateInterpolator()) .translationY(binding.messageInputView.y)
.duration = TYPING_INDICATOR_ANIMATION_DURATION .setInterpolator(AccelerateDecelerateInterpolator())
.duration = TYPING_INDICATOR_ANIMATION_DURATION
} else if (binding.typingIndicator.lineCount == 2) {
binding.typingIndicatorWrapper.animate()
.translationY(binding.messageInputView.y + DisplayUtils.convertDpToPixel(15f, context))
.setInterpolator(AccelerateDecelerateInterpolator())
.duration = TYPING_INDICATOR_ANIMATION_DURATION
}
} }
binding.typingIndicator.text = typingString
} }
} }
@ -3778,5 +3794,6 @@ class ChatActivity :
private const val WHITESPACE = " " private const val WHITESPACE = " "
private const val COMMA = ", " private const val COMMA = ", "
private const val TYPING_INDICATOR_ANIMATION_DURATION = 200L private const val TYPING_INDICATOR_ANIMATION_DURATION = 200L
private const val TYPING_INDICATOR_MAX_NAME_LENGTH = 14
} }
} }

View File

@ -553,4 +553,11 @@ public class DisplayUtils {
DateFormat df = DateFormat.getDateTimeInstance(); DateFormat df = DateFormat.getDateTimeInstance();
return df.format(date); return df.format(date);
} }
public static String ellipsize(String text, int maxLength) {
if (text.length() > maxLength) {
return text.substring(0, maxLength - 1) + "";
}
return text;
}
} }

View File

@ -156,7 +156,7 @@
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:orientation="vertical" android:orientation="vertical"
android:layout_alignParentBottom="true" android:layout_alignParentBottom="true"
android:layout_marginBottom="-20dp"> android:layout_marginBottom="-19dp">
<View <View
android:id="@+id/separator_1" android:id="@+id/separator_1"
@ -167,7 +167,9 @@
<TextView <TextView
android:id="@+id/typing_indicator" android:id="@+id/typing_indicator"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="20dp" android:layout_height="wrap_content"
android:maxLines="2"
android:ellipsize="end"
android:layout_marginStart="@dimen/side_margin" android:layout_marginStart="@dimen/side_margin"
android:layout_marginEnd="@dimen/side_margin" android:layout_marginEnd="@dimen/side_margin"
android:background="@color/bg_default" android:background="@color/bg_default"