/*
Dave Brondsema's submission to the ICFP Programming Contest 2002
Copyright (C) Dave Brondsema 2002

This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA

*/

#include "SDL_net.h"

#include <iostream>
#include <string>
#include <sstream>

#include "misc.h"
#include "package.h"
#include "action.h"
#include "globals.h"
#include "reply.h"
#include "ai.h"

using namespace std;

// printing operator
ostream & operator<< (ostream & out, const vector< vector<char> > & b)
{
	/*
	for(vector< vector<char> >::const_reverse_iterator iy = board.rbegin(); iy != board.rend(); ++iy)
	{
		for(vector<char>::const_iterator ix = iy->begin(); ix != iy->end(); ++ix)
			out << ix;
		out << endl;
	}
	*/
	vector< vector<char> > board(b);
	
	for(map<long, package>::iterator i = available_packages.begin(); i != available_packages.end(); ++i)
		board[i->second.x][i->second.y] = '%';
	
	for(map<long, bot>::iterator i = bots.begin(); i != bots.end(); ++i)
		board[i->second.x][i->second.y] = '0'+i->second.packages.size();
	
	board[me.x][me.y] = 'X';
	
	for(long y = board[0].size()-1; y >=0; --y)
	{
		for (long x = 0; x < board.size(); ++x)
			out << board[x][y];
		out << endl;
	}
	out << "$$$" << endl;
	return out;
}



int main(int argc, char *argv[])
{
	if(SDL_Init(SDL_INIT_TIMER) == -1)
	{
		e("SDLNet_Init", SDLNet_GetError());
		exit(1);
	}
	if(SDLNet_Init() ==-1)
	{
		e("SDLNet_Init", SDLNet_GetError());
		exit(2);
	}
	atexit(SDLNet_Quit);
	
	
	// create a listening TCP socket on port 9999 (server)
	IPaddress ip;
	string host;
	int port = 22006;
	if (argc < 3)
	{
		cout << "Syntax:" << endl;
		cout << "runme host_name port_number [--debug]" << endl;
		cout << "example:\n\trunme icfp1.cse.ogi.edu 22006 --debug" << endl;
		exit(1);
	}
	else
	{
		host = argv[1];
		istringstream port_iss(argv[2]);
		port_iss >> port;
		
		if (argc == 4 && (string)argv[3] == "--debug")
		{
			debug = true;
		}
	}
	if(SDLNet_ResolveHost(&ip, (char*)host.c_str(), port)==-1) {
		printf("SDLNet_ResolveHost: %s\n", SDLNet_GetError());
		exit(1);
	}
	
	sock=SDLNet_TCP_Open(&ip);
	if(!sock) {
		printf("SDLNet_TCP_Open: %s\n", SDLNet_GetError());
		exit(2);
	}

	// initialize
	send("Player");
	
	string recv;
	istringstream recv_iss;

	// board dimensions
	long board_x, board_y;
	recv_iss.str(getline());
	recv_iss >> board_x >> board_y;
	board_x += 2;
	board_y += 2;
	d("board size",board_x, board_y);
	
	// board data
	board.resize(board_x);
	for (long x = 0; x < board_x; ++x)
	{
		board[x].resize(board_y);
		board[x][0] = '#';
	}
	for (long y = 0; y < board_y-2; ++y)
	{
		board[0][y+1] = '#';
		recv = getline();
		for (long x=0; x < board_x-2; ++x)
		{
			board[x+1][y+1] = recv[x];
			if (recv[x] == '@')
			{
				bases.push_back(pair<long,long>(x+1,y+1));
				d("storing base", x+1, y+1);
			}
		}
		board[board_x-1][y+1] = '#';
		d("read line",y);
	}
	for (long x = 0; x < board_x; ++x)
		board[x][board_y-1] = '#';
	// player configuration
	recv_iss.str(getline());
	recv_iss >> me.id >> capacity >> my_money;
	d("config",me.id, capacity, my_money);
	
	// robot locations
	long robot_num;
	recv_iss.str(getline());
	char dummy;
	while (recv_iss.get() == '#')
	{
		recv_iss >> robot_num	>> dummy;
		if (robot_num == me.id)
		{
			recv_iss >> me.x >> dummy >> me.y;
			d("my loc", robot_num, me.x, me.y);
		}
		else
		{
			recv_iss >> bots[robot_num].x >> dummy >> bots[robot_num].y;
			d("loc", robot_num, bots[robot_num].x, bots[robot_num].y);
		}
		recv_iss.get(); // remove a possible trailing space so the next char is #
	}
	
	// main logic loop
	bool dead = false;
	while (!dead)
	{
		d(board);
		verify_packages_here();
		
		do_ai();
		
		process_server_reply();
		
		d("available pkgs", available_packages);
		d("my pkgs", me.packages);
	}
	
	
	// clean up
	SDLNet_TCP_Close(sock);
	
	return 0;
}