mirror of
https://github.com/nextcloud/talk-android
synced 2025-07-11 06:44:09 +01:00
add handling for multiple typing participants
Signed-off-by: Marcel Hibbe <dev@mhibbe.de>
This commit is contained in:
parent
85f637ca8a
commit
6adca2395d
@ -52,6 +52,7 @@ import android.provider.ContactsContract
|
|||||||
import android.provider.MediaStore
|
import android.provider.MediaStore
|
||||||
import android.text.Editable
|
import android.text.Editable
|
||||||
import android.text.InputFilter
|
import android.text.InputFilter
|
||||||
|
import android.text.SpannableStringBuilder
|
||||||
import android.text.TextUtils
|
import android.text.TextUtils
|
||||||
import android.text.TextWatcher
|
import android.text.TextWatcher
|
||||||
import android.util.Log
|
import android.util.Log
|
||||||
@ -76,6 +77,7 @@ import androidx.core.content.ContextCompat
|
|||||||
import androidx.core.content.FileProvider
|
import androidx.core.content.FileProvider
|
||||||
import androidx.core.content.PermissionChecker
|
import androidx.core.content.PermissionChecker
|
||||||
import androidx.core.graphics.drawable.toBitmap
|
import androidx.core.graphics.drawable.toBitmap
|
||||||
|
import androidx.core.text.bold
|
||||||
import androidx.core.widget.doAfterTextChanged
|
import androidx.core.widget.doAfterTextChanged
|
||||||
import androidx.emoji2.text.EmojiCompat
|
import androidx.emoji2.text.EmojiCompat
|
||||||
import androidx.emoji2.widget.EmojiTextView
|
import androidx.emoji2.widget.EmojiTextView
|
||||||
@ -304,6 +306,7 @@ class ChatActivity :
|
|||||||
private var videoURI: Uri? = null
|
private var videoURI: Uri? = null
|
||||||
|
|
||||||
var typingTimer: CountDownTimer? = null
|
var typingTimer: CountDownTimer? = null
|
||||||
|
val typingParticipants = HashMap<String, String>()
|
||||||
|
|
||||||
private val localParticipantMessageListener = object : SignalingMessageReceiver.LocalParticipantMessageListener {
|
private val localParticipantMessageListener = object : SignalingMessageReceiver.LocalParticipantMessageListener {
|
||||||
override fun onSwitchTo(token: String?) {
|
override fun onSwitchTo(token: String?) {
|
||||||
@ -318,16 +321,85 @@ class ChatActivity :
|
|||||||
}
|
}
|
||||||
|
|
||||||
private val conversationMessageListener = object : SignalingMessageReceiver.ConversationMessageListener {
|
private val conversationMessageListener = object : SignalingMessageReceiver.ConversationMessageListener {
|
||||||
override fun onStartTyping(session: String?) {
|
override fun onStartTyping(session: String) {
|
||||||
val name = webSocketInstance?.getDisplayNameForSession(session)
|
var name = webSocketInstance?.getDisplayNameForSession(session)
|
||||||
|
|
||||||
// binding.typingIndicator.visibility = View.VISIBLE
|
if (name != null && !typingParticipants.contains(session)) {
|
||||||
binding.typingIndicator.text = name + " started typing"
|
if (name == "") {
|
||||||
|
name = context.resources?.getString(R.string.nc_guest)!!
|
||||||
|
}
|
||||||
|
typingParticipants[session] = name
|
||||||
|
updateTypingIndicator()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onStopTyping(session: String?) {
|
override fun onStopTyping(session: String) {
|
||||||
// binding.typingIndicator.visibility = View.INVISIBLE
|
typingParticipants.remove(session)
|
||||||
binding.typingIndicator.text = "x"
|
updateTypingIndicator()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun updateTypingIndicator() {
|
||||||
|
val participantNames = ArrayList(typingParticipants.values)
|
||||||
|
|
||||||
|
val typingString: SpannableStringBuilder
|
||||||
|
when (typingParticipants.size) {
|
||||||
|
0 -> {
|
||||||
|
typingString = SpannableStringBuilder().append("")
|
||||||
|
}
|
||||||
|
|
||||||
|
1 -> {
|
||||||
|
typingString = SpannableStringBuilder()
|
||||||
|
.bold { append(participantNames[0]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.typing_is_typing))
|
||||||
|
}
|
||||||
|
|
||||||
|
2 -> typingString = SpannableStringBuilder()
|
||||||
|
.bold { append(participantNames[0]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE)
|
||||||
|
.bold { append(participantNames[1]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing))
|
||||||
|
|
||||||
|
3 -> typingString = SpannableStringBuilder()
|
||||||
|
.bold { append(participantNames[0]) }
|
||||||
|
.append(COMMA)
|
||||||
|
.bold { append(participantNames[1]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.nc_common_and) + WHITESPACE)
|
||||||
|
.bold { append(participantNames[2]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.typing_are_typing))
|
||||||
|
|
||||||
|
4 -> typingString = SpannableStringBuilder()
|
||||||
|
.bold { append(participantNames[0]) }
|
||||||
|
.append(COMMA)
|
||||||
|
.bold { append(participantNames[1]) }
|
||||||
|
.append(COMMA)
|
||||||
|
.bold { append(participantNames[2]) }
|
||||||
|
.append(WHITESPACE + context.resources?.getString(R.string.typing_1_other))
|
||||||
|
|
||||||
|
else -> {
|
||||||
|
val moreTypersAmount = typingParticipants.size - 3
|
||||||
|
|
||||||
|
val othersTyping = context.resources?.getString(R.string.typing_x_others)?.let {
|
||||||
|
String.format(it, moreTypersAmount)
|
||||||
|
}
|
||||||
|
|
||||||
|
typingString = SpannableStringBuilder()
|
||||||
|
.bold { append(participantNames[0]) }
|
||||||
|
.append(COMMA)
|
||||||
|
.bold { append(participantNames[1]) }
|
||||||
|
.append(COMMA)
|
||||||
|
.bold { append(participantNames[2]) }
|
||||||
|
.append(othersTyping)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
runOnUiThread {
|
||||||
|
if (participantNames.size > 0) {
|
||||||
|
binding.typingIndicator.visibility = View.VISIBLE
|
||||||
|
} else {
|
||||||
|
binding.typingIndicator.visibility = View.GONE
|
||||||
|
}
|
||||||
|
binding.typingIndicator.text = typingString
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3690,5 +3762,8 @@ class ChatActivity :
|
|||||||
private const val LOOKING_INTO_FUTURE_TIMEOUT = 30
|
private const val LOOKING_INTO_FUTURE_TIMEOUT = 30
|
||||||
private const val CHUNK_SIZE: Int = 10
|
private const val CHUNK_SIZE: Int = 10
|
||||||
private const val ONE_SECOND_IN_MILLIS = 1000
|
private const val ONE_SECOND_IN_MILLIS = 1000
|
||||||
|
|
||||||
|
private const val WHITESPACE = " "
|
||||||
|
private const val COMMA = ", "
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -164,9 +164,10 @@
|
|||||||
<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="wrap_content"
|
android:layout_height="match_parent"
|
||||||
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:textColor="@color/low_emphasis_text"
|
||||||
tools:text="Marcel is typing">
|
tools:text="Marcel is typing">
|
||||||
</TextView>
|
</TextView>
|
||||||
|
|
||||||
|
@ -44,6 +44,7 @@ How to translate with transifex:
|
|||||||
<!-- Common -->
|
<!-- Common -->
|
||||||
<string name="nc_yes">Yes</string>
|
<string name="nc_yes">Yes</string>
|
||||||
<string name="nc_no">No</string>
|
<string name="nc_no">No</string>
|
||||||
|
<string name="nc_common_and">and</string>
|
||||||
<string name="nc_common_skip">Skip</string>
|
<string name="nc_common_skip">Skip</string>
|
||||||
<string name="nc_common_set">Set</string>
|
<string name="nc_common_set">Set</string>
|
||||||
<string name="nc_common_dismiss">Dismiss</string>
|
<string name="nc_common_dismiss">Dismiss</string>
|
||||||
@ -447,6 +448,10 @@ How to translate with transifex:
|
|||||||
<string name="open_in_files_app">Open in Files app</string>
|
<string name="open_in_files_app">Open in Files app</string>
|
||||||
<string name="send_to_forbidden">You are not allowed to share content to this chat</string>
|
<string name="send_to_forbidden">You are not allowed to share content to this chat</string>
|
||||||
|
|
||||||
|
<string name="typing_is_typing">is typing</string>
|
||||||
|
<string name="typing_are_typing">are typing</string>
|
||||||
|
<string name="typing_1_other">and 1 other is typing…</string>
|
||||||
|
<string name="typing_x_others">and %1$s others are typing…</string>
|
||||||
|
|
||||||
<!-- Upload -->
|
<!-- Upload -->
|
||||||
<string name="nc_add_file">Add to conversation</string>
|
<string name="nc_add_file">Add to conversation</string>
|
||||||
|
Loading…
Reference in New Issue
Block a user