From fbef63822c9bcc3b2bb26988cd14a6767eba5fd8 Mon Sep 17 00:00:00 2001 From: Peter Nelson Date: Sun, 11 Apr 2021 23:02:59 +0100 Subject: Codechange: Use std::deque for chat history instead of fixed array --- src/network/network_chat_gui.cpp | 60 +++++++++++----------------------------- 1 file changed, 16 insertions(+), 44 deletions(-) diff --git a/src/network/network_chat_gui.cpp b/src/network/network_chat_gui.cpp index 80a0b7869..a1157e261 100644 --- a/src/network/network_chat_gui.cpp +++ b/src/network/network_chat_gui.cpp @@ -8,6 +8,7 @@ /** @file network_chat_gui.cpp GUI for handling chat messages. */ #include /* va_list */ +#include #include "../stdafx.h" #include "../strings_func.h" @@ -44,7 +45,7 @@ struct ChatMessage { }; /* used for chat window */ -static ChatMessage *_chatmsg_list = nullptr; ///< The actual chat message list. +static std::deque _chatmsg_list; ///< The actual chat message list. static bool _chatmessage_dirty = false; ///< Does the chat message need repainting? static bool _chatmessage_visible = false; ///< Is a chat message visible. static bool _chat_tab_completion_active; ///< Whether tab completion is active. @@ -57,20 +58,6 @@ static uint MAX_CHAT_MESSAGES = 0; ///< The limit of chat messages to sho static PointDimension _chatmsg_box; static uint8 *_chatmessage_backup = nullptr; ///< Backup in case text is moved. -/** - * Count the chat messages. - * @return The number of chat messages. - */ -static inline uint GetChatMessageCount() -{ - uint i = 0; - for (; i < MAX_CHAT_MESSAGES; i++) { - if (_chatmsg_list[i].message[0] == '\0') break; - } - - return i; -} - /** * Add a text message to the 'chat window' to be shown * @param colour The colour this message is to be shown in @@ -88,13 +75,11 @@ void CDECL NetworkAddChatMessage(TextColour colour, uint duration, const char *m Utf8TrimString(buf, DRAW_STRING_BUFFER); - uint msg_count = GetChatMessageCount(); - if (MAX_CHAT_MESSAGES == msg_count) { - memmove(&_chatmsg_list[0], &_chatmsg_list[1], sizeof(_chatmsg_list[0]) * (msg_count - 1)); - msg_count = MAX_CHAT_MESSAGES - 1; + if (_chatmsg_list.size() == MAX_CHAT_MESSAGES) { + _chatmsg_list.pop_back(); } - ChatMessage *cmsg = &_chatmsg_list[msg_count++]; + ChatMessage *cmsg = &_chatmsg_list.emplace_front(); strecpy(cmsg->message, buf, lastof(cmsg->message)); cmsg->colour = (colour & TC_IS_PALETTE_COLOUR) ? colour : TC_WHITE; cmsg->remove_time = std::chrono::steady_clock::now() + std::chrono::seconds(duration); @@ -115,15 +100,11 @@ void NetworkInitChatMessage() { MAX_CHAT_MESSAGES = _settings_client.gui.network_chat_box_height; - _chatmsg_list = ReallocT(_chatmsg_list, _settings_client.gui.network_chat_box_height); + _chatmsg_list.clear(); _chatmsg_box.x = 10; _chatmsg_box.width = _settings_client.gui.network_chat_box_width_pct * _screen.width / 100; NetworkReInitChatBoxSize(); _chatmessage_visible = false; - - for (uint i = 0; i < MAX_CHAT_MESSAGES; i++) { - _chatmsg_list[i].message[0] = '\0'; - } } /** Hide the chatbox */ @@ -175,21 +156,13 @@ void NetworkUndrawChatMessage() /** Check if a message is expired. */ void NetworkChatMessageLoop() { - for (uint i = 0; i < MAX_CHAT_MESSAGES; i++) { - ChatMessage *cmsg = &_chatmsg_list[i]; - if (cmsg->message[0] == '\0') continue; - + for (auto it = _chatmsg_list.begin(); it != _chatmsg_list.end();) { /* Message has expired, remove from the list */ - if (std::chrono::steady_clock::now() > cmsg->remove_time) { - /* Move the remaining messages over the current message */ - if (i != MAX_CHAT_MESSAGES - 1) memmove(cmsg, cmsg + 1, sizeof(*cmsg) * (MAX_CHAT_MESSAGES - i - 1)); - - /* Mark the last item as empty */ - _chatmsg_list[MAX_CHAT_MESSAGES - 1].message[0] = '\0'; + if (std::chrono::steady_clock::now() > it->remove_time) { + it = _chatmsg_list.erase(it); _chatmessage_dirty = true; - - /* Go one item back, because we moved the array 1 to the left */ - i--; + } else { + it++; } } } @@ -206,8 +179,7 @@ void NetworkDrawChatMessage() if (_iconsole_mode == ICONSOLE_FULL) return; /* Check if we have anything to draw at all */ - uint count = GetChatMessageCount(); - if (count == 0) return; + if (_chatmsg_list.size() == 0) return; int x = _chatmsg_box.x; int y = _screen.height - _chatmsg_box.y - _chatmsg_box.height; @@ -230,8 +202,8 @@ void NetworkDrawChatMessage() _cur_dpi = &_screen; // switch to _screen painting int string_height = 0; - for (uint i = 0; i < count; i++) { - SetDParamStr(0, _chatmsg_list[i].message); + for (auto &cmsg : _chatmsg_list) { + SetDParamStr(0, cmsg.message); string_height += GetStringLineCount(STR_JUST_RAW_STRING, width - 1) * FONT_HEIGHT_NORMAL + NETWORK_CHAT_LINE_SPACING; } @@ -247,8 +219,8 @@ void NetworkDrawChatMessage() /* Paint the chat messages starting with the lowest at the bottom */ int ypos = bottom - 2; - for (int i = count - 1; i >= 0; i--) { - ypos = DrawStringMultiLine(_chatmsg_box.x + 3, _chatmsg_box.x + _chatmsg_box.width - 1, top, ypos, _chatmsg_list[i].message, _chatmsg_list[i].colour, SA_LEFT | SA_BOTTOM | SA_FORCE) - NETWORK_CHAT_LINE_SPACING; + for (auto &cmsg : _chatmsg_list) { + ypos = DrawStringMultiLine(_chatmsg_box.x + 3, _chatmsg_box.x + _chatmsg_box.width - 1, top, ypos, cmsg.message, cmsg.colour, SA_LEFT | SA_BOTTOM | SA_FORCE) - NETWORK_CHAT_LINE_SPACING; if (ypos < top) break; } -- cgit v1.2.3-54-g00ecf