Monday, June 28, 2010

Auto-zoom camera

I've posted a new version of my lunar-lander-on-a-disc game to its little website. The addition of an auto-zooming camera makes the game much more playable most of the time. Changes:
  • Auto-zooming camera (can be toggled off with Space)
  • Improved landing gear graphics
  • Tuned landing gear physics
  • Rocket has to be touching ground with both feet to count as landed
  • Display elapsed time after completing mission






The landing gear has been adjusted so it can't invert itself on hard impacts. I still need to transmit shock through to the hull when you reach the compression limit on the landing gear; a current “exploit” is that you can survive an impact of any magnitude so long as you can absorb it completely without letting the hull touch the ground.

Line drawing is very slow on some graphics drivers, so I'm gradually replacing my uses of that. The landing gear was one; the trajectory plots are the other.

The big change this week is the camera. Most of the time it works well enough that you can complete the game without needing to manually adjust it. The algorithm right now is very simple: it frames the rocket and the nearest objective.

The biggest place where this falls down is when you need to do some close maneuvering and the nearest objective is far away. It also doesn't work if the player has something else in mind besides going to the nearest objective. I've been trying to think of better metrics but haven't hit on anything yet. I think the camera needs may change once opposing force is added, so I will probably do that next. I'll start with some simple turrets and give the rocket the ability to shoot back.

7 comments:

Mark said...

My suggestions:

1. The camera will preferentially frame nearby landmasses the rocket is on a course to collide with, and/or enemy units that are targeting you.

2. If you're allowed to visit the landing sites in order, then the player should have the ability to switch objectives. The camera would then frame the ship and the nearest objective.

James McNeill said...

In an earlier prototype I experimented with a camera that framed the rocket and the projected impact point. It works well for landing tasks, but the impact point can change wildly when the rocket's thrusting so there needs to be some way of smoothing that out. I will be trying something like that again soon.

I'd like to encourage exploration of the terrain's nooks and crannies (finding semi-hidden things, say), so ideally the camera would support undirected movement.

I'm kicking around a lot of ideas about which direction to take the game. One is to make it into a bit of a real-time strategy game, along the lines of Herzog Zwei, where your rocket is your "cursor" for moving ground units around. I don't know how strategic I can make ground combat on a side-scrolling environment, though.

Jotaf said...

[Oops, I accidentaly commented on an older post. It'll probably get missed so I'm re-posting here.]

Hey man, I just tried out the new version, it's pretty cool! Having an objective, simple as it may be, really makes it feel much more gamey and much less prototypey.

I think it would be even more satisfying if you saw some stranded astronauts walking towards the ship (or getting picked up by a grappling hook, as you mentioned, or climbing up a rope-ladder). A crashed ship (and some other scattered ship parts maybe), just making part of the scenery, would also add to the immersion :)

About improving the camera, maybe I'm simplifying a bit, but I would interpolate nicely (to prevent sudden transitions) between 2 camera modes:
1) when any of the powered/unpowered trajectories hit a rock in less than, say, 10 seconds, center/zoom the camera on those points and the ship (make sure they're visible).
2) when the collisions are more than 10 seconds away, or don't exist, center on the ship and provide a good default zoom level.

Just making some suggestions; the amount of progress you made in this prototype is amazing :)

Jotaf said...

There's a relatively easy way to tame jumpy cameras that I used earlier in other games (although, as all generic smoothing schemes, it has its limits). Don't recalculate the camera's position/zoom every time, keep the current state and update it a bit towards the target state (the desired position/zoom calculated by whatever method). It's easier to describe with some pseudo-code:

camera_x += min(max_pos_change, target_camera_x - camera_x);
camera_y += min(max_pos_change, target_camera_y - camera_y);
camera_zoom += min(max_zoom_change, target_camera_zoom - camera_zoom);

Here, max_pos_change and max_zoom_change are tweakable values. You could use a more sophisticated system (cap movement magnitude, etc) but this one sufficed for me. I think it works better than the classic interpolation method of camera_x = camera_x*0.8 + target_camera_x*0.2 (or other values that add to 1), since it makes the camera move a lot at the beginning and decrease velocity as it approaches the target. :)

James McNeill said...

Jotaf:

Yeah, making the arrows behave like little guys is slated for the near future. I want them to move toward the rocket when it's landed, and attempt to get out of the way of the rocket flame when it's landing.

I'll also put some sort of art in to make them look like guys but it's likely to be pretty crude for a while. Think bathroom gender signs, or crosswalk signs.

Looks like you're proposing linear interpolation of the camera parameters over time?

I think what I might like is something with limited acceleration, so it eases into motion and then eases back out, but doesn't have any cap on how fast it can go.

jice said...

Very nice ! Quite addictive despite its simplicity. Keep going ! Also I would love if the autocam goes closer to the ship. Playing at this range :
http://3.bp.blogspot.com/_n1-d7AQD7f4/TCipbBsw68I/AAAAAAAAAtA/tu5TEmpQSrI/s400/new-lander-legs.gif
for really slow approaches would allow to enjoy the ship physics much better.

jice said...

erf.. stupid me... I had the autozoom disabled on first try. It already goes at close range :D