Uppercut Games talks mobile development; making 'Danger Dodgers' for the App Store
Uppercut Games was formed in 2011 by a group of ex Irrational Games Australia developers. We have previously released a number of Unreal Engine 3 mobile titles on the App Store including EPOCH and EPOCH 2, and late last year our first Unreal Engine 4 title Submerged for Steam, PS4 and XBOX One.
After shipping a PC and console title with Unreal Engine 4, we wanted to do something smaller and faster, which led us to take another look at mobile. After a bit of investigation, it looked to us that with 4.9 the engine now had everything we needed to ship a game and the result is Danger Dogers, which has just landed in the App Store. Here's how this fast-moving mobile project went from concept to completion.
A Shorter Dev Cycle
Danger Dodgers development took a total of six months, with two months prototyping, three months of development, and a final month of bug fixing, tuning and testing. Six developers worked on the game, with four full time and two part time.
Materials, Materials, Materials!
One of the major differences we found between developing for mobile with UE3 and Unreal Engine 4 is the freedom we now had to be a lot more creative with materials. But this is a double edged sword, there is now a HUGE performance difference between the older and newer iOS devices we need to support. All the way from an iPad2 to the new iPad Pro. The performance gulf is most noticeable between the Metal and non-Metal devices.
With a very simple shader (pictured above) with just flat colour, roughness value and a normal map, we had frame rates below 10 fps (on older devices like iPad 2). We also turned on the ‘Fully Rough’ optimization on a lot of shaders that didn’t need any highlights. Since we were going for a claymation aesthetic this worked out well.
We started developing Danger Dodgers on version 4.9 of the engine which had some limited scalability for materials, as it required you to optimize every single material manually and create switches and levels of detail within your material graphs. With 4.10 we were able to use the new iOS ES2 Quality Presets.
This system requires all your shaders to be lower quality for any device you tell it to. It’s as simple as turning it on and adding a single line to the device profiles. We ended up using this on all the non metal devices. We saw an instant 10 fps bump in performance on these devices which took the game from unshippabe to playable instantly.
The new UI for editing and managing the device profiles is also a great help, with so many iOS devices to test and manage performance on now, having an easy place to edit the .ini using a UI instead of a text editor saves a lot of time and avoids input errors and typos.
Testing for mobile
Deploying builds to multiple devices in one go was also a great improvement for testing, we were able to set up a powered USB Hub, and connect up to eight devices to deploy a new build simultaneously. This really streamlined the performance and gameplay testing process.
Some of the many iOS devices Danger Dodgers needed to run on.
Danger Dodgers uses a couple of vertex shaders to add a bit more life to the environments. We found these had very little (if any) effect on the performance on device, and made a big impact on the visuals of the game.
The first one we called "squash and stretch" does just that. It stretches out the meteors as they fall and then squashes them as they land, giving them a rubbery, bouncy look. Here’s the nodes in the material:
I’m cheating a bit here. I’m assuming the thing I’m squashing and stretching is round. Luckily for me our meteorites are round, huzzah! I’m also assuming the object’s pivot is in the center which also turns out to be true, yay! Using those two assumptions the first part of the graph calculates the distance of each vertex from the center of the meteorite then just takes the Z component to give us the distance for each vertex from the X-Y plane through the meteor. Dividing that by the radius of the object gives us a value between -1 and 1 which we then multiply by a stretch factor and offset the vertex Z by that value. So, basically, the further from the X-Y plane the vertex is the more it stretches/squashes away from/towards that plane.
To control the stretch/squash each meteor has a dynamic material instance applied to it when it spawns. I then set the FallingObjectStretch value each tick. While the meteors are falling I set the FallingObjectStretch to max, which elongates the meteors as they fall. Then when they land I ease out the max stretch before running an elastic easing function to make the meteors squash and stretch like a rubber ball. When I say “ease out” and “elastic easing function” I’m refering to Robert Penner’s easing functions which you can learn all about here.
Let’s look at it in motion:
The other vertex effect we used is actually two separate effects smooshed into the one material which we apply to most objects in our level. When a particularly large meteor lands the objects around it pop up into the air and then bounce back into place. Here’s the bounce part of the material:
Bounce doesn’t distort the object like the squash and stretch material does. Here we’re just creating a Z offset based on the actors location relative to the location of impact. The sphere mask gives us a nice falloff from the impact location. Again, the LandedObjectForce is controlled in code by easing functions. The difference with this effect is it isn’t per object. All objects get the same force value through a Material Parameter Collection object (basically global shader parameters). The limitation of this technique is that only one meteor can cause bouncing at any one time. We limit this effect to the very large meteors so most of the time it’s hard to notice when a meteor lands but doesn’t cause bouncing.
There’s a special type of meteor in Danger Dodgers that explodes, pushing the player away from it. When this explosion happens for the very large meteors we run a “ripple” distortion through the world. Here’s the part of the material for the ripple effect:
The basic idea here is to move a sphere mask through the world. We do that by growing the ExplosionRadius over time and positioning a sphere mask at that radius and then masking out vertices based on their location relative to the ExplosionLocation. As the ExplosionRadius expands the sphere mask moves through vertices causing them to get pushed up and then back down as the sphere moves away. Hmm… I hope that makes sense. The following video show the bounce and ripple effects when the large meteors land and explode:
The ripple effect has the same limitation as the bounce in that only one explosive meteor will cause a ripple through the world at any one time.
Each of these node graphs gets combined with an Add node so the ripple effect will pass through bouncing objects.
While this information might be foreign to some and familiar to others, we hope you've enjoyed an inside look at how Danger Dodgers was developed!
Danger Dodgers is available now on the App Store, download it for free and let us know what you think!