I'm trying to program 2048, but seem to be having a issue with blocks merging.
World.GameBoard code:
Actor.GameSquare code:
The issue seems to be within:
I can't see how I would be able to fix it
import greenfoot.*; // (World, Actor, GreenfootImage, Greenfoot and MouseInfo) import java.util.List; //Instance Constants //Define some directions to make it easier to reference which way the blocks are moving private static final int UP = 0; private static final int RIGHT = 1; private static final int DOWN = 2; private static final int LEFT = 3; int sqrCount = 0; /** * Constructor for objects of class MyWorld. * */ public GameBoard() { // Create a new world with 4x4 cells with a cell size of 50x50 pixels. super(4, 4, 50); //populate gameboard with x randomly placed objects while(sqrCount<1) { if(placeRandomBlock()){ sqrCount++; } else { continue; } } } /** * Place a block on a random location on the board * * @return Returns true if successful, false if not successful */ private boolean placeRandomBlock() { GameSquare gs = new GameSquare(); //make new game square int x = (Greenfoot.getRandomNumber(4)); //Get random num from 0-3, and add 1 int y = (Greenfoot.getRandomNumber(4)); //Check to ensure random location is not yet taken, if the spot is free add it to the world if (getObjectsAt(x, y, GameSquare.class).isEmpty()) { addObject(gs,x,y); return true; } else { return false; } } /** * Act - Check for key presses and tell each block to move itself. */ public void act() { //Add key press actoins here String key = Greenfoot.getKey(); //If a key was pressed...do something if (key != null) { switch(key) { case "up": //Tell the blocks to move up //Start checking from the top, then move downwards for (int i=0; i<getWidth(); i++) { for (int j=0; j<getHeight(); j++) { //Get a list containing all of the GameSquare objects at position (i,j) List blockList = getObjectsAt(i,j,GameSquare.class); //Tell the other block object we wish to merge with it. If successful, delete this block from the game if (blockList.size() == 1) { //Error checking Object tempObject; tempObject = blockList.get(0); GameSquare tempSquare; tempSquare = (GameSquare)tempObject; tempSquare.move(UP); } } } break; case "right": //Tell the blocks to move right //Start checking from the right most col, then move left for (int i=3; i>=0; i--) { for (int j=0; j<getHeight(); j++) { //Get a list containing all of the GameSquare objects at position (i,j) List blockList = getObjectsAt(i,j,GameSquare.class); //Tell the other block object we wish to merge with it. If successful, delete this block from the game if (blockList.size() == 1) { //Error checking Object tempObject; tempObject = blockList.get(0); GameSquare tempSquare; tempSquare = (GameSquare)tempObject; tempSquare.move(RIGHT); } } } break; case "down": //Tell the blocks to move down //Start checking from the bottom, then move up for (int i=3; i>=0; i--) { for (int j=3; j>=0; j--) { //Get a list containing all of the GameSquare objects at position (i,j) List blockList = getObjectsAt(j,i,GameSquare.class); //Tell the other block object we wish to merge with it. If successful, delete this block from the game if (blockList.size() == 1) { //Error checking Object tempObject; tempObject = blockList.get(0); GameSquare tempSquare; tempSquare = (GameSquare)tempObject; tempSquare.move(DOWN); } } } break; case "left": //Tell the blocks to move left //Start checking from the left, then move right for (int i=0; i<getWidth(); i++) { for (int j=0; j<getHeight(); j++) { //Get a list containing all of the GameSquare objects at position (i,j) List blockList = getObjectsAt(j,i,GameSquare.class); //Tell the other block object we wish to merge with it. If successful, delete this block from the game if (blockList.size() == 1) { //Error checking Object tempObject; tempObject = blockList.get(0); GameSquare tempSquare; tempSquare = (GameSquare)tempObject; tempSquare.move(LEFT); } } } break; } int count = 0; if(numberOfObjects() < 16) { while (count < 1) { if (placeRandomBlock()) { count++; } } } } } }
import greenfoot.*; // (World, Actor, GreenfootImage, Greenfoot and MouseInfo) import java.util.List; public class GameSquare extends Actor { //Instance Constants //Define some directions to make it easier to reference which way the blocks are moving private static final int UP = 0; private static final int RIGHT = 1; private static final int DOWN = 2; private static final int LEFT = 3; //Define a debugging variable (See video linked in assignment outline) private final boolean debug = false; //Instance Variables private int value; //Constructor public GameSquare() { this(2); } public GameSquare(int valueIn) { setValue(valueIn); displayValue(); } /** * Tell the block to move in the given direction until it hits an obstacle * * @param The direction in which the block is to move (UP = 0; RIGHT = 1; DOWN = 2; LEFT = 3; */ public void move(int direction) { //check if can move int movable = canMove(direction); System.out.println(movable); //if moveable, start a loop while (movable > 0) { //Get current coordinates int xval = getX(); int yval = getY(); //Change x and y values to the "new" location based on direction if (direction == 0) { yval-=1; } else if (direction == 1) { xval+=1; } else if (direction == 2) { yval+=1; } else if (direction == 3) { xval-=1; } //If Nothing in the way - move the block if (movable == 1) { movable = canMove(direction); setLocation(xval,yval); continue; //return; } //Merge the blocks else { if (!getWorld().getObjectsAt(xval,yval,GameSquare.class).isEmpty()) { GameSquare sqr = (GameSquare)getWorld().getObjectsAt(xval,yval,GameSquare.class).get(0); if(merge(sqr.getValue())) { getWorld().removeObject(sqr); setLocation(xval,yval); movable = canMove(direction); continue; } else { movable = canMove(direction); continue; } } else { movable = canMove(direction); continue; } } } //can't move, so don't move. return; } /** * Sets the value of the game square to the value of the input parameter. * Will only work if the value is a factor of 2 * * @param The number to use as the new value * @return If the number was set correctly return true, otherwise return false */ boolean setValue(int valueIn) { if(valueIn % 2 != 0) { return false; } else { value = valueIn; return true; } } /** * Merge with another block and combine values. * Will only work if the two blocks are of the same value * * @param The value of the block to be added * * @return Return true if the merge is successful. */ public boolean merge(int valueIn) { int sqrVal = getValue(); if (sqrVal == valueIn) { setValue((sqrVal*2)); return true; } else { return false; } } /** * Returns the current value of the gameSquare * * @return The current value (int) of the game square */ public int getValue() { return this.value; } /** * Checks to see if the block can move * * @return int value representing what is in the space to be moved to. 0 -> Path Blocked, 1 -> Empty Space, int>1 value of block in the space to be moved to. */ private int canMove(int direction) { //Get World World world = getWorld(); //Get x and y values of current object int xval = getX(); int yval = getY(); //Change x and y values to the "new" location based on direction if (direction == 0) { yval-=1; } else if (direction == 1) { xval+=1; } else if (direction == 2) { yval+=1; } else if (direction == 3) { xval-=1; } //Test for outside border if (xval<0 || xval>3 || yval<0 || yval>3) { return 0; } //Check to see if there is a block in the way if(!world.getObjectsAt(xval, yval, GameSquare.class).isEmpty()) { GameSquare sqr = (GameSquare)world.getObjectsAt(xval,yval,GameSquare.class).get(0); return sqr.getValue(); } return 1; } /** * displayValue - Displays the current value of a block in an image, then sets that image to the block display image */ private void displayValue() { //Create an image consisting of the display value using built in greenfoot commands GreenfootImage displayImage; displayImage = new GreenfootImage( Integer.toString(value), 20, Color.BLACK, Color.WHITE); //Add the image as the new image for this object setImage(displayImage); } }
if(merge(sqr.getValue())) { getWorld().removeObject(sqr); setLocation(xval,yval); movable = canMove(direction); continue; } else { movable = canMove(direction); continue; } } else { movable = canMove(direction); continue; } } }