Thursday, December 13, 2012

Nostalgia and Inspiration

I took a trip down memory lane this week; I played the original Sid Meier's Colonization and the original Stronghold.

Sid Meier's Colonization
Stronghold
I was probably about 15 years old the last time that I played these, and really quite bad at strategy games.  Now that I play them again, I can really start to appreciate them.  It was pure luck that I played these two at about the same time; I started thinking, and they blended in my mind: I could see the similarities and the differences and the good ideas and the bad ideas, and suddenly inspiration struck.

Nation Builder would no longer be just another Dwarf Fortress clone; it will be something new.  It will bear some similarity to Dwarf Fortress, Colonization and Stronghold, but it will be a game in its own right.

Monday, November 26, 2012

Axonometric Graphics and Status Effects Redesign

After a lot of thought, I have decided that using actors is a better approach to persistent status effects than sticking modifiers onto an actor's statistics and removing them with events in an event queue.

This way one can have complicated effects that change with time, effects that only occur at certain places or under certain circumstances, effects can be the targets of spells and abilities, and it is much easier to add visuals to applied effects.  I feel certain I will find many more uses for this.

I have also grudgingly accepted that my game-play ideas require that the game is three-dimensional, so this weekend I added a third dimension to the map and to the base class for physical actors.  I have decided that "proper" 3-D graphics is still not an option, so I am implementing an axonometric graphics renderer.

Isometric graphics makes use of an isometric projection, which is a special case of an axonometric projection.  In an isometric projection, each three-dimensional axis is assigned a direction on the plane of the two-dimensional projection, the three directions are 120 degrees apart, and the scale of the axes are the same.  This gives a view without perspective, as if the world is seen using only parallel rays, and these rays are all parallel to the vector (1, 1, 1).

In an axonometric projection, the view still has no perspective, but the rays are no longer parallel to (1, 1, 1), but rather to a vector of my choosing.  So the axes' directions are no longer separated by 120 degrees, and are no longer at the same scale.  Calculating the new angles and scales from the rays' direction vector would be a chore, but fortunately one does not need to do that.  As most things in graphics go, getting it to look right is much more practical than making it be right.  Since the axonometric tiles will be drawn by hand and the computer will only assemble them accurate to within a pixel, it is sufficient to draw a cube by hand and use its measurements as the basis for all the rest of the tiles.


Monday, November 19, 2012

Physics Engine - Part One (Introduction)

Inspired by Shamus Young's soft-body physics explanation, and disillusioned by the shortcomings of jODE and jBullet, I recently started working on an OpenCL-based physics engine in Java.  After reading up a lot about how these systems work, I discovered a way to handle the full continuum from soft to hard constraints, which, to my knowledge, not even the top-of-the-range commercial physics libraries do.

To keep the development fast, I decided to first implement it in 2-D in Java, then upgrade it to 3-D and finally port it to OpenCL.  Normally one couldn't just port from a serial language to a parallel language and expect a performance improvement, but I will keep this in mind throughout the design and implementation.

I am handling all objects as sets of connected simplices with a particle at every vertex, and a length constraint on every edge.  To calculate the mass of each particle, I will divide each simplex into Voronoi cells for its vertices, calculate the volumes of these cells, multiply these volumes by the density of the simplex, and finally sum these masses for each vertex.

Unlike most soft-body systems, my simulation will support rigid length constraints between the particles.  The way to do this, I believe, is not to use forces directly, but rather to find the closest local minimum in a potential field.  And with 'closest' I mean that I minimize the sum of the squares of the impulse required to reach that minimum.  The potential functions applied are simple enough that this means that I could use gradient descent or a related method.  In fact, I plan on having each individual constraint simple enough to solve in one step.  In the end, this is identical to using the forces directly, except that the forces' strengths are exactly as required, rather than arbitrary, and therefore causes/allows no oscillations or exponentials.

Of course, it would not be a soft-body system without soft constraints.  I will handle soft constraints the same as the rigid constraints, except with a hard limit on the strength.  This is again very similar to the force-based method, except that it doesn't apply more force than is needed.  (However, I do expect some trouble with keeping track of the total applied impulse over multiple iterations.)

To handle collisions, sliding, rolling and friction, I could use conditional constraints if I can think up the right data structure to optimize the calculations.  It will probably resemble some of the common collision detection algorithms, except adapted to run in parallel.  I will post more about this when I have the details sorted out.

Friday, November 16, 2012

Gaming the Meta-game

An enjoyable article examining how game designers can affect the meta-game:

When Players Make The Rules: On Memes and the Meta-Game

Of course, a player could possibly also make use of this phenomenon, and game the meta-game as such.

Monday, November 5, 2012

A Framework for Special Abilities

I have been working on the framework that will handle the characters' special abilities in my as-yet-unnamed RPG.  Special abilities include skills and spells, as well as the effects of equipment and consumable items.

The main idea is that an ability is triggered and has certain effects, some of which are instant and some of which are delayed.  For instance, if there was a spell called 'Frog', it would be triggered when the character casts the spell. The effect would be to apply a frog transformation on the target, and to put a 'cancel transformation' event in the event queue, to be applied when the spell would wear off.

Some typical trigger use-cases that I considered were:

  • An active ability registers its trigger object(s) with a player or AI, indicating that it needs to be activated when the controller sees fit.
  • A semi-passive ability registers itself with its character object, giving a trigger object that specifies when it should activate.
  • A passive ability triggers when the ability is gained.

It looks like all abilities can be handled with triggers and effects, but during transformations, possessions and body swaps there will need to be special handling of non-instant and delayed-effect abilities.  Maybe the event queue is not the best way to handle long-term effects.

Back to the drawing board!

Wednesday, October 31, 2012

Useful links and a new perspective

I spent the last year programming lots of stuff, but with very little worth showing:

I got myself up to date with OpenGL 4.
I tried to learn OpenCL.  Will have to try again, though.
I wrote a terrain mesh simplifier, based on ideas from Shamus Young's Terrain Project.
I wrote an emulator for the DCPU-16 from Notch's new game 0x10c.
I designed ROBOL, a new programming language specialized for game AI and robotics.
I worked on a graphics engine based on dual-contouring of voxel data, deferred convex polyhedron volumetric lighting and portals, with gamma-correction, pre-multiplied alpha and dithering.
I wrote a buggy AI for a Tron lightcycles-like game as part of the Entelect R100000 challenge.

The graphics engine would be worth showing, except that I'm trying to implement it in OpenCL, and have thus far failed to really get it started.  Maybe I should try it in pure Java first...  modify the Cyclopean engine...

Meanwhile, I've decided to get away from 3-D graphics for a bit, and get back to simple 2-D sprites.  It's amazing what you can do with 2-D if you're artistic.  And the quality of my recent paintings do imply that I am sufficiently artistic.

Yesterday I had an idea for a project that would be simple enough to produce rapid progress:  A 2-D real-time RPG with a significant amount of modularity.  The modularity is needed so that I can start with a bare-bones game (i.e. rapid visible progress) and then add more ideas with time, until it has enough features.

Overall, I intend to update this blog every Sunday from now on.  I will mostly post about my new RPG: showing off screenshots, explaining design choices, hyping the innovative ideas, etcetera.  When I don't have time to work on the RPG, I will go more in-depth and technical on things that I did in my previous projects.

Hopefully, my new articles will teach others useful new tricks and give them understanding of some interesting algorithms.