Thread: Snake Game

Page 2 of 2 First 12
  • Jump to page:
    #16
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    12
    Rep Power
    0
    I'm thinking that the loop should look something like this:

    Code:
    for (int i = snake.size() - 1; i > 0; i--) {
    
    /* something to make a specific index of the snake take the spot 
    of the one preceding it, so I know that for the left and right commands it will 
    somehow involve snake.some method or code.x = snake.some method or code.x + 1 */
    
    }
    Any hints on this?
  2. #17
  3. Contributing User
    Devshed Expert (3500 - 3999 posts)

    Join Date
    Aug 2010
    Location
    Eastern Florida
    Posts
    3,714
    Rep Power
    348
    so if I press the up arrow, all five blocks are shifted up one space instead of only the head going up.
    How should the code print the motion of the body of the snake? The following sections need to continue in the same direction until they get to the turning point before changing direction. They can not ALL change direction at the same time.
  4. #18
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    12
    Rep Power
    0
    Originally Posted by NormR
    How should the code print the motion of the body of the snake? The following sections need to continue in the same direction until they get to the turning point before changing direction. They can not ALL change direction at the same time.
    Precisely. My intention is to use the head of the snake as a guide for the user, so that when the player enters an arrow key it moves the head in the corresponding direction. However, that leaves the issue of the rest of the body. I want the rest of the body to take the position of the block that came before it. So let's take the default snake:

    Code:
     public void initGame() {
    		snake = new ArrayList<Coordinate>();
    		snake.add(new Coordinate (15,15));
    		snake.add(new Coordinate (14,15));
    		snake.add(new Coordinate (13,15));
    		snake.add(new Coordinate (12,15));
    		snake.add(new Coordinate (11,15));
    		
    		board.updateSnake(snake);
    		
    		timer = new Timer(DELAY, this);
    		timer.start();
    		growCounter = 0;
    		moveCounter = 0;
    		
    		left = false;
    		right = true;
    		up = false;
    		down = false;		
    	}
    This initializes the snake from a range of (11,15) to the head of (15,15). Now, lets say that I want to move the head up. The correct coordinates should be:

    (12,15) , (13,15) , (14,15) , (15,15) and (15,16) and the snake should should make the following transformation:

    -------------------------------------x
    xxxxx (default snake) to ---> xxxx (new snake)

    I don't know how to move the head up one y-value unit without moving the rest of the body up. How can I do this?
  6. #19
  7. Contributing User
    Devshed Expert (3500 - 3999 posts)

    Join Date
    Aug 2010
    Location
    Eastern Florida
    Posts
    3,714
    Rep Power
    348
    Work on the logic before writing any code. What are the steps the program needs to do to have each part of the body continue in the current direction until it gets to the turning point before starting to move in the new direction. The body sections change direction one at a time.
  8. #20
  9. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    12
    Rep Power
    0
    Been working for a few more hours now...up to this:

    Code:
    import java.util.*;
    import java.awt.Color;
    import java.awt.Font;
    import java.awt.FontMetrics;
    import java.awt.Graphics;
    import java.awt.Image;
    import java.awt.Toolkit;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.awt.event.KeyAdapter;
    import java.awt.event.KeyEvent;
    import java.util.ArrayList;
    
    import javax.swing.ImageIcon;
    import javax.swing.JOptionPane;
    import javax.swing.JPanel;
    import javax.swing.Timer;
    
    /**
     * The main game class that reads user input,
     * maintains a snake and updates game board
     * 
     *
     **/
    public class MainGame implements ActionListener {
    
    	// size of the game board (30 * 30 by default)
    	private final int WIDTH = 30;
    	private final int HEIGHT = 30;
    	
    	private final int Init_Snake_Length = 5;
    	
    	// delay of detecting user input ( in milliseconds )
    	private final int DELAY = 100;
    	
    	// grow the snake every GROWTH_INTERVAL milliseconds
    	private final int GROWTH_INTERVAL = 5000;
    	// move the snake every MOVE_INTERVAL milliseconds
    	private final int MOVE_INTERVAL = 500;
    	
    	// The snake (as a list of coordinates in the 2D board array)
    	private ArrayList<Coordinate> snake;
    	
    	// The game board object - read GameBoard.java
    	private GameBoard board; 
    	
    	// Flag variables indicating which direction is chosen
    	// by user. Only one of the four can be true at any moment
    	private boolean left = false;
    	private boolean right = true;
    	private boolean up = false;
    	private boolean down = false;
    
    	private Timer timer;
    	private long growCounter;
    	private long moveCounter;
    	
    	public MainGame() {
    		board = new GameBoard(WIDTH, HEIGHT);
    		initGame();
    		board.addKeyListener(new TAdapter());
    	}
    	
    	public static void main(String[] argv) {
    		MainGame mg = new MainGame();
    	}
    	
    	public void initGame() {
    		snake = new ArrayList<Coordinate>();
    		snake.add(new Coordinate (15,15)); //head
    		snake.add(new Coordinate (14,15)); // upper body
    		snake.add(new Coordinate (13,15)); // middle body
    		snake.add(new Coordinate (12,15)); // lower body
    		snake.add(new Coordinate (11,15)); // tail
    		
    		board.updateSnake(snake);
    		
    		timer = new Timer(DELAY, this);
    		timer.start();
    		growCounter = 0;
    		moveCounter = 0;
    		
    		left = false;
    		right = true;
    		up = false;
    		down = false;		
    	}
    	
    	private void moveSnake() 
    	{
    		
    		if (right == true) 
    		{
    			snake.get(0).x = snake.get(0).x + 1;
    			for (int i = 1; i < snake.size() -1; i++) 
    			{
    				snake.get(i).x = snake.get(i+1).x;
    			}
    		}
    		
    		if (left == true) 
    		{
    			snake.get(0).x = snake.get(0).x - 1;
    			for (int i = 1; i < snake.size() -1; i++) 
    			{
    				snake.get(i).x = snake.get(i+1).x;
    			}
    		}
    			
    		if (up == true) 
    		{	
    			snake.get(0).y = snake.get(0).y - 1;
    			for (int i = 1; i < snake.size() -1; i++) 
    			{
    				snake.get(i).y = snake.get(i+1).y;
    			}
    		}
    
    		
    		if (down == true) 
    		{
    			snake.get(0).y = snake.get(0).y + 1;
    			for (int i = 1; i < snake.size() -1; i++) 
    			{
    				
    				snake.get(i).y = snake.get(i+1).y;
    			}
    		}
    		}
    				
    
    		// -------------------------------------------------------------
    		// Task 2: Move the snake by updating the list of coordinates properly
    		// The direction to move to is given by the four flag variables (left, right, up, down)
    		//
    
    		
    		// Task 2 end
    		//--------------------------------------------------------------
    
    		
    	
    	private void growSnake() {
    		// -------------------------------------------------------------
    		// Task 3: Grow the snake by updating the list of coordinates properly
    		//
    
    		
    		
    		// Task 3 end
    		//--------------------------------------------------------------
    	}
    
    
    	private void checkCollision() {
    		boolean collision = false;
    		
    		// -------------------------------------------------------------
    		// Task 4: Insert code here to detect collision
    		//
    
    		
    		
    		// Task 4 end
    		//--------------------------------------------------------------		
    		
    		
    		if (collision) {
    			gameOver();
    		}
    	}
    	
    	private void gameOver() {
    		JOptionPane.showMessageDialog(board, "Game Over");
    		System.exit(0);
    	}
    	
    	/**
    	 * The actions to be performed every DELAY milliseconds
    	 */
    	public void actionPerformed(ActionEvent e) {
    		
    		if ( ++growCounter * DELAY >= GROWTH_INTERVAL) {
    			growSnake();
    			growCounter = 0;
    		} 
    		if ( ++moveCounter * DELAY >= MOVE_INTERVAL) {
    			moveSnake();
    			moveCounter = 0;
    		}
    
    		checkCollision();
    		board.resetBoard();
    		board.updateSnake(snake);
    		board.repaint();
    
    	}
    
    
    	/**
    	 * A key listener class for reading user's input.
    	 * 
    	 *
    	 */
    	private class TAdapter extends KeyAdapter {
    
    		public void keyPressed(KeyEvent e) {
    
    			int key = e.getKeyCode();
    
    			if ((key == KeyEvent.VK_LEFT) && (!right)) {
    				left = true;
    				up = false;
    				down = false;
    			}
    
    			if ((key == KeyEvent.VK_RIGHT) && (!left)) {
    				right = true;
    				up = false;
    				down = false;
    			}
    
    			if ((key == KeyEvent.VK_UP) && (!down)) {
    				up = true;
    				right = false;
    				left = false;
    			}
    
    			if ((key == KeyEvent.VK_DOWN) && (!up)) {
    				down = true;
    				right = false;
    				left = false;
    			}
    		}
    	}
    }
    I've tried to think through it as logically as possibly, changed and tested my code at least 50 times, however now when I run my program it begins correctly with the head moving to the right, however the rest of the body dissipates except for the tail at (11,15). What is the cause of this?
  10. #21
  11. Contributing User
    Devshed Expert (3500 - 3999 posts)

    Join Date
    Aug 2010
    Location
    Eastern Florida
    Posts
    3,714
    Rep Power
    348
    Try debugging the code by printing out the values of the variables so you can see what the code is doing when it executes.

    Can you post the steps in your logic (as pseudo code) so we can see it?

    I'm done for tonight. Back tomorrow.
  12. #22
  13. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    74
    Rep Power
    18
    May I suggest a different approach?

    As of now you iterate over the snake arraylist and update each snake-coordinate to the value of the next snake-coordinate:
    Code:
    for (int i = 1; i < snake.size() -1; i++) 
    {
    	snake.get(i).x = snake.get(i+1).x;
    }
    This is certainly not bad, as it is true that as the snake moves the coordinate of snake-part i will become the coordinate of snake-part i+1. What is missing in your code: what happens to the tail of the snake, which is effectively at position snake.get(snake.size()-1) ? In your for-loop the update for tail is missed because you iterate until a value smaller than snake.size()-1. The old coordinate of the tail at snake.get(snake.size()-1) will still be in the arraylist.

    Now, as for a different approach. As you look at the snake, there is only 1 coordinate that is really changing: the head. As the head moves forward, coordinates from the tail are truncated. All other coordinates between the head and tail remain equal, until those hit the tail and are removed as well.
    My suggestion would be: during movement, add a new coordinate to position 0 of the arraylist, and remove the last item in the arraylist.
  14. #23
  15. Contributing User
    Devshed Expert (3500 - 3999 posts)

    Join Date
    Aug 2010
    Location
    Eastern Florida
    Posts
    3,714
    Rep Power
    348
    A suggestion for helping you debug the code:
    Add a toString() method to the Coordinate class that returns a String with the values of x and y. That will show their values easily when you print them.
    Add a call to the println() method in the updateSnake() method that prints out the value of the ArrayList: snake. The print out will show you how the values of the Coordinates objects are being changed and will explain:
    it begins correctly with the head moving to the right, however the rest of the body dissipates except for the tail at (11,15).
Page 2 of 2 First 12
  • Jump to page:

IMN logo majestic logo threadwatch logo seochat tools logo