Pixel Perfect Posted January 22, 2013 Share Posted January 22, 2013 This is proving really good timing as I'm about to do a complete engine re-write (for various reasons) and I wanted to look at putting the foundations in for multi-player. Quote Intel Core i5 2.66 GHz, Asus P7P55D, 8Gb DDR3 RAM, GTX460 1Gb DDR5, Windows 7 (x64), LE Editor, GMax, 3DWS, UU3D Pro, Texture Maker Pro, Shader Map Pro. Development language: C/C++ Link to comment Share on other sites More sharing options...
Rick Posted January 22, 2013 Share Posted January 22, 2013 Just some code I've used/read before. If you use game states and state manager this can help simplify things. This is what I use myself. I've done this from memory so it's just to get the idea behind it and not 100% how mine looks. void StateManager::NetworkUpdate() { for(p=client->Receive(); p; client->DeallocatePacket(p), p=client->Receive()) { // this reads the first byte of the packet and is the enum values like ID_REQUEST_LOGIN packetIdentifier = GetPacketIdentifier(p); // get the bitstream to read the data and ignore the message type so we can just read the game data right away when inside // our function RakNet::BitStream reader(p->data, p->length, false); reader->IgnoreBytes(sizeof(MessageID)); // validate our current state has registered/subscribed to this network message if(_currentState->IsNetworkMessageRegistered(packetIdentifier)) { // if it has, fire the message off _currentState->FireNetworkEvent(packetIdentifier, p, reader) } } } // inside base State class map<MessageID, Event2<Packet*, BitStream&>> _networkMessages; bool State::IsNetworkMessageRegistered(MessageID msg) { if(_networkMessages.find(msg) != _networkMessages.end()) return true; return false; } void State::FireNetworkEvent(MessageID msg, Packet* p, BitStream& reader) { // this will fire the function that was bound to the message _networkMessages[msg].Raise(p, reader); } void GameplayState::OnEnter() { // this replaces the need for a big ugly switch state and is how you link network messages to member functions _networkMessages[iD_RESPONSE_LOGIN].Bind(this, &GameplayState::OnResponseLogin); } void GameplayState::OnResponseLogin(Packet* p, BitStream& reader) { RakString status; RakString reason; reader.Read(status); if(status == "failure") { reason = reader.Read(reason); printf("Failed to login: %s", reason.C_Str()); } } This is the way I do things. A slight modification to this could be to make classes for each message type and a factory create said type using the message id. void Gameplay::OnResponseLogin(LoginMessage& msg) { if(msg.Status == "failure") printf("Failed to login: %s", msg.Reason); } This is "cleaner", but it adds more overhead to make work. With this you need a class for every message id and you'll end up with hundreds of small classes. It also requires some casting being done to the message class type. The nice thing about this is that inside the network function you don't have to worry about reading the data as that's been done for you in the message class itself. However, you'd still have to do that reading in the class, but if working in a team project it can lead to nice separation of duties. These are just things I've done/learned from others and is no way the only way to do things, but just thought I'd share my experiences. 1 Quote Link to comment Share on other sites More sharing options...
Pixel Perfect Posted January 22, 2013 Share Posted January 22, 2013 These are just things I've done/learned from others and is no way the only way to do things, but just thought I'd share my experiences. Thanks for sharing Rick, this is all great background information. I'll read and digest Quote Intel Core i5 2.66 GHz, Asus P7P55D, 8Gb DDR3 RAM, GTX460 1Gb DDR5, Windows 7 (x64), LE Editor, GMax, 3DWS, UU3D Pro, Texture Maker Pro, Shader Map Pro. Development language: C/C++ Link to comment Share on other sites More sharing options...
Guest Red Ocktober Posted January 22, 2013 Share Posted January 22, 2013 The player on the server is very necessary, but it just doesn't require the visuals. unless your server is also connected as one of the players... ie, not a dedicated server... --Mike 1 Quote Link to comment Share on other sites More sharing options...
Canardia Posted January 22, 2013 Share Posted January 22, 2013 I still think that network messages should be transferred in a low priority thread, like only once every 60 seconds. The rest can be done with AI prediction. Quote ■ Ryzen 9 ■ RX 6800M ■ 16GB ■ XF8 ■ Windows 11 ■ ■ Ultra ■ LE 2.5 ■ 3DWS 5.6 ■ Reaper ■ C/C++ ■ C# ■ Fortran 2008 ■ Story ■ ■ Homepage: https://canardia.com ■ Link to comment Share on other sites More sharing options...
ChrisMAN Posted January 22, 2013 Share Posted January 22, 2013 I still think that network messages should be transferred in a low priority thread, like only once every 60 seconds. The rest can be done with AI prediction. Certainly the majority of actions can be treated this way. Quote Link to comment Share on other sites More sharing options...
Rick Posted January 22, 2013 Share Posted January 22, 2013 I still think that network messages should be transferred in a low priority thread, like only once every 60 seconds. The rest can be done with AI prediction. So you want to only send some network traffice once a min? Think if it took a minute before others see your chat messages. Or a minute to tell you that the other player actually picked up this item that you thought you picked up because you both got there at at the same time. As a player I'd be pretty pissed to think I have an item for 60 seconds before the game takes it back away from me because it finally realized I didn't really get there first to get it. The truth is almost nothing you do in a networked game will ever be spaced out that long. Prediction only masks the reality for a very short time to help the illusion. Letting corrections only happen every 60 seconds would cause all sorts of visible problems in games. I could do all sorts of cheats on the client within that 1 minute time window. 1 min is a very long time in the world of networking considering things generally happen around 100ms or so. The 2 main things you are thinking about with online games: 1) Create the illusion of instant 2) Stop the cheating These 2 things are the most important. If your game fails on either of these 2 the game will die quickly. Nobody likes lag and a sluggish game, and when your game is filled with cheaters nobody likes that either. Quote Link to comment Share on other sites More sharing options...
ChrisMAN Posted January 22, 2013 Share Posted January 22, 2013 A minute is a long time but the concept still holds. Quote Link to comment Share on other sites More sharing options...
Road Kill Kenny Posted January 23, 2013 Share Posted January 23, 2013 I still think that network messages should be transferred in a low priority thread, like only once every 60 seconds. The rest can be done with AI prediction. 60 seconds is way too long. AI prediction cannot even come close to predicting that length ahead of time. Quote STS - Scarlet Thread Studios AKA: Engineer Ken Fact: Game Development is hard... very bloody hard.. If you are not prepared to accept that.. Please give up now! Link to comment Share on other sites More sharing options...
ChrisMAN Posted January 23, 2013 Share Posted January 23, 2013 60 seconds is way too long. AI prediction cannot even come close to predicting that length ahead of time. The black walls in diablo ii took about a minute Quote Link to comment Share on other sites More sharing options...
gamecreator Posted January 23, 2013 Share Posted January 23, 2013 I think Mika was joking and you guys are running with it. Quote Link to comment Share on other sites More sharing options...
Road Kill Kenny Posted January 23, 2013 Share Posted January 23, 2013 I think Mika was joking and you guys are running with it. Well it's Mika we're talking about.. who knows? I wouldn't be surprised either way. Quote STS - Scarlet Thread Studios AKA: Engineer Ken Fact: Game Development is hard... very bloody hard.. If you are not prepared to accept that.. Please give up now! Link to comment Share on other sites More sharing options...
Pixel Perfect Posted January 23, 2013 Share Posted January 23, 2013 I'd much prefer factual advice from real experience over supposition (I have Mika on constant ignore due to his past history of this). It's a lot more helpful to people starting off down this route who may be hoping to get some good pointers from this thread. Quote Intel Core i5 2.66 GHz, Asus P7P55D, 8Gb DDR3 RAM, GTX460 1Gb DDR5, Windows 7 (x64), LE Editor, GMax, 3DWS, UU3D Pro, Texture Maker Pro, Shader Map Pro. Development language: C/C++ Link to comment Share on other sites More sharing options...
Canardia Posted January 23, 2013 Share Posted January 23, 2013 So you want to only send some network traffice once a min? Think if it took a minute before others see your chat messages. Or a minute to tell you that the other player actually picked up this item that you thought you picked up because you both got there at at the You can do it the other way around: Let the player request an item to pick up, and after some time the server will tell the player if the pickup was succesful. It doesn't have to appear as long waiting time, but you can have a game story why it takes sometimes longer to get an item, for example the item must be carefully removed to avoid it getting damaged. Kinda when you remove some jewel from a statue, it takes also time. Quote ■ Ryzen 9 ■ RX 6800M ■ 16GB ■ XF8 ■ Windows 11 ■ ■ Ultra ■ LE 2.5 ■ 3DWS 5.6 ■ Reaper ■ C/C++ ■ C# ■ Fortran 2008 ■ Story ■ ■ Homepage: https://canardia.com ■ Link to comment Share on other sites More sharing options...
Rick Posted January 23, 2013 Share Posted January 23, 2013 You can do it the other way around: Let the player request an item to pick up, and after some time the server will tell the player if the pickup was succesful. It doesn't have to appear as long waiting time, but you can have a game story why it takes sometimes longer to get an item, for example the item must be carefully removed to avoid it getting damaged. Kinda when you remove some jewel from a statue, it takes also time. Come on man lol Quote Link to comment Share on other sites More sharing options...
Canardia Posted January 23, 2013 Share Posted January 23, 2013 That's the only way you can host a MMO on your own server with 1MBit/s connection. Movement can be point and click style, and fights can be easily predicted based on the equipment and enemy. Quote ■ Ryzen 9 ■ RX 6800M ■ 16GB ■ XF8 ■ Windows 11 ■ ■ Ultra ■ LE 2.5 ■ 3DWS 5.6 ■ Reaper ■ C/C++ ■ C# ■ Fortran 2008 ■ Story ■ ■ Homepage: https://canardia.com ■ Link to comment Share on other sites More sharing options...
ChrisMAN Posted January 23, 2013 Share Posted January 23, 2013 At that scale a thread based concurrency would choke. Getting an evented io lib is really important https://github.com/joyent/libuv Quote Link to comment Share on other sites More sharing options...
Pixel Perfect Posted January 23, 2013 Share Posted January 23, 2013 You guys just crack me up! Not one published game made with LE2 yet * and you're discussing what's required for an MMO * I don't really count Hoodwink; as the only part of the engine it used was the renderer ... although full kudos to NA. I'm off to start reading through the RAKNET documentation. Thanks to all who provided practical advice and provided pointers to key areas I'll need to familiarize myself with. I hope you'll provide some feedback as you develop you're multi-player engine DigitalHax and I'll try and do likewise. I'll be taking a look at your code too Scarlet, thanks for releasing your tutorials I'm sure they will be really helpful. Quote Intel Core i5 2.66 GHz, Asus P7P55D, 8Gb DDR3 RAM, GTX460 1Gb DDR5, Windows 7 (x64), LE Editor, GMax, 3DWS, UU3D Pro, Texture Maker Pro, Shader Map Pro. Development language: C/C++ Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.