How to organize RecyclerView on Chat App with different types of messages?(如何在聊天应用上组织不同类型的消息的循环查看?)
问题描述
我开发的聊天应用程序,有不同类型的消息:简单的文本、图像、文件等。 还有就是信息(其他,在屏幕的左边)和我的信息(在屏幕的右边)。
现在,我对每种类型的邮件都有不同的布局:
Item_Message_Simple
Item_My_Message_Simple
Item_Message_Image
Item_My_Message_Image
Item_Message_FILE
Item_My_Message_FILE
所有这些类型都是在ReccyclerView.Adapter中定义的,并且getItemViewType()中有许多If-Else条件
还可以回复和转发具有更复杂布局的消息。 如果我想添加新的消息类型,那将是一场灾难。那么如何更好地组织呢? 也许它应该全部包含在一个布局和两种类型中:Message、My_Message和显示/隐藏布局的各个部分。 或再次键入2个类型(MESSAGE、MY_MESSAGE)并在ViewHolder中膨胀所需的子布局。
请帮忙!
推荐答案
在我的情况下,我也有相同类型的邮件选项,需要根据发件人邮件和收到的邮件进行区分。我根据消息类型创建视图容器时,为发送者和接收者添加了不同的布局
每个MSG具有不同的消息选项(文本、图像、视频、文件、音频等),我处理onBindViewHolder()中的切换大小写,具有可见性显示和隐藏。我总共有三个不同的取景器。
您:您发送的邮件(应始终显示在屏幕上)在您的案例中My_Message
其他:您的案例中由其他人发送的邮件(应始终显示在屏幕左侧)邮件
时间线:时间线消息,如用户更改聊天名称、删除so n so用户等
所以这里
@Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
MyViewHolder viewHolder = null;
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
switch (viewType) {
case YOU:
View v1 = inflater.inflate(R.layout.chat_right_layout, parent, false);
viewHolder = new MyViewHolder(v1, true);
break;
case OTHERS:
View v2 = inflater.inflate(R.layout.chat_left_layout, parent, false);
viewHolder = new MyViewHolder(v2, false);
break;
case TIMELINE:
View v3 = inflater.inflate(R.layout.chat_timeline_layout, parent, false);
viewHolder = new MyViewHolder(v3, false);
break;
}
return viewHolder;
}
这里我总共有3个不同的XML文件(您、其他人和时间线消息)
您和其他每个XML版面都具有分别合并文本、图像和PDF的视图。
@Override
public void onBindViewHolder(final MyViewHolder holder, int position) {
ChatModel model = mDataList.get(position);
if (model.getMessageType() == 10) // timeline message {
holder.mTvTimeLine.setText(DecodeUtil.decodeBase64(model.getMessageText())+" on "+date);
}else{
showTextAndMediaData(holder, model);
}
}
以下是我编写的逻辑,用于单独处理不同的消息类型(您和其他人的文本、图像等)。
private void showTextAndMediaData(MyViewHolder myViewHolder, ChatModel model) {
switch (model.getMessageType()) {
case 1: // Image Type
myViewHolder.mTxtMsg.setVisibility(View.GONE);
myViewHolder.chatImageView.setVisibility(View.VISIBLE);
myViewHolder.videoLayout.setVisibility(View.GONE);
myViewHolder.documentImageView.setVisibility(View.GONE);
Uri mInitialUri = Uri.parse(model.getMessageText());
try {
myViewHolder.chatImageView.setImageURI(mInitialUri);
} catch (Exception e) {
e.printStackTrace();
}
break;
case 3: // video type
myViewHolder.mTxtMsg.setVisibility(View.GONE);
myViewHolder.chatImageView.setVisibility(View.GONE);
myViewHolder.videoLayout.setVisibility(View.VISIBLE);
myViewHolder.documentImageView.setVisibility(View.GONE);
Glide.with(mContext).load(Headers.getUrlWithHeaders(mContext, model.getThumbnailURL()))
.placeholder(R.drawable.novideo)
.thumbnail(0.5f)
.crossFade()
.diskCacheStrategy(DiskCacheStrategy.ALL)
.into(myViewHolder.vedioImageView);
}
break;
case 4:
case 5:
case 6:
case 7:
case 8:
case 9: // file type
myViewHolder.mTxtMsg.setVisibility(View.GONE);
myViewHolder.chatImageView.setVisibility(View.GONE);
myViewHolder.videoLayout.setVisibility(View.GONE);
myViewHolder.documentImageView.setVisibility(View.VISIBLE);
switch (model.getMediaType()) {
case "doc":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_word_document));
break;
case "pdf":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_pdf));
break;
case "excel":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_excel));
break;
case "ppt":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_ppt));
break;
case "txt":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_txt));
break;
case "csv":
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_csv));
break;
default:
myViewHolder.documentImageView.setImageDrawable(ContextCompat.getDrawable(mContext, R.drawable.img_otherdoc));
}
break;
default: // text type
myViewHolder.mTxtMsg.setVisibility(View.VISIBLE);
myViewHolder.chatImageView.setVisibility(View.GONE);
myViewHolder.videoLayout.setVisibility(View.GONE);
myViewHolder.documentImageView.setVisibility(View.GONE);
try {
myViewHolder.mTxtMsg.setText(text);
} catch (Exception e) {
e.printStackTrace();
myViewHolder.mTxtMsg.setText(text);
}
}
}
删除了一些案例逻辑,因为所有案例逻辑的类型都不同,并且处理方式相同。我还有一些关于发送者和接收者的更多逻辑,也在这个挡路中去掉了。您可以根据需要添加
是的,添加新消息类型很困难,您需要在onBindViewHolder中再添加一个案例才能添加它。
希望它能对您完成任务有所帮助。
这篇关于如何在聊天应用上组织不同类型的消息的循环查看?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!
本文标题为:如何在聊天应用上组织不同类型的消息的循环查看?
基础教程推荐
- Kivy Buildozer 无法构建 apk,命令失败:./distribute.sh -m “kivy"d 2022-01-01
- 如何在没有IB的情况下将2个按钮添加到右侧的UINavigationbar? 2022-01-01
- 当从同一个组件调用时,两个 IBAction 触发的顺序是什么? 2022-01-01
- 如何在 iPhone 上显示来自 API 的 HTML 文本? 2022-01-01
- 如何在 UIImageView 中异步加载图像? 2022-01-01
- 如何让对象对 Cocos2D 中的触摸做出反应? 2022-01-01
- UIWebView 委托方法 shouldStartLoadWithRequest:在 WKWebView 中等效? 2022-01-01
- android 应用程序已发布,但在 google play 中找不到 2022-01-01
- 在 gmail 中为 ios 应用程序检索朋友的朋友 2022-01-01
- Android:对话框关闭而不调用关闭 2022-01-01