Commit 64a8d351 authored by Leonardo Aramaki's avatar Leonardo Aramaki

Add @all and @here when suggesting members

parent c678be49
package chat.rocket.android.chatroom.adapter package chat.rocket.android.chatroom.adapter
import DrawableHelper import DrawableHelper
import android.content.Context
import android.view.LayoutInflater import android.view.LayoutInflater
import android.view.View import android.view.View
import android.view.ViewGroup import android.view.ViewGroup
...@@ -16,7 +17,30 @@ import chat.rocket.android.widget.autocompletion.ui.SuggestionsAdapter ...@@ -16,7 +17,30 @@ import chat.rocket.android.widget.autocompletion.ui.SuggestionsAdapter
import chat.rocket.common.model.UserStatus import chat.rocket.common.model.UserStatus
import com.facebook.drawee.view.SimpleDraweeView import com.facebook.drawee.view.SimpleDraweeView
class PeopleSuggestionsAdapter : SuggestionsAdapter<PeopleSuggestionViewHolder>("@") { class PeopleSuggestionsAdapter(context: Context) : SuggestionsAdapter<PeopleSuggestionViewHolder>("@") {
init {
val allDescription = context.getString(R.string.suggest_all_description)
val hereDescription = context.getString(R.string.suggest_here_description)
val pinnedList = listOf(
PeopleViewModel(imageUri = null,
text = "all",
username = "all",
name = allDescription,
status = null,
pinned = false,
searchList = listOf("all")),
PeopleViewModel(imageUri = null,
text = "here",
username = "here",
name = hereDescription,
status = null,
pinned = false,
searchList = listOf("here"))
)
setPinnedSuggestions(pinnedList)
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PeopleSuggestionViewHolder { override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PeopleSuggestionViewHolder {
val view = LayoutInflater.from(parent.context).inflate(R.layout.suggestion_member_item, parent, val view = LayoutInflater.from(parent.context).inflate(R.layout.suggestion_member_item, parent,
false) false)
...@@ -34,15 +58,19 @@ class PeopleSuggestionsAdapter : SuggestionsAdapter<PeopleSuggestionViewHolder>( ...@@ -34,15 +58,19 @@ class PeopleSuggestionsAdapter : SuggestionsAdapter<PeopleSuggestionViewHolder>(
val statusView = itemView.findViewById<ImageView>(R.id.image_status) val statusView = itemView.findViewById<ImageView>(R.id.image_status)
username.text = item.username username.text = item.username
name.text = item.name name.text = item.name
if (item.imageUri.isEmpty()) { if (item.imageUri?.isEmpty() != false) {
avatar.setVisible(false) avatar.setVisible(false)
} else { } else {
avatar.setVisible(true) avatar.setVisible(true)
avatar.setImageURI(item.imageUri) avatar.setImageURI(item.imageUri)
} }
val status = item.status ?: UserStatus.Offline() val status = item.status
if (status != null) {
val statusDrawable = DrawableHelper.getUserStatusDrawable(status, itemView.context) val statusDrawable = DrawableHelper.getUserStatusDrawable(status, itemView.context)
statusView.setImageDrawable(statusDrawable) statusView.setImageDrawable(statusDrawable)
} else {
statusView.setVisible(false)
}
setOnClickListener { setOnClickListener {
itemClickListener?.onClick(item) itemClickListener?.onClick(item)
} }
......
...@@ -493,7 +493,7 @@ class ChatRoomFragment : Fragment(), ChatRoomView, EmojiKeyboardListener, EmojiR ...@@ -493,7 +493,7 @@ class ChatRoomFragment : Fragment(), ChatRoomView, EmojiKeyboardListener, EmojiR
private fun setupSuggestionsView() { private fun setupSuggestionsView() {
suggestions_view.anchor(text_message) suggestions_view.anchor(text_message)
.bindTokenAdapter(PeopleSuggestionsAdapter()) .bindTokenAdapter(PeopleSuggestionsAdapter(context!!))
.bindTokenAdapter(RoomSuggestionsAdapter()) .bindTokenAdapter(RoomSuggestionsAdapter())
.addSuggestionProviderAction("@") { query -> .addSuggestionProviderAction("@") { query ->
if (query.isNotEmpty()) { if (query.isNotEmpty()) {
......
...@@ -3,7 +3,7 @@ package chat.rocket.android.chatroom.viewmodel ...@@ -3,7 +3,7 @@ package chat.rocket.android.chatroom.viewmodel
import chat.rocket.android.widget.autocompletion.model.SuggestionModel import chat.rocket.android.widget.autocompletion.model.SuggestionModel
import chat.rocket.common.model.UserStatus import chat.rocket.common.model.UserStatus
class PeopleViewModel(val imageUri: String, class PeopleViewModel(val imageUri: String?,
text: String, text: String,
val username: String, val username: String,
val name: String, val name: String,
......
...@@ -6,5 +6,6 @@ interface CompletionStrategy { ...@@ -6,5 +6,6 @@ interface CompletionStrategy {
fun getItem(prefix: String, position: Int): SuggestionModel fun getItem(prefix: String, position: Int): SuggestionModel
fun autocompleteItems(prefix: String): List<SuggestionModel> fun autocompleteItems(prefix: String): List<SuggestionModel>
fun addAll(list: List<SuggestionModel>) fun addAll(list: List<SuggestionModel>)
fun addPinned(list: List<SuggestionModel>)
fun size(): Int fun size(): Int
} }
\ No newline at end of file
...@@ -6,23 +6,30 @@ import java.util.concurrent.CopyOnWriteArrayList ...@@ -6,23 +6,30 @@ import java.util.concurrent.CopyOnWriteArrayList
internal class StringMatchingCompletionStrategy : CompletionStrategy { internal class StringMatchingCompletionStrategy : CompletionStrategy {
private val list = CopyOnWriteArrayList<SuggestionModel>() private val list = CopyOnWriteArrayList<SuggestionModel>()
private val pinnedList = mutableListOf<SuggestionModel>()
override fun autocompleteItems(prefix: String): List<SuggestionModel> { override fun autocompleteItems(prefix: String): List<SuggestionModel> {
return list.filter { val partialResult = list.filter {
it.searchList.forEach { word -> it.searchList.forEach { word ->
if (word.contains(prefix, ignoreCase = true)) { if (word.contains(prefix, ignoreCase = true)) {
return@filter true return@filter true
} }
} }
false false
}.sortedByDescending { it.pinned }.take(5) }.sortedByDescending { it.pinned }
val result = partialResult.take(5).toMutableList()
result.addAll(pinnedList)
return result.toList()
} }
override fun addAll(list: List<SuggestionModel>) { override fun addAll(list: List<SuggestionModel>) {
// this.list.removeAll { !it.pinned }
this.list.addAllAbsent(list) this.list.addAllAbsent(list)
} }
override fun addPinned(list: List<SuggestionModel>) {
this.pinnedList.addAll(list)
}
override fun getItem(prefix: String, position: Int): SuggestionModel { override fun getItem(prefix: String, position: Int): SuggestionModel {
return list[position] return list[position]
} }
......
...@@ -27,5 +27,9 @@ class TrieCompletionStrategy : CompletionStrategy { ...@@ -27,5 +27,9 @@ class TrieCompletionStrategy : CompletionStrategy {
} }
} }
override fun addPinned(list: List<SuggestionModel>) {
}
override fun size() = items.size override fun size() = items.size
} }
\ No newline at end of file
...@@ -12,9 +12,10 @@ abstract class SuggestionsAdapter<VH : BaseSuggestionViewHolder>(val token: Stri ...@@ -12,9 +12,10 @@ abstract class SuggestionsAdapter<VH : BaseSuggestionViewHolder>(val token: Stri
private var itemType: Type? = null private var itemType: Type? = null
private var itemClickListener: ItemClickListener? = null private var itemClickListener: ItemClickListener? = null
private var providerExternal: ((query: String) -> Unit)? = null private var providerExternal: ((query: String) -> Unit)? = null
private var pinnedSuggestions: List<SuggestionModel>? = null
private var prefix: String by Delegates.observable("", { _, _, _ -> private var prefix: String by Delegates.observable("", { _, _, _ ->
strategy.autocompleteItems(prefix) strategy.autocompleteItems(prefix)
notifyItemRangeChanged(0, 5) notifyDataSetChanged()
}) })
init { init {
...@@ -35,6 +36,15 @@ abstract class SuggestionsAdapter<VH : BaseSuggestionViewHolder>(val token: Stri ...@@ -35,6 +36,15 @@ abstract class SuggestionsAdapter<VH : BaseSuggestionViewHolder>(val token: Stri
return strategy.autocompleteItems(prefix)[position] return strategy.autocompleteItems(prefix)[position]
} }
/**
* Set suggestions that should always appear when prompted.
*
* @param suggestions The list of suggestions that will be pinned.
*/
fun setPinnedSuggestions(suggestions: List<SuggestionModel>) {
this.strategy.addPinned(suggestions)
}
fun autocomplete(prefix: String) { fun autocomplete(prefix: String) {
this.prefix = prefix.toLowerCase().trim() this.prefix = prefix.toLowerCase().trim()
} }
......
...@@ -94,7 +94,7 @@ class SuggestionsView : FrameLayout, TextWatcher { ...@@ -94,7 +94,7 @@ class SuggestionsView : FrameLayout, TextWatcher {
if (new.startsWith(" ")) { if (new.startsWith(" ")) {
// just halts the completion execution // just halts the completion execution
cancelSuggestions(false) cancelSuggestions(true)
return return
} }
......
...@@ -6,9 +6,9 @@ ...@@ -6,9 +6,9 @@
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginBottom="2dp" android:layout_marginBottom="2dp"
android:layout_marginEnd="2dp" android:layout_marginEnd="2dp"
android:layout_marginLeft="4dp" android:layout_marginLeft="8dp"
android:layout_marginRight="2dp" android:layout_marginRight="2dp"
android:layout_marginStart="4dp" android:layout_marginStart="8dp"
android:layout_marginTop="2dp" android:layout_marginTop="2dp"
android:background="@color/suggestion_background_color"> android:background="@color/suggestion_background_color">
...@@ -22,7 +22,8 @@ ...@@ -22,7 +22,8 @@
android:id="@+id/image_avatar" android:id="@+id/image_avatar"
android:layout_width="24dp" android:layout_width="24dp"
android:layout_height="24dp" android:layout_height="24dp"
android:layout_margin="4dp" android:layout_marginTop="4dp"
android:layout_marginBottom="4dp"
app:roundedCornerRadius="3dp" app:roundedCornerRadius="3dp"
tools:src="@tools:sample/avatars" /> tools:src="@tools:sample/avatars" />
......
...@@ -117,4 +117,8 @@ ...@@ -117,4 +117,8 @@
<string name="status_authenticating">autenticando</string> <string name="status_authenticating">autenticando</string>
<string name="status_disconnecting">desconectando</string> <string name="status_disconnecting">desconectando</string>
<string name="status_waiting">conectando em %d segundos</string> <string name="status_waiting">conectando em %d segundos</string>
<!--Suggestions-->
<string name="suggest_all_description">Notifica todos nesta sala</string>
<string name="suggest_here_description">Notifica usuários ativos nesta sala</string>
</resources> </resources>
\ No newline at end of file
...@@ -119,4 +119,8 @@ ...@@ -119,4 +119,8 @@
<string name="status_disconnecting">disconnecting</string> <string name="status_disconnecting">disconnecting</string>
<string name="status_waiting">connecting in %d seconds</string> <string name="status_waiting">connecting in %d seconds</string>
<!--Suggestions-->
<string name="suggest_all_description">Notify all in this room</string>
<string name="suggest_here_description">Notify active users in this room</string>
</resources> </resources>
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment