8
\$\begingroup\$

I've recently gotten into XNA and must say I love it. As sort of a hello world game I decided to create the classic game "Snake". The 90 degree version was very simple and easy to implement. But as I try to make a version of it that allows 360 degree rotation using left and right arrows, I've come into sort of a problem.

What i'm doing now stems from the 90 degree version: Iterating through each snake body part beginning at the tail, and ending right before the head. This works great when moving every 100 milliseconds. The problem with this is that it makes for a choppy style of gameplay as technically the game progresses at only 6 fps rather than it's potential 60.

I would like to move the snake every game loop. But unfortunately because the snake moves at the rate of it's head's size it goes way too fast. This would mean that the head would need to move at a much smaller increment such as (2, 2) in it's direction rather than what I have now (32, 32). Because I've been working on this game off and on for a couple of weeks while managing school I think that I've been thinking too hard on how to accomplish this. It's probably a simple solution, i'm just not catching it.

Here's some pseudo code for what I've tried based off of what makes sense to me. I can't really think of another way to do it.

for(int i = SnakeLength - 1; i > 0; i--){
    current = SnakePart[i], next = SnakePart[i - 1];

    current.x = next.x - (current.width * cos(next.angle));
    current.y = next.y - (current.height * sin(next.angle));

    current.angle = next.angle;
} 

SnakeHead.x += cos(SnakeAngle) * SnakeSpeed;
SnakeHead.y += sin(SnakeAngle) * SnakeSpeed;

This produces something like this: Code in Action. As you can see each part always stays behind the head and doesn't make a "Trail" effect.

A perfect example of what i'm going for can be found here: Data Worm. Not the viewport rotation but the trailing effect of the triangles.

Thanks for any help!

\$\endgroup\$

1 Answer 1

5
\$\begingroup\$

With that algorithm, you're making each segment face the same angle as the one in front of it. That's why they all end up getting directly behind the head, they're ultimately all facing the same angle. As you can see in the Data Worm game you linked, each segment just faces toward the segment in front of it. Determine the angle from the current segment to its next and have the segment point that way instead of setting it to next.angle.

For that implementation, you may want to actually iterate from front to back instead. The behavior will be different based on the direction you pass through the list. Try them both and see which works better.

I've used a similar idea for a project prototype in the past (Unity WebPlayer link). I used similar (albeit 3D) code to get each segment to turn toward the segment in front of it and stay back a set distance. Worked like a charm.

\$\endgroup\$
6
  • \$\begingroup\$ That's great! I was reading a blog that uses a concept similar to that but didn't think of iterating from the front to back. I'll give it a shot and mark this as an answer if it's successful. \$\endgroup\$ Jun 10, 2012 at 22:13
  • \$\begingroup\$ Update: Got it working! Took some time to grasp the concept and understand what's actually going on. Thanks again for leading me into the right direction! Here's a video of the working code :) screenr.com/Fhn8. Don't mind the food collision, haven't spent much time on it. \$\endgroup\$ Jun 11, 2012 at 0:01
  • 1
    \$\begingroup\$ Glad I could help! \$\endgroup\$ Jun 11, 2012 at 2:32
  • \$\begingroup\$ Your link is dead. \$\endgroup\$
    – Jeff
    Mar 22, 2013 at 23:13
  • 1
    \$\begingroup\$ @Jeff Apparently Dropbox has decided I'm drawing too much traffic somehow, which is weird... \$\endgroup\$ Mar 24, 2013 at 6:12

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .