Category Archives: Games

Game assets now use CloudKit

Imperium uses some game data that could be fairly dynamic.  This includes things like the single- and multiplayer scenarios, engine parameters and all AI behavior scripts. Initially all this data was included in the normal game bundle. Easy solution as there’s really nothing to do but to load then data when needed. It’s also not very dynamic. To tweak a parameter, improve the AI slightly or just fix some issue in a scenario I would have to create a new version and submit it to the App Store. There it would be subject to the normal app review delay, making any form of quick turnaround impossible. Clearly not ideal.

To solve this I added an asset server to the normal multiplayer server. This game server runs on some hosted server and will be used for multiplayer games. It was quite simple to add some extra requests to allow the server to also serve asset data from a set of known files. The game would upon startup request a list of available assets. Each asset in the list would have a version and Imperium would compare the version to a local version and request a new version if the server had a newer one. Easy to set up and manage. The server side would just be a simple text file containing the asset index which could be easily updated as new asset versions were created. The problem with this solution is that the server is not really 100% done yet and requires some work in order to scale and be robust enough. That requires time that I don’t have right now.

CloudKit

In order to not have to work on the server asset handling I moved the static assets to Apple’s iCloud and access them via CloudKit. The conversion was quite easy and the code is now a lot simpler. The simplicity is mostly because I don’t have to worry about network communication myself, that’s handled by CloudKit. I also do not have to worry about scalability or stability of the server, that’s also handled by someone else. The asset downloading is perhaps a tiny bit slower now, but there will not be too frequent changes anyway so that’s a hit I’m willing to take. For single player games my own server will not be used at all for now, it will be back in the picture when it’s time to finish the multiplayer side. The game will download only changed assets by using a similar version attribute. Each game keeps track of the last version of assets it has downloaded and just asks CloudKit for any new assets with a higher version. Sometimes the result is empty, sometimes it’ll get some assets.

The drawbacks of using CloudKit is that the asset handling is a bit more cumbersome from my point of view. Uploading assets has to be done via Apple’s CloudKit dashboard and there is no easy form of automation available that could, say, sync the assets that I have locally with those on CloudKit. There is a web service that can be used to build such a thing, but it’s far too low level for this to be a viable task for me to do now. So assets will have to be manually click-click-click uploaded when they change. Not a terribly big issue once the game has been released, but while developing it’s a bit annoying.

But there’s been progress at least, some minor part has been finished. 🙂

Beta testing, streaming and tutorials

Tutorials

The original tutorials for Imperium were not too great. Or specifically the third one was a bit buggy and it was easy to do something that confused the tutorial and messed up the progression. That tutorial has now been redone and it’s much less fragile and easier to play. The game will still require all three tutorials to be played through before allowing any online or campaign games to start. That’s just to make sure that all players have at least some form of grasp what the game is about before jumping into online battles without any idea how to play.

Streaming content

There has been a possibility to put updated content on the server and have the game download that when it starts up for quite a while. Now I however changed the system so that a lot of the real game content is always downloaded from the server instead of being shipped with the game. When starting up for the first time all scenarios, campaign data, AI data as well as all help files will be downloaded from the server and saved locally on the iPad. From then on each start will check if there is some updated data and download if available. This allows for trivial distribution of new scenarios, update old ones, tweak the AI and write new help documentation without having to do an App Store update. The server side resource system is also very simple to handle, so I see this as a very nice improvement.

Beta testing

As normal, if you want to play the game is it is now, get in touch and I’ll set up a TestFlight version for you. So far there have been absolutely no interest for any of the test versions I’ve released over the years. I assume that’s an indication that this type of game really isn’t interesting to anyone, or that Imperium simply looks boring or bad. I assume it’s the former.

Multiplayer progress

The multiplayer code in Imperium has seen a lot of work this summer. It’s shaping up quite well and it’s soon in a state where it can be tested live. Setting up games works fine via a server hosted by https://www.digitalocean.com/. Latencies seem to be ok but I still need to do some measuring to make sure there are no issues. The lobby works ok and it’s possible to set up games that others can join.

The video below shows how to set up an online game from scratch as well as how to edit armies.

 

 

Multiplayer changes

The multiplayer code in Imperium has seen a bit of activity lately. A new server has been written to work as the backend server and the old PubNub backend was ditched. Before that I used Photon, but it was a real cluster mess when used from Objective-C, it was quite clear that they did not care one bit about keeping that API up to date. So, an own simple server it was. That server is open source and can be downloaded from GitHub. I will host the backend where Imperium connects to on Digital Ocean.

The main change to the multiplayer code is that previously multiplayer battles were predefined scenarios with a fixed map and fixed units. That meant that there was not too much variation between battles. The new thing is that the player can define own armies which are used in multiplayer battles. These armies are a bit like decks in Clash Royale and similar games. There can be three different armies defined and they can contain any kind of units. When the player starts a multiplayer battle he/she first selects the army to be used and then proceeds to either host a game or join an existing game.

The army selection screen looks like this:

Army selection screen

Army selection screen

Select the current army from the buttons on the left, view the contents of the selected army on the right and then tap Play to continue with the multiplayer setup.

Pressing Edit takes the player to the army editing screen where the contents of the selected army can be changed.

Army editor screen

Army editor screen

When creating an army there are two limitations:

  1. the army can contain a maximum of 20 units
  2. the total cost of the army can be max 1000 credits.

The three buttons on the left select what troop types should be shown on the right side field.  The Standard troops (shown above) are normal infantry and cavalry troops. The Artillery troops contains all artillery units and the Support troops are various smaller support teams such as machine guns, mortars, snipers and flamethrowers.

All units have a cost associated with them. An army can cost 1000 credits. The cost of each unit is shown after the unit name.

All units are available as individual units as well as larger formations. The larger formations all come with a headquarter unit and various other units. The larger formations give price discounts as well as a headquarter as a bonus unit. The contents of each larger formation is shown below the formation name.

 

New weapon

This is a minor post just to mention that there’s now a new weapon type in Imperium. It’s quite easy to add new weapon types, especially if they are similar to some old weapon type. The new one is a sniper rifle which basically is a normal rifle with a longer range and far better accuracy. Normal infantry shooting with normal rifles are not very accurate at all, they mostly shoot in the correct direction. The sniper rifles are meant to be used by small support units of a few men, not big formations. The role of all the support units is to provide specialized support to the bulk of the troops. The sniper units will join the other support units: mortars, machine gunners and flamethrowers.

In other news, there is not much other progress. I tried to improve the scenario selection screen with a new commissioned background, but it did not work out how I intended it. I’ll see what to do about that, but for now it sapped my motivation pretty badly and I can’t really be bothered to put in any serious effort.

 

Online server

Server architecture

Imperium will use a dedicated server for handling online games. An online game is always between two human players that currently have online access. The server is written in Python and is very minimal. The server handles both TCP and UDP:

  • TCP is used for all setup for the games, such as lobby handling, announcing games, player data etc.
  • UDP is used for all updates once the game has started.

The server know about announced games and connected player and handles the starting of games when a player has joined an announced game. Basically everything that relates to handling a lobby. Anything to do with the real Imperium data or logic is unknown to it. When the games start the server becomes a simple data relay that just forwards packets to the other player. The only exception here is a ping packet which the server answers.

The server is available at: GitHub.

Lobby and setting up games

Imperium will have a really simple “lobby” where available games are shown and you can choose to host a game of your own. There will be no filtering, ranking or similar, all open games are available to all players. Initially when players connect to the lobby they enter a name that will be shown to other players. No filtering or sanity checks are done (yet) on these names. Time will tell if that needs to be done.

Once a name has been entered Imperium will connect to the server and show the lobby. The lobby lists games that other players host that currently await an opponent as well as the scenarios that the local player can choose to host. To join a game in the lobby simply tap on it and it will start. To host an own game just select a scenario from the list and tap Host on the next screen. Imperium will now show a waiting screen while it waits for some other player to connect to the game. Once a player connects the game starts. As soon as both players have loaded the scenario in question the server starts the game.

Game engine architecture

It’s quite hard to get a good architecture for doing realtime games. As time is a factor when resolving action it all depends on where the action is resolved so that it’s fait to both players. There are a few possibilities:

  • the server resolves all action and the players just display the results and handle input. This is fait to both players, but requires a server with full knowledge of the game logic, basically a client without any graphics. Imperium’s server is very dumb and doesn’t know anything about the game other than sending some data back and forth.
  • one player does all the calculations. This is unfair to the second player who will always have a lagging connection to the server. The local player will be able to perform actions and see results a bit faster, thus getting an unfair edge.
  • both players calculate all action. This would be fair to both players, but would be a bit complex when it comes to keeping it all in sync.
  • both players handle the calculations of the local player’s units.

The last of the options has been chosen for Imperium. Each client will handle the calculations for all the local player’s units. This is fair to both players as both handle their own units without any lag. There will be a fair deal of synchronization going on as both clients will send all changed missions to the other as well as updates for moving units. This method will make it possible that a client acts on old data, for example firing on a unit that technically has moved out of range. But as the action is very slow paced and it doesn’t really matter much if some limit will be exceeded a bit, this shouldn’t really be a problem.

All the updates for units that move or change state somehow will be sent as UDP packets to minimize lag. Periodically extra data with all missions etc will be sent so that both clients can keep their state in sync.

Slow progress

Some real like issues have more or less prevented me from doing much on Imperium since the last update. I won’t have much time over this fall, but there has been some progress though and I’ll try my best to push out a new test version soon.

AI updates

The AI has seen a bit of an overhaul and now the foundations are looking very good. The rules that actually make the computer units do things will still need a lot of work, but everything needed to make those decisions is ready. The efficiency of the AI code is also improved and the AI calculations are now spread out more in order to avoid hiccups in the game when the AI is executed.

Howitzers

There is now a new weapon type: howitzers.  These are guns that can be used to do direct fire just like the other cannons but they can also be used to provide indirect fire just like the mortars. Their range is longer than that of the mortars, so howitzer units can be used to provide efficient fire support and attack units they can not see themselves.

Rallying

Headquarters automatically rally units that have routed that are within their command control radius. Now the headquarters can also be given an explicit rally mission that has the headquarter focus on a particular own unit and makes it rally much faster.

Networking

The networking component will be PubNub. Originally Photon was to be used, but their Objective-C API is a real mess and very hard to use. It’s basically just a very low level set of calls without any documentation whatsoever apart from a badly designed example application. I wasted a lot of time with Photon in the past and during the summer while trying to get the new version to work. PubNub is much cleaner and the API is magnitudes easier to use. It has not yet proved itself to actually work in a realtime game context though, so we’ll see how it goes. The idea now is to see if the multiplayer could be added to version 1.0 after all.

 

Imperium now more or less feature complete

It seems that Imperium is now more or less feature. I’m looking at the Trello lists where all features, todo:s and bugs are listed and they are more or less empty right now. Of course there are some items left, but none of those are really too important. So it seems that there really isn’t too much new that needs to be added at least right now. There is obviously a lot of balancing and tweaking to be done, that all important “polish” that everyone raves about.

What now is needed is content such as scenarios and a narrative that holds it all together. This is not something I’m good at. In fact, I suck at making content that requires a creative imagination. 🙂 Of course, the scenario editor is still open source so anyone can help out. The scenarios are even easy to test on an iPad directly from the scenario editor. If you’re interested, get in touch and I’ll get you started.

Once there are 15-20 ok scenarios the game can be released. I do plan on adding more content later after release, but there must be a solid base set at release. Nobody wants to buy a game with 1h of play time.

 

Real time with pause

Yesterday I started thinking a bit about adding a pause button to Imperium that would pause the simulation but still allow orders to be given. Previously I’ve thought that it would be a massive undertaking and require a lot of work on the simulation side. When I thought a bit about it I came to the conclusion that it should not be that hard after all, in fact it could be quite simple. Seems it was simple after all and there is now a nice pause button up in the right corner.

Pause-hdTap the button once to pause and again to resume the normal action. All I basically had to do was pause the simulation, and that functionality has always been there. I wonder why I never thought about this before.

 

 

 

Imperium combat

I thought I’d blog a bit about how the combat resolution works in Imperium. It’s not just a simple die roll and then apply some random casualties, but there is a bit more to it than that. I’ll use as an example an infantry unit with 30 men firing basic rifles at another infantry unit with 20 men 150 m away.

Firepower

The first thing is to figure out a base firepower that the firing unit sends out in the air and how much of that firepower reaches the target.

baseFirepower = number of firing weapons * firepower per weapon
baseFirepower = 30 * 0.3
baseFirepower = 9

This firepower is modified based on the range to the target. At 50% of maximum range the firepower is unaffected, but then it linearly decreases and reaches a given modifier at max range. For the basic rifles the max range is 250 meter. Interpolating a bit gives us:

rangeModifier = 0.9

If the unit is low on ammunition then a modifier of 0.3 is applied. The units will never run completely out of ammo but can always share, scavenge, steal or somehow find something to fire, but the efficiency is greatly reduced. In our case the firing unit has plenty of ammunition.

ammoModifier = 1.0

The firing unit’s experience is also a modifier. A green unit will not fire as accurately and as well in general as an elite unit. They will fumble and just not get as much firepower into the air. This modifier is currently set at 0.5 for green units, 0.7 for regular, 0.8 for veterans and 1.0 for elite units. Lets assume our unit is a veteran unit.

experienceModifier = 0.8

The unit type modifier gives a slight penalty of 0.7 for firing cavalry units. They fire when mounted and the accuracy is just not too good. Headquarter units also get a slight penalty as not all men are busy firing, some will be busy shouting orders and leading the battle in general. Our unit is an infantry so the modifier is 1.0.

unitTypeModifier = 1.0

A terrain modifier is then applied based on the terrain the attacker is in. Some terrain is detrimental to the effect of the fire. As an example when firing in woods some of the firepower will hit trees and thus get lost. Different units get different penalties for different terrain. For instance artillery firing from a ford gets a 0.2 modifier which is the worst possible. Lets assume our unit is on a field and gets no penalty.

attackerTerrainModifier = 1.0

If the unit fires as part of an advance or assault then a penalty is applied due to the stressful and hasty situation. They units simply don’t shoot as well when on the move. This modifier is 0.7 for advancing or assaulting units. Our unit is standing still and firing and gets ni penalty.

missionTypeModifier = 1.0

Finally a random modifier is applied, it’s [0.8 .. 1.2]. Lets assume it’s 1.0 for this example.

randomModifier = 1.0

This is everything that affects the outgoing firepower, lets multiply it all together:

firepower = baseFirepower * rangeModifier * ammoModifier * experienceModifier * unitTypeModifier * attackerTerrainModifier * missionTypeModifier * randomModifier
firepower = 6.48

The total firepower that leaves the firing unit is thus 6.48.

Scatter

Now that some firepower has left the firing unit and flies through the air it will cause something to happen to the target. The first thing to modify the effect is how much the firing is scattered. This is basically similar to the rangeModifier, but does not diminish the firepower, it modifies where it lands. Each weapon has a scatter value which is based on the distance. Every weapon type is inaccurate at max distance. A flamethrower for instance has a scatter distance of up to 50 meters on a max firing range of 100 meters. Quite a  lot.  The scatter is calculated as a scatter distance from the target position and then modified by the attacker experience. The idea is that more experience units are more accurate at hitting their desired target. Elite units will have the scatter distance modified by 0.5 and green units will not have it modified at all. Finally a random modifier is applied. to the distance and the center point is calculated.

All units that are close enough will receive some damage. This tries to  make fire more realistic as units that were not targeted at all can still be damaged, even own units. So don’t fire into a melee where your own units are. The cut off distance is currently set at 30 meters from the “landing point”. Any unit further away than that will be unharmed and units within that radius will get a distance modifier based on how far they really were. Lets assume 10 meters of scatter.

distanceModifier = 1 - 10 / 30 = 0.66

Fire effect

Each unit within the area of effect is then dealt damage. It’s irrelevant for this example if there are other units close, so lets assume there are none. A target terrain modifier is then resolved. It is a value from 0.5 to 1.0 and indicates how well the terrain protects the target. Woods for instance has a value of 0.6, fields 1.0 and so on. Various unit types can also have slightly different modifiers to indicate how well they can use the terrain they are in. Lets assume the target is in scattered trees:

targetTerrainModifier = 0.8

Finally the casualties are calculated. This gives us a direct value of how many men were hit:

casualties = (firepower / hitUnits ) * distanceModifier * targetTerrainModifier
casualties = (6.48 / 1) * 0.66 * 0.9 = 3.85 men

The value is rounded down, which means that the target loses 3 men.

Retreating

We then calculate a percentage for how many men the target lost:

percentageLost = (casualties / men) * 100
percentageLost = (3 / 20) * 100 = 15%

If the target does not have command control the percentage is doubled and if the target is disorganized then it is also doubled. The reason for calculating the lost percentage is that it is used to check if the target unit will retreat. A higher percentage of lost men means it’s more eager to retreat. Our target has command control and is not disorganized, so the percentage is not modified. Then a random value from 0 to 100 is checked against the percentage. If it is less than the percentage then the unit retreats. So a disorganized unit simply has a higher chance to retreat. In our case the target does not retreat, but if it would have to retreat a suitable position away from the attacker would be chosen and the unit would retreat. For our example the target would have a 15% chance or retreating.

Finally the attacker has expended one ammunition point.

Phew, this is roughly how it all goes. 🙂