Android auto-translation chat - how to translate and refresh UI

[Problem/Question]
We are using SendBird for chat and VoIP calls, and to be more precise, we use the Group-channel.

Now, we are trying to implement auto-translation feature but we couldn’t find any documentation how to perform that exactly. For now, we are NOT implementing our chat list or adapter. We use this sdk as is out of the box.
Recently, we implemented CustomFragment via CustomFragmentFactory, in order to add the translation feature (or at least we were hoping this is the path we need).

This is what we use:

SendbirdUIKit.setUIKitFragmentFactory(CustomFragmentFactory(context))
SendbirdUIKit.setDefaultThemeMode(SendbirdUIKit.ThemeMode.Light)

Also, we use CustomMessageListComponent.

There are two cases where we need to use translate feature:

  1. New message arrives - we need to translate it and display it in the chat (translated)
  2. Previous/existing messages to be translated as well

Most confusing part to us is that we don’t know how to update the UI with translated message, or messages. In the documentation all we can find is this comment: // Display translation in the UI.

This is from the documentation:

SendbirdChat.addChannelHandler(
    UNIQUE_HANDLER_ID,
    object : GroupChannelHandler() {
        override fun onMessageReceived(channel: BaseChannel, message: BaseMessage) {
            if (message is UserMessage) {
                val map = message.translations
                val esTranslatedMessage = map["es"] // Spanish

                // Display translation in the UI.
            }
        }
    }
)

It does not show how to update the UI.

Should we override the Adapter for messages?
How to access and update UI in the adapter?

Recently, we tried overriding the fragment, where we could load the messages list from LiveData, and try translating it on-demand, message by message. After that we would try calling adapter.setItems(…), with our list.

Of course, it does not work as expected.

P.S. For chat initialization, we use SendbirdUIKit.init().
These are the lib versions we use:

com.sendbird.sdk:uikit:3.2.0
com.sendbird.sdk:sendbird-chat:3.8.2
1 Like

After deep investigation, we managed to find solution which is a bit hacky, and it is not written anywhere in the documentation.

It requires to crease a custom adapter extending MessageListAdapter, in order to hack the access to the textview for setting translated text. It took us some time to find in SDK’s source code the textViews res ID.

The key is in the following lines:

            val chatView = holder.clickableViewMap[ClickableViewIdentifier.Chat.name]
            val textViewMessage = chatView?.findViewById<TextView>(R.id.tvMessage)
            if (textViewMessage != null) {
                textViewMessage.text = translatedMessage ?: userMessage.message
            }

Our entire adapter class looks like this:

class CustomMessageListAdapter(
    channel: GroupChannel,
    var selectedLanguage: String
) : MessageListAdapter(channel) {

    override fun onBindViewHolder(holder: MessageViewHolder, position: Int) {
        super.onBindViewHolder(holder, position)

        val userMessage = getItem(position) as? UserMessage
        if (userMessage != null) {
            val translatedMessage = userMessage.translations[selectedLanguage]

            val chatView = holder.clickableViewMap[ClickableViewIdentifier.Chat.name]
            val textViewMessage = chatView?.findViewById<TextView>(R.id.tvMessage)
            if (textViewMessage != null) {
                textViewMessage.text = translatedMessage ?: userMessage.message
            }
        }
    }
}

It would be great to have a property, for adapter or fragment or SDK, to set desired language code and it automatically shows message translated to that language. That would be the real auto-translate feature!

1 Like