Skip to content

Commit 72eabce

Browse files
committed
- Added support for "host wants to start"
- Improved "Host wants to start" by automatically readying everyone up 30 seconds later
1 parent 9f4cc4e commit 72eabce

7 files changed

Lines changed: 157 additions & 15 deletions

File tree

GeneralsMD/Code/GameEngine/Include/GameNetwork/GeneralsOnline/OnlineServices_Init.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -208,6 +208,7 @@ class NGMP_OnlineServicesManager
208208

209209
std::string& GetMOTD() { return m_strMOTD; }
210210

211+
211212
private:
212213
//EOS_HPlatform m_EOSPlatformHandle = nullptr;
213214

GeneralsMD/Code/GameEngine/Include/GameNetwork/GeneralsOnline/OnlineServices_LobbyInterface.h

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,8 @@ class NGMP_OnlineServices_LobbyInterface
7676
void UpdateCurrentLobby_MyStartPos(int side);
7777
void UpdateCurrentLobby_MyTeam(int side);
7878

79+
void UpdateCurrentLobby_ForceReady();
80+
7981
void SetLobbyListDirty()
8082
{
8183
m_bLobbyListDirty = true;
@@ -110,6 +112,7 @@ class NGMP_OnlineServices_LobbyInterface
110112
AsciiString GetCurrentLobbyMapPath();
111113

112114
void SendChatMessageToCurrentLobby(UnicodeString& strChatMsgUnicode);
115+
void SendAnnouncementMessageToCurrentLobby(UnicodeString& strAnnouncementMsgUnicode, bool bShowToHost);
113116

114117
void InvokeCreateLobbyCallback(bool bSuccess)
115118
{
@@ -164,6 +167,20 @@ class NGMP_OnlineServices_LobbyInterface
164167
//UpdateRoomDataCache();
165168
m_lastForceRefresh = currTime;
166169
}
170+
171+
// do we have a pending start?
172+
if (IsHost())
173+
{
174+
if (m_timeStartAutoReadyCountdown > 0)
175+
{
176+
if ((currTime - m_timeStartAutoReadyCountdown) > 30000)
177+
{
178+
// TODO_NGMP: Don't do this clientside...
179+
UpdateCurrentLobby_ForceReady();
180+
ClearAutoReadyCountdown();
181+
}
182+
}
183+
}
167184
}
168185
}
169186

@@ -277,6 +294,21 @@ class NGMP_OnlineServices_LobbyInterface
277294
bool m_bHostMigrated = false;
278295
bool m_bPendingHostHasLeft = false;
279296

297+
void StartAutoReadyCountdown()
298+
{
299+
m_timeStartAutoReadyCountdown = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::utc_clock::now().time_since_epoch()).count();
300+
}
301+
302+
void ClearAutoReadyCountdown()
303+
{
304+
m_timeStartAutoReadyCountdown = -1;
305+
}
306+
307+
bool HasAutoReadyCountdown()
308+
{
309+
return m_timeStartAutoReadyCountdown != -1;
310+
}
311+
280312
private:
281313
std::vector<std::function<void(bool)>> m_vecCreateLobby_PendingCallbacks = std::vector<std::function<void(bool)>>();
282314

@@ -290,4 +322,6 @@ class NGMP_OnlineServices_LobbyInterface
290322
NGMPGame* m_pGameInst = nullptr;
291323

292324
bool m_bLobbyListDirty = false;
325+
326+
int64_t m_timeStartAutoReadyCountdown = -1;
293327
};

GeneralsMD/Code/GameEngine/Include/GameNetwork/GeneralsOnline/Packets/NetworkPacket_NetRoom_ChatMessage.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,14 +5,18 @@
55
class NetRoom_ChatMessagePacket : public NetworkPacket
66
{
77
public:
8-
NetRoom_ChatMessagePacket(AsciiString& strMessage);
8+
NetRoom_ChatMessagePacket(AsciiString& strMessage, bool bIsAnnouncement, bool bShowAnnounceToHost);
99

1010
NetRoom_ChatMessagePacket(CBitStream& bitstream);
1111

1212
virtual CBitStream* Serialize() override;
1313

1414
const std::string& GetMsg() const { return m_strMessage; }
15+
bool IsAnnouncement() const { return m_bIsAnnouncement; }
16+
bool ShowAnnouncementToHost() const { return m_bShowAnnounceToHost; }
1517

1618
private:
1719
std::string m_strMessage = "";
20+
bool m_bIsAnnouncement = false;
21+
bool m_bShowAnnounceToHost = false;
1822
};

GeneralsMD/Code/GameEngine/Source/GameClient/GUI/GUICallbacks/Menus/WOLGameSetupMenu.cpp

Lines changed: 28 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -890,6 +890,9 @@ static void StartPressed(void)
890890

891891
if(isReady)
892892
{
893+
// reset autostart just incase
894+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->ClearAutoReadyCountdown();
895+
893896
//PeerRequest req;
894897
//req.peerRequestType = PeerRequest::PEERREQUEST_STARTGAME;
895898
//TheGameSpyPeerMessageQueue->addRequest(req);
@@ -913,18 +916,35 @@ static void StartPressed(void)
913916
}
914917
else if (allHaveMap)
915918
{
916-
// TODO_NGMP: today
917-
GadgetListBoxAddEntryText(listboxGameSetupChat, TheGameText->fetch("GUI:NotifiedStartIntent"), GameSpyColor[GSCOLOR_DEFAULT], -1, -1);
918-
PeerRequest req;
919-
req.peerRequestType = PeerRequest::PEERREQUEST_UTMROOM;
920-
req.UTM.isStagingRoom = TRUE;
921-
req.id = "HWS/";
922-
req.options = "true";
923-
TheGameSpyPeerMessageQueue->addRequest(req);
919+
// send HWS chat message
920+
921+
if (!NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->HasAutoReadyCountdown())
922+
{
923+
// local msg
924+
GadgetListBoxAddEntryText(listboxGameSetupChat, TheGameText->fetch("GUI:NotifiedStartIntent"), GameSpyColor[GSCOLOR_DEFAULT], -1, -1);
925+
926+
// remote msg
927+
UnicodeString strInform = TheGameText->fetch("GUI:HostWantsToStart");
928+
UnicodeString strInform2 = UnicodeString(L"All players will be forced to ready up in 30 seconds");
929+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->SendAnnouncementMessageToCurrentLobby(strInform, false);
930+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->SendAnnouncementMessageToCurrentLobby(strInform2, true);
931+
932+
// TODO_NGMP: Add the reverse too, if everyone is ready but the host wont start... just start it in X seconds
933+
934+
// start a countdown to auto start
935+
// TODO_NGMP: Don't have this client driven...
936+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->StartAutoReadyCountdown();
937+
}
938+
else
939+
{
940+
UnicodeString strInform = UnicodeString(L"You have already informed players you want to start. A countdown has begun after which they will be marked as ready.");
941+
GadgetListBoxAddEntryText(listboxGameSetupChat, strInform, GameSpyColor[GSCOLOR_DEFAULT], -1, -1);
942+
}
924943
}
925944

926945
}//void StartPressed(void)
927946

947+
928948
//-------------------------------------------------------------------------------------------------
929949
/** Update options on screen */
930950
//-------------------------------------------------------------------------------------------------

GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/NetworkMesh.cpp

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -422,6 +422,9 @@ void NetworkMesh::Tick()
422422
// TODO_NGMP: Support longer msgs
423423
NetworkLog("[NGMP]: Received chat message of len %d: %s from %d", chatPacket.GetMsg().length(), chatPacket.GetMsg().c_str(), event.peer->incomingPeerID);
424424

425+
// get host ID
426+
int64_t localID = NGMP_OnlineServicesManager::GetInstance()->GetAuthInterface()->GetUserID();
427+
425428
// find user
426429
for (auto& connectionData : m_mapConnections)
427430
{
@@ -433,9 +436,24 @@ void NetworkMesh::Tick()
433436
{
434437
if (lobbyUser.user_id == connectionData.first)
435438
{
436-
UnicodeString str;
437-
str.format(L"%hs: %hs", lobbyUser.display_name.c_str(), chatPacket.GetMsg().c_str());
438-
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->m_OnChatCallback(str);
439+
// if its an announce, dont show it to the sender, they did something locally instead
440+
if (chatPacket.IsAnnouncement())
441+
{
442+
// if its not us, show the message
443+
if (chatPacket.ShowAnnouncementToHost() || lobbyUser.user_id != localID)
444+
{
445+
UnicodeString str;
446+
str.format(L"%hs", chatPacket.GetMsg().c_str());
447+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->m_OnChatCallback(str);
448+
}
449+
}
450+
else
451+
{
452+
UnicodeString str;
453+
str.format(L"%hs: %hs", lobbyUser.display_name.c_str(), chatPacket.GetMsg().c_str());
454+
NGMP_OnlineServicesManager::GetInstance()->GetLobbyInterface()->m_OnChatCallback(str);
455+
}
456+
439457

440458
break;
441459
}

GeneralsMD/Code/GameEngine/Source/GameNetwork/GeneralsOnline/OnlineServices_LobbyInterface.cpp

Lines changed: 61 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,11 +52,15 @@ enum class ELobbyUpdateField
5252
MY_START_POS = 3,
5353
MY_TEAM = 4,
5454
LOBBY_STARTING_CASH = 5,
55-
LOBBY_LIMIT_SUPERWEAPONS = 6
55+
LOBBY_LIMIT_SUPERWEAPONS = 6,
56+
HOST_ACTION_FORCE_START = 7
5657
};
5758

5859
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_Map(AsciiString strMap, AsciiString strMapPath, int newMaxPlayers)
5960
{
61+
// reset autostart if host changes anything (because ready flag will reset too)
62+
ClearAutoReadyCountdown();
63+
6064
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
6165
std::map<std::string, std::string> mapHeaders;
6266

@@ -76,6 +80,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_Map(AsciiString strM
7680

7781
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_LimitSuperweapons(bool bLimitSuperweapons)
7882
{
83+
// reset autostart if host changes anything (because ready flag will reset too)
84+
ClearAutoReadyCountdown();
85+
7986
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
8087
std::map<std::string, std::string> mapHeaders;
8188

@@ -93,6 +100,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_LimitSuperweapons(bo
93100

94101
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_StartingCash(UnsignedInt startingCashValue)
95102
{
103+
// reset autostart if host changes anything (because ready flag will reset too)
104+
ClearAutoReadyCountdown();
105+
96106
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
97107
std::map<std::string, std::string> mapHeaders;
98108

@@ -110,6 +120,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_StartingCash(Unsigne
110120

111121
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MySide(int side, int updatedStartPos)
112122
{
123+
// reset autostart if host changes anything (because ready flag will reset too). This occurs on client too, but nothing happens for them
124+
ClearAutoReadyCountdown();
125+
113126
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
114127
std::map<std::string, std::string> mapHeaders;
115128

@@ -128,6 +141,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MySide(int side, int
128141

129142
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyColor(int color)
130143
{
144+
// reset autostart if host changes anything (because ready flag will reset too). This occurs on client too, but nothing happens for them
145+
ClearAutoReadyCountdown();
146+
131147
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
132148
std::map<std::string, std::string> mapHeaders;
133149

@@ -145,6 +161,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyColor(int color)
145161

146162
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyStartPos(int startpos)
147163
{
164+
// reset autostart if host changes anything (because ready flag will reset too). This occurs on client too, but nothing happens for them
165+
ClearAutoReadyCountdown();
166+
148167
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
149168
std::map<std::string, std::string> mapHeaders;
150169

@@ -162,6 +181,9 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyStartPos(int start
162181

163182
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyTeam(int team)
164183
{
184+
// reset autostart if host changes anything (because ready flag will reset too). This occurs on client too, but nothing happens for them
185+
ClearAutoReadyCountdown();
186+
165187
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
166188
std::map<std::string, std::string> mapHeaders;
167189

@@ -177,14 +199,31 @@ void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_MyTeam(int team)
177199
});
178200
}
179201

202+
void NGMP_OnlineServices_LobbyInterface::UpdateCurrentLobby_ForceReady()
203+
{
204+
std::string strURI = std::format("{}/{}", NGMP_OnlineServicesManager::GetAPIEndpoint("Lobby", true), m_CurrentLobby.lobbyID);
205+
std::map<std::string, std::string> mapHeaders;
206+
207+
nlohmann::json j;
208+
j["field"] = ELobbyUpdateField::HOST_ACTION_FORCE_START;
209+
std::string strPostData = j.dump();
210+
211+
// convert
212+
NGMP_OnlineServicesManager::GetInstance()->GetHTTPManager()->SendPOSTRequest(strURI.c_str(), EIPProtocolVersion::DONT_CARE, mapHeaders, strPostData.c_str(), [=](bool bSuccess, int statusCode, std::string strBody)
213+
{
214+
UnicodeString msg = UnicodeString(L"All players have been forced to ready up.");
215+
SendAnnouncementMessageToCurrentLobby(msg, true);
216+
});
217+
}
218+
180219
void NGMP_OnlineServices_LobbyInterface::SendChatMessageToCurrentLobby(UnicodeString& strChatMsgUnicode)
181220
{
182221
// TODO_NGMP: Custom
183222
// TODO_NGMP: Support unicode again
184223
AsciiString strChatMsg;
185224
strChatMsg.translate(strChatMsgUnicode);
186225

187-
NetRoom_ChatMessagePacket chatPacket(strChatMsg);
226+
NetRoom_ChatMessagePacket chatPacket(strChatMsg, false, false);
188227

189228
// TODO_NGMP: Move to uint64 for user id
190229
std::vector<int64_t> vecUsersToSend;
@@ -199,6 +238,21 @@ void NGMP_OnlineServices_LobbyInterface::SendChatMessageToCurrentLobby(UnicodeSt
199238
}
200239
}
201240

241+
// TODO_NGMP: Just send a separate packet for each announce, more efficient and less hacky
242+
void NGMP_OnlineServices_LobbyInterface::SendAnnouncementMessageToCurrentLobby(UnicodeString& strAnnouncementMsgUnicode, bool bShowToHost)
243+
{
244+
AsciiString strChatMsg;
245+
strChatMsg.translate(strAnnouncementMsgUnicode);
246+
247+
NetRoom_ChatMessagePacket chatPacket(strChatMsg, true, bShowToHost);
248+
249+
std::vector<int64_t> vecUsersToSend;
250+
if (m_pLobbyMesh != nullptr)
251+
{
252+
m_pLobbyMesh->SendToMesh(chatPacket, vecUsersToSend);
253+
}
254+
}
255+
202256
NGMP_OnlineServices_LobbyInterface::NGMP_OnlineServices_LobbyInterface()
203257
{
204258
/*
@@ -825,6 +879,8 @@ void NGMP_OnlineServices_LobbyInterface::JoinLobby(int index)
825879

826880
void NGMP_OnlineServices_LobbyInterface::LeaveCurrentLobby()
827881
{
882+
m_timeStartAutoReadyCountdown = -1;
883+
828884
// kill mesh
829885
if (m_pLobbyMesh != nullptr)
830886
{
@@ -1180,6 +1236,9 @@ void NGMP_OnlineServices_LobbyInterface::CreateLobby(UnicodeString strLobbyName,
11801236

11811237
void NGMP_OnlineServices_LobbyInterface::OnJoinedOrCreatedLobby(bool bAlreadyUpdatedDetails)
11821238
{
1239+
// reset timer
1240+
m_timeStartAutoReadyCountdown = -1;
1241+
11831242
// TODO_NGMP: We need this on create, but this is a double call on join because we already got this info
11841243
// must be done in a callback, this is an async function
11851244
if (!bAlreadyUpdatedDetails)
Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,25 @@
11
#include "GameNetwork/GeneralsOnline/NetworkPacket.h"
22
#include "GameNetwork/GeneralsOnline/Packets/NetworkPacket_NetRoom_ChatMessage.h"
33

4-
NetRoom_ChatMessagePacket::NetRoom_ChatMessagePacket(AsciiString& strMessage) : NetworkPacket(EPacketReliability::PACKET_RELIABILITY_RELIABLE_ORDERED)
4+
NetRoom_ChatMessagePacket::NetRoom_ChatMessagePacket(AsciiString& strMessage, bool bIsAnnouncement, bool bShowAnnounceToHost) : NetworkPacket(EPacketReliability::PACKET_RELIABILITY_RELIABLE_ORDERED)
55
{
66
m_strMessage = strMessage.str();
7+
m_bIsAnnouncement = bIsAnnouncement;
8+
m_bShowAnnounceToHost = bShowAnnounceToHost;
79
}
810

911
NetRoom_ChatMessagePacket::NetRoom_ChatMessagePacket(CBitStream& bitstream) : NetworkPacket(bitstream)
1012
{
1113
m_strMessage = bitstream.ReadString();
14+
m_bIsAnnouncement = bitstream.Read<bool>();
15+
m_bShowAnnounceToHost = bitstream.Read<bool>();
1216
}
1317

1418
CBitStream* NetRoom_ChatMessagePacket::Serialize()
1519
{
1620
CBitStream* pBitstream = new CBitStream(EPacketID::PACKET_ID_NET_ROOM_CHAT_MSG);
1721
pBitstream->WriteString(m_strMessage.c_str());
22+
pBitstream->Write<bool>(m_bIsAnnouncement);
23+
pBitstream->Write<bool>(m_bShowAnnounceToHost);
1824
return pBitstream;
1925
}

0 commit comments

Comments
 (0)