Advertisement

Need help on designing an RTS AI system

Started by June 07, 2011 08:14 AM
0 comments, last by ApochPiQ 13 years, 5 months ago
Hi everyone!

I've created an RTS. It has almost no content at this point, but the technical parts of it is fairly stable. It's meant to be an Age of Empires 2 clone/remake and shares many of the basic gameplay elements. Most low level stuff is implemented, such as buildings, resource gathering, attacking, pathfinding, exploration/fog of war etc. The GUI is somewhat lacking, but complete enough for now. The game is currently playable in multiplayer with 2-4 players, but I want to add AI players as soon as possible. I want to create a system that allows users to create their own AI implementations using C# or Python, but I'm not sure how to design the AI API. I want it to be simple to use and understand, yet efficient so that it doesn't stall the game. I also want to disallow cheating by simply not making it possible. I should probably mention that I'm doing this in C# / Xna.

My engine is split into 4 layers: The simulation layer, the network layer, the controller layer and the GUI layer. The simulation contains all the low level game logic such as units, terrain, actions, buildings and what not. The simulation runs at a fixed framerate and should always be 100% synchronized across all players in a multiplayer game. This is why the simulation can only be affected by what I call interrupts. Interrupts are synchronized over the network and therefore the game stays synchronized. Ofcourse I have methods to make sure all interrupts arrive at all players in the same order and that no player can miss an interrupt so it should be safe. The simulation doesn't really know about anything above itself.

The network layer just makes sure all interrupts reaches all players. The next layer is the controller layer. Here there can be a number of controllers, which are updated for each frame. For the player, there's a simple PassThroughController which just receives actions from the GUI and passes them on to the network which then passes them to the simulation. For the AI, there will be something like an AIController. What this means is that each AI player will run on one computer only. I guess this will increase the bandwidth usage somewhat, but allows me to load balance and simplifies synchonization so I think it's worth it.

Does this seem like a reasonable architecture to begin with?


My main concern is how to create the interface for the AI. For example, ideally one would want to be able to just do something like unit.MoveTo(x, y) but since Unit is part of the simulation layer, I can't do that since it would only affect the local simulation. I could do controller.Move(unit, x, y), but that feels unclean somehow. I was thinking about wrapping units in a PerceivedUnit class/struct at the controller layer (and also PerceivedBuilding, PerceivedMap etc). I think this would potentially give me a very nice and clean interface, but I have to admit I'm a bit scared about the performance hit here, since it would basically wrap the entire gamestate. What do you people think?
The main thing to keep in mind is that you are designing what should be an opaque API; i.e. the AI layer should have no implicit representation or knowledge of what's going on underneath in the network/simulation areas. So it really doesn't matter what the API looks like; make it however you want. Just add a thin layer that translates the scriptable objects and method calls into the actual network-synchronized game state changes.

By limiting what functionality your API exposes in this way, you can make it impossible to really cheat by writing a nasty AI script. For instance, your API could provide exclusively a list of units/buildings within the currently visible fog of war, and offer no way to access "the list of all units in the world" or whatnot.

Wielder of the Sacred Wands
[Work - ArenaNet] [Epoch Language] [Scribblings]

This topic is closed to new replies.

Advertisement