/* world.c
 *
 * Represents a map.
 *
 * (c) 2006, Joseph Curtis
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "world.h"
#include "player.h"

#ifndef x86
#include <pspdebug.h>
#define printf pspDebugScreenPrintf
#endif



/* The default world */
struct world *default_world;

struct world *create_world() {
  struct world *w;

  printf("create_world:\n");

  w = calloc(1, sizeof(struct world));

#ifndef x86
  w->graphics = loadImage("images/SCENERYC.png");
  if(w->graphics == NULL)
    printf("Failed to load scenery.\n");
  w->army_graphics = loadImage("images/ARMIESC.png");
  if(w->army_graphics == NULL)
    printf("Failed to load army graphics.\n");
#endif

  w->num_players = NUM_PLAYERS;

  return w;
}


int destroy_world(struct world *w) {
  free(w->map);
  free(w->towns);
  free(w->armies);
#ifndef x86
  free(w->graphics);
#endif
  free(w);
  return 1;
}


// TODO: error checking here and below

int save_world(struct world *w, char * file) {
  FILE *f;

  f = fopen(file, "w");

  if(f == NULL)
    return (int)NULL;

  /* write the eight ints */
  fwrite(w, sizeof(int), 8, f);

 /* write the command */
  fwrite(w->command, sizeof(char), 1, f);

  /* write the name */
  fwrite(w->name, sizeof(char), WORLD_NAME_LENGTH, f);

  /* write the cells */
  fwrite(w->map, sizeof(struct cell), w->width*w->height, f);
  /* write the towns */
  fwrite(w->towns, sizeof(struct town), w->num_towns, f);
  /* write the armies */
  fwrite(w->armies, sizeof(struct army_group), w->num_armies, f);
  /* write the players */
  fwrite(w->players, sizeof(struct player), w->num_players, f);

  return 1;
}


int load_world(struct world *w, char *file) {
 FILE *f;

 f = fopen(file, "r");
 
 if(f == NULL)
   return NULL;

 w = realloc(w, sizeof(struct world));
 printf("realloc'ed world\n");

 /* read the eight ints */
 fread(w, sizeof(int), 8, f);
 printf("read six ints, %d, %d, %d, %d, %d, %d\n", w->width, w->height,
	w->num_towns, w->num_armies, w->vis_x, w->vis_y);

 /* read the command */
 fread(w->command, sizeof(char), 1, f);

 /* read the name */
 fread(w->name, sizeof(char), WORLD_NAME_LENGTH, f);
 printf("read the name: %s\n", w->name);

 w->map = realloc(w->map, sizeof(struct cell) * w->width * w->height);
 printf("realloc'ed map\n");
 /* read the cells */

 printf("read %d cells\n",  fread(w->map, sizeof(struct cell), w->width*w->height, f));

 w->towns = realloc(w->towns, sizeof(struct town) * w->num_towns);
 // printf("realloc'ed the towns\n");
 /* read the towns */

 printf("read %d towns\n",  fread(w->towns, sizeof(struct town), w->num_towns, f));

 w->armies = realloc(w->armies, sizeof(struct army_group) * w->num_armies);
 // printf("realloc'ed the armies\n");
 /* read the armies */

 printf("read %d armies\n",  fread(w->armies, sizeof(struct army_group), w->num_armies, f));

 w->players = realloc(w->players, sizeof(struct player) * w->num_players);
  /* read the players */
  fread(w->players, sizeof(struct player), w->num_players, f);
 return 1;
}

int load_world_text(struct world *w, char *file) {
  FILE *f;
  int i, j;

  printf("load_world_text:\n");
  
  f = fopen(file, "r");

  if (f == NULL)
    return (int)NULL;

   w = realloc(w, sizeof(struct world));
   
   /* read the first line */
   fscanf(f, "%d %d %d %d %d %d %d %d %d %s\n", &(w->width), &(w->height),
	  &(w->num_towns), &(w->num_armies), &(w->num_players), &(w->vis_x),
	  &(w->vis_y), &(w->turn), &(w->command), w->name);

   printf("Read first line\n");

   w->map = realloc(w->map, sizeof(struct cell) * w->width * w->height);
   w->towns = realloc(w->towns, sizeof(struct town) * w->num_towns);
   w->armies = realloc(w->armies, sizeof(struct army_group) * w->num_armies);
   w->players = realloc(w->players, sizeof(struct player) * w->num_players);
 
   printf("Realloced\n");

   for (j=0;j<w->height;j++) {
     for (i=0;i<w->width;i++) {
       fscanf(f, "%d ", &(w->map[I(i, j, w->width)].image));
     }
   }

   printf("Read cells\n");

   for (i=0;i<w->num_towns;i++) {
     printf("About to read town %d\n", i);
     fscanf(f, "%s %d %d %d\n", w->towns[i].name, &(w->towns[i].x),
     	    &(w->towns[i].y), &(w->towns[i].image));
     //	    (int *)&(w->towns[i].defence),
     //     	    (int *)&(w->towns[i].owner), (int *)&(w->towns[i].income),
     //     	    (int *)&(w->towns[i].num_production));
     printf("Read town %d\n", i);
   }

   printf("Read towns\n");

   return 1;
}



int setup_default_world() {
  int i, j;
  
  default_world = create_world();

  default_world->width = 11;
  default_world->height = 19;

  strcpy(default_world->name, "Defaultia");

  default_world->map = malloc(sizeof(struct cell)*default_world->width*default_world->height);

  for(i=0;i<(default_world->height)*(default_world->width);i++)
      default_world->map[i].image = 9;

  for (i=0;i<default_world->width;i++)
    default_world->map[i].image = 8;
  for (i=0;i<default_world->width;i++)
    default_world->map[I(i, (default_world->height-1), default_world->width)].image = 8;
  for(i=0;i<default_world->height;i++)
    default_world->map[I(0, i, default_world->width)].image = 8;
  for(i=0;i<default_world->height;i++)
    default_world->map[I((default_world->width-1), i, default_world->width)].image = 8;

  for (i=0;i<default_world->width;i++)
    default_world->map[I(i, (default_world->height/2), default_world->width)].image = 8;
  for (i=0;i<default_world->height;i++)
    default_world->map[I((default_world->width/2), i, default_world->width)].image = 8;

  default_world->vis_x = ((default_world->width*CELL_WIDTH) / 2) - ((VIS_WIDTH * CELL_WIDTH) / 2);
  default_world->vis_y = ((default_world->height*CELL_HEIGHT) / 2) - ((VIS_HEIGHT * CELL_HEIGHT) / 2);

#ifndef x86
  default_world->graphics = loadImage("images/SCENERY.png");
  if(!default_world->graphics) {
    printf("Image load failed!\n");
  } else {
    printf("After show_world\n");
  }
#endif
  
  return 1;
}




void print_world(struct world *w) {
  int i, j;

  printf("Name: %s\n", w->name);
  printf("width: %d, height: %d\n", w->width, w->height);
  printf("num_towns: %d, num_armies: %d\n", w->num_towns, w->num_armies);
  printf("vis_x: %d, vis_y: %d\n\n", w->vis_x, w->vis_y);
  
  for (j=0;j<w->height;j++) {
    for(i=0;i<w->width;i++) {
      printf("%3d ", w->map[I(i, j, w->width)].image);
    }
    printf("\n");
  }

  for(i=0;i<w->num_towns;i++) {
    printf("%s: %d, %d, %d\n", w->towns[i].name, w->towns[i].x,
	   w->towns[i].y, w->towns[i].image);
  }
  
}


void create_test_army(struct world *w) {
  printf("create_test_army:\n");

  w->armies = realloc(w->armies, sizeof(struct army_group) * 1);
  w->num_armies = 1;
  
  w->armies[0].num_armies = 1;
  w->armies[0].on_top = 0;
  w->armies[0].a[0].type = light_infantry;
  strcpy(w->armies[0].a[0].name, "Jo's Magnificent!");
  w->armies[0].a[0].moves_left = light_infantry.max_moves;
  w->armies[0].a[0].x = 5;
  w->armies[0].a[0].y = 5;

  //  print_army(w->armies[0].a[0]);

}


void create_test_player(struct world *w) {
  printf("create_test_player:\n");

  w->players = realloc(w->players, sizeof(struct player) * 1);
  w->num_players = 1;

  printf("realloced players\n");
  
  strcpy(w->players[0].name, "Sirians");
  w->players[0].team = SIRIANS;
  w->players[0].num_cities = 1;
  w->players[0].income = 50;
  w->players[0].upkeep = 0;
  w->players[0].gold = 100;
  w->players[0].type = HUMAN;
  w->players[0].capital = 0;
  
  return;
}

