java - 聊天记录 - 图像在文本之前加载 - android
问题描述
我有一个聊天应用程序,现在我在历史部分。(我正在使用这个库 - https://github.com/stfalcon-studio/ChatKit)我从服务器获取数据,然后我检查它是否是文本我显示它,否则如果它是一个图像,那么我请求改造以获取图像字节数组(来自服务器的图像是文本格式,所以我需要一个额外的调用来获取 imageBytes 并用 Glide 显示它。)。我的问题是我的聊天中的示例有 TEXT1、TEXT2、IMAGE1、IMAGE2、TEXT3、IMAGE3、TEXT4。历史加载如下`IMAGE1,IMAGE2,IMAGE3,TEXT1,TEXT2,TEXT3,TEXT4。
这是我的代码。
public class ChatSample extends BaseFragment {
private View mainView;
private ApiClient apiClient;
private MessageList messageList;
private MessagesListAdapter<Message> messagesAdapter;
private String myUserName;
private String sender;
private Message message;
private MessagesHistory[] messagesHistory;
private static final String BUNDLE_USER_NAME = "personUserNameBundle";
private final String senderId = "0";
private static final String TAG = "4564323";
private final int CHAT_IMAGE_TYPE = 5;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
mainView = inflater.inflate(R.layout.chat_fragment, container, false);
apiClient = ApiClient.getInstance();
//Setting my userName and other users userName
Bundle bundle = getArguments();
sender = bundle.getString(BUNDLE_USER_NAME);
myUserName = SharedPreferencesManager.getInstance().getUserData().getUserName();
//A function for image loading
ImageLoader imageLoader = new ImageLoader() {
@Override
public void loadImage(ImageView imageView, String s, byte[] imageBytes) {
Log.d(TAG, "Glide");
if (imageBytes != null) {
Glide.with(getActivity()).load(imageBytes).into(imageView);
}
}
};
messageList = (MessageList) mainView.findViewById(R.id.chatKitList);
messagesAdapter = new MessagesListAdapter<>(senderId, imageLoader);
messageList.setAdapter(messagesAdapter);
//Getting date for requesting history
SimpleDateFormat dateFormat = new SimpleDateFormat(
"yyyy-MM-dd", Locale.US);
Calendar mCurrentDate = Calendar.getInstance();
int year = mCurrentDate.get(Calendar.YEAR);
int month = mCurrentDate.get(Calendar.MONTH);
int day = mCurrentDate.get(Calendar.DAY_OF_MONTH) + 1;
mCurrentDate.set(year, month, day);
Calendar earlierDate = Calendar.getInstance();
int earlierYear = earlierDate.get(Calendar.YEAR);
int earlierMonth = earlierDate.get(Calendar.MONTH);
int earlierDay = earlierDate.get(Calendar.DAY_OF_MONTH) - 7;
earlierDate.set(earlierYear, earlierMonth, earlierDay);
String currentTextDate = dateFormat.format(mCurrentDate.getTime());
String earlierTextDate = dateFormat.format(earlierDate.getTime());
//requesting history
getMessages(earlierTextDate, currentTextDate);
return mainView;
}
//History request
public void getMessages(final String from, final String to) {
Call<MessagesHistory[]> getMessageHistory = apiClient.getMessageHistory(from, to);
getMessageHistory.enqueue(new Callback<MessagesHistory[]>() {
@Override
public void onResponse(Call<MessagesHistory[]> call, Response<MessagesHistory[]> response) {
if (response.isSuccessful()) {
messagesHistory = response.body();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss", Locale.getDefault());
dateFormat.setTimeZone(TimeZone.getTimeZone("Etc/UTC"));
//Getting all information about history
for (int i = 0; i < messagesHistory.length; i++) {
String messageSender = messagesHistory[i].getSender();
String messageReceiver = messagesHistory[i].getReceiver();
final String messages = messagesHistory[i].getText();
String date = messagesHistory[i].getSendtime();
Date convertDate = new Date();
try {
convertDate = dateFormat.parse(date);
} catch (ParseException e) {
e.printStackTrace();
}
convertDate.getTime();
//If I'm sending message
if (messageSender.equals(myUserName) && messageReceiver.equals(sender)) {
//If that is an image message
if(messages.startsWith("gago+")) {
getImagesHistory(convertDate, messages, "0");
} else {
//If that is a text message
getMessagesHistory(convertDate, messages, "0", null);
}
}
//If other user sends me a message
if (messageReceiver.equals(myUserName) && messageSender.equals(sender)) {
//If that is an image message
if(messages.startsWith("gago+")) {
getImagesHistory(convertDate, messages, "1");
} else {
//If that is a text message
getMessagesHistory(convertDate, messages, "1", null);
}
}
}
} else {
Toast.makeText(context, "Something went wrong", Toast.LENGTH_SHORT).show();
}
}
@Override
public void onFailure(Call<MessagesHistory[]> call, Throwable t) {
Toast.makeText(context, "An error occurred", Toast.LENGTH_SHORT).show();
}
});
}
//Request an image when I already have the image name
public void getImagesHistory(final Date convertDate, final String messages, final String id) {
String cutMessage = messages.substring(5, messages.length());
Call<ResponseBody> getChatImageCall = apiClient.getImages(cutMessage, CHAT_IMAGE_TYPE);
getChatImageCall.enqueue(new Callback<ResponseBody>() {
@Override
public void onResponse(Call<ResponseBody> call, final Response<ResponseBody> response) {
if (response.isSuccessful()) {
try {
getMessagesHistory(convertDate, messages, id, response.body().bytes());
} catch (IOException e) {
e.printStackTrace();
}
} else {
Toast.makeText(getActivity(), "Something went wrong", Toast.LENGTH_SHORT).show();
}
}
@Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
Toast.makeText(getActivity(), "An error occurred", Toast.LENGTH_SHORT).show();
}
});
}
//Display the message we got
public void getMessagesHistory(final Date startDate, final String historyMessages, final String id, byte[] imgBytes) {
ArrayList<Message> messages = new ArrayList<>();
//I'm getting my images with an array of byte
//So if the image bytes are not null
if(imgBytes != null) {
message = MessagesFixtures.getImageBytesMessage(imgBytes, id);
} else {
//This is a text
message = MessagesFixtures.getTextMessage(historyMessages, id);
}
message.setCreatedAt(startDate);
messages.add(message);
messagesAdapter.addToEnd(messages, false);
}
}
在我的代码messagesAdapter.addToEnd(messages, false);
中,将消息数组和集合带到了 recyclerView。在我的情况下recyclerView
,MessageList
适配器是MessagesListAdapter
. 所以我想我需要退出 messagesAdapter.addToEnd(messages, false);
fromgetMessagesHistory
函数并添加到另一个地方。但我不能这样做,因为getMessagesHistory
在构造函数中有一些参数,而最后一个参数byte[] imgBytes
在某些情况下为空。当我从服务器收到短信时,我将其设置为空,否则我将我的数组字节设置在那里。所以请帮助我怎么做这部分?
解决方案
推荐阅读
- javascript - 如何使用 JavaScript 加载大型本地文件?
- ios - 如何将带有参数的 iOS URl Schema 共享为我可以单击的链接,而不仅仅是字符串
- c# - UWP ListView DataTemplate 绑定
- angular - Angular Openvidu 作为子组件
- ruby-on-rails - 为什么我会收到此错误:ActiveRecord::AssociationTypeMismatch?
- c - C中的套接字:关闭套接字的正确方法
- git - 是否可以用“统一”补丁替换来自 git 中不同提交的文件?
- android - 如何为 android 创建一个电视调谐器库?
- eloquent - 如何在一对多关系中从多个表中获取和显示最后一行值
- kotlin - Kotlin:为什么在这个例子中 Sequence 的性能更高?