It’s been almost a year since I officially started the project, although I haven’t been working on it full-time (I had to leave the project in July and only picked it back up this January). I really wanted to keep a full development log, but got carried away developing… and for a significant amount of time I had no connection to the world (wide web), but enough excuses, lets do a quick recap…
My last post was in May. The first change that occurred after I came back to it was to abandon test-driven development, as once again I got convinced that it is a major buzz-kill and not very appropriate when you have to play with the product (it could be just me though). Once unit testing was out of the way things got wild, in a matter of a few hours there were tops chasing each other and clashing in battles, going in and out of the arena. This only proves how powerful evolutionary prototyping is for games. The first milestone was making the dyzx human controlled, but later I added some basic AI that could chase, go random and/or avoid being kicked out.
The arena had a pretty nice evolution. At first it was darkness (just a normal map), the first natural step afterwards was to use that normal map to lit it up, and so there was (directional) light. Eventually I added point lights as well. But more interesting than the visuals were the gameplay aspects of the arena. At first the dyzx (tops) were merely controlled by the normal map, at some point I had to implement the arena-out event (when dyzx leave the stadium they die) and with that came the holes, it was now possible to place holes anywhere on the arena that would kill dyzx that fall into them. At a later stage I made it possible for dyzx to bump into high arena features, which could be placed at strategic spots to prevent dyzx from flying out of the arena or falling into a hole. When I was doing the dyzk-arena collision I initially planned to make the hit model for the dyzk a circle (just like in the dyzk-dyzk collision), but for simplicity I only implemented it as a diameter line running in the direction of the dyzk velocity. I knew very well the drawbacks of this approach – if the dyzk goes straight towards the fall and hits it front first then it works, but if it goes sideways the collision won’t occur and the dyzk would climb the wall instead (because the slope isn’t as steep when you take it under an angle) – that behaviour was not intended, it was a bug… Then it hit me that was actually a wall-ride trick, you could use it to get to otherwise unreachable places, or gain extra acceleration. Up until that point I thought of the arena as a dyzk container where the main attraction would be the battles, but it can be much more than that – it can easily become a skatepark, a place full of obstacles that brings out the best of action players and becomes a battleground for demonstration of skills other than mere brawling. Shortly after that the gameplay entered the third dimension. X and Y were sufficient when we only had a normal map to navigates us in the 4 directions, but now we needed Z so that we can catch air and fly around the map. After reworking the physics a bit and faking 3D visuals I got to the current state of the project.
Here’s a video:
There is still a whole lot more to do. I’ll be really happy once I manage to get online multiplayer working (but it will probably be some time before that happens).
Top War sounds a little generic and uninspired, it was a placeholder after all.
After a giving it some thought I realized that a small flat circular object is not a top, but rather a disc. After tilting it a bit it looks even flatter than it should .
see what I mean? It’s flat : )
I could of course draw a line or a beam through the center of the image but that would be too easy. Instead I decided to declare the spinning objects to be discs. I thought disx sounds cool, after a while it turned into dizx and I though “I need to get a Y in there” so it became dyzx – seemed to be unique enough in google, especially in combination with “battle” it yelds no results, so I claimed it! :3
Did creating of a normal map from a depth mask yesterday, which will be used by the game physics. It was quite a challenge to get it right in the first place and then to get to perform well in lua (here’s the relevant source bit). Just for the fun of it I made the top follow the normals and this is the fruit of all those effort:
It still takes about 1 to 5 seconds to process a 1024×1024 image, but at least I’m sure it does it in the most optimal way :)
It is sort of important to save CPU cycles when doing physics stuff because all of this will have to be handled by the server. Love2D allows saving of image data so once computed it could be stored for later. And if bad comes to worse this can always be implemented in C…
Next step will be getting this tested and integrated in the trunk (boring stuff) and making of a server and a client.
When something spins fast, it blurs. It has to otherwise it looks as if it’s rotating by arbitrary angles. Originally I had this effect done by rendering the same image multiple times, each time slightly rotated and more transparently than the previous time. Yesterday I tried doing it the GLSL way, which looks way better (and is faster). Here’s the result:
And here’s the shader:
uniform float angle;
#define NUM_ROTATIONS 30
vec4 effect( vec4 color, Image texture, vec2 texture_coords, vec2 screen_coords )
vec2 center = vec2( 0.5, 0.5 );
vec2 relPos = texture_coords - center;
vec4 finalColor = vec4( 0.0, 0.0, 0.0, 0.0 );
float progression = 0.0;
for( int i=0; i<NUM_ROTATIONS; i++ )
float angleFract = - angle*float(i)/float(NUM_ROTATIONS);
float cs = cos( angleFract );
float sn = sin( angleFract );
vec2 newPos = vec2( relPos.x*cs - relPos.y*sn, relPos.x*sn + relPos.y*cs );
newPos += center;
vec4 tex = texture2D( texture, newPos );
float rate = pow(float(i),1.2) * (tex.a +0.4);
progression = progression + rate;
finalColor += tex * rate;
I had prototyped a spinner based game earlier in November (I think) and it was very fun to play against my brother, but I couldn’t get to develop it because of the constantly emerging university deadlines. Finally uni’s over which means I’m free… at last until the exams come.
The game is supposed to be an action/fighting game where 2 or more spinning tops fight to the death. It was mainly inspired by the cheap plastic Chipicao spinners I used to collect as a kid (good times…), and they were in turn based on beyblade. There are a couple of Beyblade video games for different consoles already and they new ones keep coming out. Unfortunately it isn’t a ground-breaking idea, people have been making tops for millennia, but there aren’t great many (enough) spinning top games either (especially for PC), plus I really want to make this one.
It is a seemingly simple scenario – there is an arena or terrain (usually bowl shaped) and 2 or more spinning tops. Gravity moves the tops as low as it can (i.e. towards a local minimum) and rigid body physics sends them flying when they touch. Although simply watching this simulation (over and over) becomes more boring by the second, it peaks the interest when you try to predict the outcome and reason about the underlying system, especially if you have the choice of what top(s) to use. Adding the ability to control one of the tops to a certain degree while it still obeys the laws of physics adds even more fun to the equation as now players are no longer mere spectators. Being able to defy and exaggerate those laws on occasions (or more importantly your opponent’s ability to do so) adds a pinch of unpredictability. To cut it short, just the core concept of it sounds enough to keep players engaged.
Anyways, I’ve been playing with this yesterday and since the first prototype was a complete mess (merely a proof of concept), I had to start from scratch. There are many ideas that will go in the mix (and probably more that will drop out), here are a few of them:
- Tops are flat 2D images which rotate on the screen and bump into each other.
- Each top has the following primary stats – WEIGHT, JAGGEDNESS, RADIUS, BALANCE. These are directly calculated based on the image. The more pixels, the more weight, the less of a circle it is the more jaggedness, the more off-center the mass is the less balance… you get the picture.
- In addition tops will have secondary stats some of which are based on the primary ones – MAX-RPM, PUSH-BACK, ENERGY. Stats are a really boring part of the mechanics so I’ll skip the explanations… :)
- Special abilities possibly based on the colors from the image
- Arenas are 2D color images with a depth mask. The depth mask determines the incline and can also be used for lighting (and possibly displace mapping).
- It is a 2D game (no need for a 3rd dimension) but with a couple of cheap tricks can be given 3D-ish look :)
- Competitive multilayer on a single machine or over the network.