domenica 5 ottobre 2014

Main concepts of a grid-based game in processing

This isn't actually a project I worked on but something I did two years ago and I want to share.
For the ones who don't know what a grid based game is, try to think at most of the Pokémon games.
The advantages of creating a grid-based game are:
-lightweight game: all the information (as we'll see) can be stored in a few file and the media files (graphics and sound) are usually a few.
-long-plot game: in this post I'll talk about just the basic concepts but developing this type of game can bring you a endless suite of tools for creating a really long-plotted game.
-easy to code: generally this type of game is easy to code natively (without the use of any external library) and this makes you able to access all the parts of your own engine.

Some concept of my really really simple engine:
1) the game is based on a "map", stored in an array and load from a file
2) in the map moves an element called Personaggio (it's the italian word for "character"), I created a customized class for this
3) the draw() function is used just to draw what's saved in the map array, all the  changes to array are made through the keyPressed() function
4) the character moves to a direction (up, down, left, right) which is stored in a variable

Here is the code I wrote, everyone is free to use it but I would appreciate if you mention my name:

//code by Damiano Andreghetti 08/2014

String mapfile = "map.txt";
int msx = 0;
int msy = 0;
int[][] map = new int[1000][1000];
int dir = 0;
int s = 20;
Personaggio personaggio;

void setup(){
  loadMap(mapfile);
  size(800,800);
}
 
void draw(){
  background(180);
  for(int row = 0; row < msy; row++){
    for(int col = 0; col < msx; col++){
      int val = map[row][col];
      if(val == 49){
          fill(255,0,0);
          rect(col*s, row*s, s, s);         
         }
      if(val == 50){
        fill(0, 255, 0);
        rect(col*s, row*s, s, s);
        if(dir == 0){
          fill(0);
          line(col*s+s/2, row*s+s/2, col*s+s, row*s+s/2);
          }
        if(dir == 1){
          line(col*s+s/2, row*s+s/2, col*s+s/2, row*s+s);
          }
        if(dir == 2){
          line(col*s+s/2, row*s+s/2, col*s, row*s+s/2);
          }
        if(dir == 3){
          line(col*s+s/2, row*s+s/2, col*s+s/2, row*s);
          }
        }
      if(val == 51){
        fill(0, 0, 255);
        rect(col*s, row*s, s, s);
        }
      }
  }   
}

void loadMap(String mapfile){
  String lines[] = loadStrings(mapfile);
  msy = lines.length;
  msx = lines[0].length();
  for (int i = 0 ; i < msy; i++) {   
    for (int b = 0; b < msx; b++) {
      map[i][b] = lines[i].charAt(b);
      if(lines[i].charAt(b) == 50){
        personaggio = new Personaggio(b,i);
        }
      }
    } 
  }

class Personaggio {;
int xpos, ypos;
  Personaggio(int x, int y){
    xpos = x;
    ypos = y;   
    map[ypos][xpos] = 50;
    }
  void move(int mx, int my){
    if(map[ypos+my][xpos+mx] == 48){
        map[ypos][xpos] = 48;
        xpos += mx;
        ypos += my;
        map[ypos][xpos] = 50;
      }
    }
}

void keyPressed() {
  if(keyCode == UP){
   if(dir == 3){
     personaggio.move(0, -1);
     }
   else{
     dir = 3;
     }
   }
  if(keyCode == DOWN){
   if(dir == 1){
     personaggio.move(0, 1);
     }
   else{
     dir = 1;
     }
   }
  if(keyCode == LEFT){
   if(dir == 2){
     personaggio.move(-1, 0);
     }
   else{
     dir = 2;
     }
   }
  if(keyCode == RIGHT){
   if(dir == 0){
     personaggio.move(1, 0);
     }
   else{
     dir = 0;
     }
   }
}


This is a good map you can use to test it:

11111111111
12000000001
10000000001
10000000003
10000000003
10000000001
10011100001
10010100001
10000100001
10000100001
11111111111


the code is really simple but you can make it better easily, by adding for example:
-sprites
-functions for making the character interact with the environment
-bots

I hope this will be useful for you as a row and basic engine for a grid-based game.
If you have any question about the code just comment or send me an email to damianoandre@gmail.com

Bye, Dami