فهرست منبع

* fixed reading .defs
* new system for handling objects and their behaviors, most functionalities don't work now but will be restored soon
* more serialization code, savegame/loadgame bit closer :)
CHANGES IN PROJECT FILES:
* removed CLua.h and CLua.cpp (server)
* removed CScriptCallback.h and CScriptCallback.cpp (server)
* added IGameCallback.h header (lib)

Michał W. Urbańczyk 17 سال پیش
والد
کامیت
ae48e73fe7

+ 1 - 1
CCallback.cpp

@@ -241,7 +241,7 @@ std::vector < std::string > CCallback::getObjDescriptions(int3 pos) const
 	if(!isVisible(pos,player))
 		return ret;
 	BOOST_FOREACH(const CGObjectInstance * obj, gs->map->terrain[pos.x][pos.y][pos.z].blockingObjects)
-		ret.push_back(obj->hoverName);
+		ret.push_back(obj->getHoverText());
 	return ret;
 }
 bool CCallback::verifyPath(CPath * path, bool blockSea) const

+ 30 - 29
CCastleInterface.cpp

@@ -140,7 +140,7 @@ void CBuildingRect::clickRight (tribool down)
 			(LOCPLINT->playerID,
 			CGI->buildh->buildings[str->townID][str->ID]->description,
 			LOCPLINT->castleInt->bicons->ourImages[str->ID].bitmap,
-			CGI->buildh->buildings[str->townID][str->ID]->name);
+			CGI->buildh->buildings[str->townID][str->ID]->Name());
 		vinya->pos.x = screen->w/2 - vinya->bitmap->w/2;
 		vinya->pos.y = screen->h/2 - vinya->bitmap->h/2;
 		vinya->activate();
@@ -165,8 +165,8 @@ void CBuildingRect::mouseMoved (const SDL_MouseMotionEvent & sEvent)
 				if((*LOCPLINT->castleInt->hBuild)<(*this)) //set if we are on top
 				{
 					LOCPLINT->castleInt->hBuild = this;
-					if(CGI->buildh->buildings[str->townID][str->ID] && CGI->buildh->buildings[str->townID][str->ID]->name.length())
-						LOCPLINT->statusbar->print(CGI->buildh->buildings[str->townID][str->ID]->name);
+					if(CGI->buildh->buildings[str->townID][str->ID] && CGI->buildh->buildings[str->townID][str->ID]->Name().length())
+						LOCPLINT->statusbar->print(CGI->buildh->buildings[str->townID][str->ID]->Name());
 					else
 						LOCPLINT->statusbar->print(str->name);
 				}
@@ -174,8 +174,8 @@ void CBuildingRect::mouseMoved (const SDL_MouseMotionEvent & sEvent)
 			else //no building hovered
 			{
 				LOCPLINT->castleInt->hBuild = this;
-				if(CGI->buildh->buildings[str->townID][str->ID] && CGI->buildh->buildings[str->townID][str->ID]->name.length())
-					LOCPLINT->statusbar->print(CGI->buildh->buildings[str->townID][str->ID]->name);
+				if(CGI->buildh->buildings[str->townID][str->ID] && CGI->buildh->buildings[str->townID][str->ID]->Name().length())
+					LOCPLINT->statusbar->print(CGI->buildh->buildings[str->townID][str->ID]->Name());
 				else
 					LOCPLINT->statusbar->print(str->name);
 			}
@@ -193,12 +193,12 @@ void CHeroGSlot::hover (bool on)
 	{
 		if(highlight)//view NNN
 		{
-			temp = CGI->townh->tcommands[4];
+			temp = CGI->generaltexth->tcommands[4];
 			boost::algorithm::replace_first(temp,"%s",hero->name);
 		}
 		else if(other->hero && other->highlight)//exchange
 		{
-			temp = CGI->townh->tcommands[7];
+			temp = CGI->generaltexth->tcommands[7];
 			boost::algorithm::replace_first(temp,"%s",hero->name);
 			boost::algorithm::replace_first(temp,"%s",other->hero->name);
 		}
@@ -206,12 +206,12 @@ void CHeroGSlot::hover (bool on)
 		{
 			if(upg)//down - visiting
 			{
-				temp = CGI->townh->tcommands[32];
+				temp = CGI->generaltexth->tcommands[32];
 				boost::algorithm::replace_first(temp,"%s",hero->name);
 			}
 			else //up - garrison
 			{
-				temp = CGI->townh->tcommands[12];
+				temp = CGI->generaltexth->tcommands[12];
 				boost::algorithm::replace_first(temp,"%s",hero->name);
 			}
 		}
@@ -220,7 +220,7 @@ void CHeroGSlot::hover (bool on)
 	{
 		if(other->highlight && other->hero) //move NNNN
 		{
-			temp = CGI->townh->tcommands[6];
+			temp = CGI->generaltexth->tcommands[6];
 			boost::algorithm::replace_first(temp,"%s",other->hero->name);
 		}
 		else //empty
@@ -367,9 +367,9 @@ CCastleInterface::CCastleInterface(const CGTownInstance * Town, bool Activate)
 
 	townlist = new CTownList(3,pos.x+744,pos.y+414,"IAM014.DEF","IAM015.DEF");//744,526);
 	exit = new AdventureMapButton
-		(CGI->townh->tcommands[8],"",boost::bind(&CCastleInterface::close,this),pos.x+744,pos.y+544,"TSBTNS.DEF",SDLK_RETURN);
+		(CGI->generaltexth->tcommands[8],"",boost::bind(&CCastleInterface::close,this),pos.x+744,pos.y+544,"TSBTNS.DEF",SDLK_RETURN);
 	split = new AdventureMapButton
-		(CGI->townh->tcommands[3],"",boost::bind(&CGarrisonInt::splitClick,garr),pos.x+744,pos.y+382,"TSBTNS.DEF");
+		(CGI->generaltexth->tcommands[3],"",boost::bind(&CGarrisonInt::splitClick,garr),pos.x+744,pos.y+382,"TSBTNS.DEF");
 	statusbar = new CStatusBar(pos.x+7,pos.y+555,"TSTATBAR.bmp",732);
 	resdatabar = new CResDataBar("ZRESBAR.bmp",pos.x+3,pos.y+575,32,2,85,85);
 	resdatabar->pos.x = pos.x+3; resdatabar->pos.y = pos.y+575;
@@ -544,7 +544,7 @@ void CCastleInterface::buildingClicked(int building)
 				if(!hero)
 				{
 					std::string pom = CGI->generaltexth->allTexts[273];
-					boost::algorithm::replace_first(pom,"%s",CGI->buildh->buildings[town->subID][16]->name);
+					boost::algorithm::replace_first(pom,"%s",CGI->buildh->buildings[town->subID][16]->Name());
 					LOCPLINT->showInfoDialog(pom,std::vector<SComponent*>());
 					return;
 				}
@@ -653,7 +653,8 @@ void CCastleInterface::showAll( SDL_Surface * to/*=NULL*/, bool forceTotalRedraw
 	if(pom)
 		showing = false;
 
-	CMessage::drawBorder(LOCPLINT->playerID,to,828,628,pos.x-14,pos.y-15);
+	if(screen->w != 800 || screen->h !=600)
+		CMessage::drawBorder(LOCPLINT->playerID,to,828,628,pos.x-14,pos.y-15);
 }
 void CCastleInterface::townChange()
 {
@@ -896,11 +897,11 @@ void CHallInterface::CBuildingBox::hover(bool on)
 	{
 		std::string toPrint;
 		if(state==8)
-			toPrint = CGI->townh->hcommands[5];
+			toPrint = CGI->generaltexth->hcommands[5];
 		else
-			toPrint = CGI->townh->hcommands[state];
+			toPrint = CGI->generaltexth->hcommands[state];
 		std::vector<std::string> name;
-		name.push_back(CGI->buildh->buildings[LOCPLINT->castleInt->town->subID][BID]->name);
+		name.push_back(CGI->buildh->buildings[LOCPLINT->castleInt->town->subID][BID]->Name());
 		LOCPLINT->statusbar->print(CSDL_Ext::processStr(toPrint,name));
 	}
 	else
@@ -953,7 +954,7 @@ void CHallInterface::CBuildingBox::show(SDL_Surface * to)
 	blitAt(hi->bars->ourImages[pom].bitmap,pos.x-1,pos.y+71);
 	if(pom2>=0)
 		blitAt(hi->status->ourImages[pom2].bitmap,pos.x+135, pos.y+54);
-	CSDL_Ext::printAtMiddle(CGI->buildh->buildings[LOCPLINT->castleInt->town->subID][BID]->name,pos.x-1+hi->bars->ourImages[0].bitmap->w/2,pos.y+71+hi->bars->ourImages[0].bitmap->h/2, GEOR13,zwykly);
+	CSDL_Ext::printAtMiddle(CGI->buildh->buildings[LOCPLINT->castleInt->town->subID][BID]->Name(),pos.x-1+hi->bars->ourImages[0].bitmap->w/2,pos.y+71+hi->bars->ourImages[0].bitmap->h/2, GEOR13,zwykly);
 }
 void CHallInterface::CBuildingBox::activate()
 {
@@ -996,7 +997,7 @@ CHallInterface::CHallInterface(CCastleInterface * owner)
 	bars = CDefHandler::giveDefEss("TPTHBAR.DEF");
 	status = CDefHandler::giveDefEss("TPTHCHK.DEF");
 	exit = new AdventureMapButton
-		(CGI->townh->tcommands[8],"",boost::bind(&CHallInterface::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
+		(CGI->generaltexth->tcommands[8],"",boost::bind(&CHallInterface::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
 	exit->assignedKeys.insert(SDLK_ESCAPE);
 
 	//preparing boxes with buildings//
@@ -1169,11 +1170,11 @@ std::string CHallInterface::CBuildWindow::getTextForState(int state)
 {
 	std::string ret;
 	if(state<7)
-		ret =  CGI->townh->hcommands[state];
+		ret =  CGI->generaltexth->hcommands[state];
 	switch (state)
 	{
 	case 4:	case 5: case 6:
-		ret.replace(ret.find_first_of("%s"),2,CGI->buildh->buildings[tid][bid]->name);
+		ret.replace(ret.find_first_of("%s"),2,CGI->buildh->buildings[tid][bid]->Name());
 		break;
 	case 7:
 		return CGI->generaltexth->allTexts[219]; //all prereq. are met
@@ -1222,7 +1223,7 @@ std::string CHallInterface::CBuildWindow::getTextForState(int state)
 			bool first=true;
 			for(std::set<int>::iterator i=reqs.begin();i!=reqs.end();i++)
 			{
-				ret+=(((first)?(" "):(", ")) + CGI->buildh->buildings[tid][*i]->name);
+				ret+=(((first)?(" "):(", ")) + CGI->buildh->buildings[tid][*i]->Name());
 				first = false;
 			}
 		}
@@ -1240,10 +1241,10 @@ CHallInterface::CBuildWindow::CBuildWindow(int Tid, int Bid, int State, bool Mod
 	pos.x = screen->w/2 - bitmap->w/2;
 	pos.y = screen->h/2 - bitmap->h/2;
 	blitAt(LOCPLINT->castleInt->bicons->ourImages[bid].bitmap,125,50,bitmap);
-	std::vector<std::string> pom; pom.push_back(CGI->buildh->buildings[tid][bid]->name);
-	CSDL_Ext::printAtMiddleWB(CGI->buildh->buildings[tid][bid]->description,197,168,GEOR16,40,zwykly,bitmap);
+	std::vector<std::string> pom; pom.push_back(CGI->buildh->buildings[tid][bid]->Name());
+	CSDL_Ext::printAtMiddleWB(CGI->buildh->buildings[tid][bid]->Description(),197,168,GEOR16,40,zwykly,bitmap);
 	CSDL_Ext::printAtMiddleWB(getTextForState(state),197,248,GEOR13,50,zwykly,bitmap);
-	CSDL_Ext::printAtMiddle(CSDL_Ext::processStr(CGI->townh->hcommands[7],pom),197,30,GEOR16,tytulowy,bitmap);
+	CSDL_Ext::printAtMiddle(CSDL_Ext::processStr(CGI->generaltexth->hcommands[7],pom),197,30,GEOR16,tytulowy,bitmap);
 	int resamount=0; 
         
         for(int i=0;i<7;i++) {
@@ -1355,7 +1356,7 @@ CFortScreen::CFortScreen( CCastleInterface * owner )
 	pos = owner->pos;
 	LOCPLINT->curint->subInt = this;
 	bg = NULL;
-	exit = new AdventureMapButton(CGI->townh->tcommands[8],"",boost::bind(&CFortScreen::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
+	exit = new AdventureMapButton(CGI->generaltexth->tcommands[8],"",boost::bind(&CFortScreen::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
 	positions += genRect(126,386,10,22),genRect(126,386,404,22),
 		genRect(126,386,10,155),genRect(126,386,404,155),
 		genRect(126,386,10,288),genRect(126,386,404,288),
@@ -1377,7 +1378,7 @@ void CFortScreen::draw( CCastleInterface * owner, bool first)
 	graphics->blueToPlayersAdv(bg2,LOCPLINT->playerID);
 	bg = SDL_ConvertSurface(bg2,screen->format,0); 
 	SDL_FreeSurface(bg2);
-	printAtMiddle(CGI->buildh->buildings[owner->town->subID][owner->town->fortLevel()+6]->name,400,13,GEORXX,zwykly,bg);
+	printAtMiddle(CGI->buildh->buildings[owner->town->subID][owner->town->fortLevel()+6]->Name(),400,13,GEORXX,zwykly,bg);
 	for(int i=0;i<CREATURES_PER_TOWN; i++)
 	{
 		bool upgraded = owner->town->creatureDwelling(i,true);
@@ -1385,7 +1386,7 @@ void CFortScreen::draw( CCastleInterface * owner, bool first)
 		CCreature *c = &CGI->creh->creatures[upgraded ? owner->town->town->upgradedCreatures[i] : owner->town->town->basicCreatures[i]];
 		printAtMiddle(c->namePl,positions[i].x+79,positions[i].y+10,GEOR13,zwykly,bg); //cr. name
 		blitAt(owner->bicons->ourImages[30+i+upgraded*7].bitmap,positions[i].x+4,positions[i].y+21,bg); //dwelling pic
-		printAtMiddle(CGI->buildh->buildings[owner->town->subID][30+i+upgraded*7]->name,positions[i].x+79,positions[i].y+100,GEOR13,zwykly,bg); //dwelling name
+		printAtMiddle(CGI->buildh->buildings[owner->town->subID][30+i+upgraded*7]->Name(),positions[i].x+79,positions[i].y+100,GEOR13,zwykly,bg); //dwelling name
 		if(present) //if creature is present print avail able quantity
 		{
 			SDL_itoa(owner->town->strInfo.creatures.find(i)->second,buf,10);
@@ -1467,7 +1468,7 @@ CMageGuildScreen::CMageGuildScreen(CCastleInterface * owner)
 	resdatabar.pos.x += pos.x;
 	resdatabar.pos.y += pos.y;
 	bg = BitmapHandler::loadBitmap("TPMAGE.bmp");
-	exit = new AdventureMapButton(CGI->townh->tcommands[8],"",boost::bind(&CMageGuildScreen::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
+	exit = new AdventureMapButton(CGI->generaltexth->tcommands[8],"",boost::bind(&CMageGuildScreen::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
 	exit->assignedKeys.insert(SDLK_ESCAPE);
 	scrolls = CDefHandler::giveDefEss("SPELLSCR.DEF");
 	scrolls2 = CDefHandler::giveDefEss("TPMAGES.DEF");

+ 6 - 6
CGameState.cpp

@@ -292,7 +292,7 @@ CGHeroInstance* CGameState::HeroesPool::pickHeroFor(bool native, int player, con
 {
 	if(player<0 || player>=PLAYER_LIMIT)
 	{
-		tlog1 << "Cannot pick hero for " << town->name << ". Wrong owner!\n";
+		tlog1 << "Cannot pick hero for " << town->Name() << ". Wrong owner!\n";
 		return NULL;
 	}
 	std::vector<CGHeroInstance *> pool;
@@ -655,7 +655,7 @@ void CGameState::applyNL(IPack * pack)
 			if(p->what == 3) //set creatures amount
 			{
 				tlog5 << "Setting creatures amount in " << p->id << std::endl;
-				static_cast<CCreatureObjInfo*>(map->objects[p->id]->info)->number = p->val;
+				static_cast<CGCreature*>(map->objects[p->id])->army.slots[0].second = p->val;
 				break;
 			}
 			ui8 CGObjectInstance::*point;
@@ -1184,7 +1184,7 @@ void CGameState::init(StartInfo * si, Mapa * map, int Seed)
 		}
 		CGHeroInstance * vhi = (map->heroes[i]);
 		vhi->initHero();
-		players[vhi->getOwner()].heroes.push_back(vhi);
+		players.find(vhi->getOwner())->second.heroes.push_back(vhi);
 		hids.erase(vhi->subID);
 	}
 	for(int i=0; i<map->predefinedHeroes.size(); i++)
@@ -1286,7 +1286,7 @@ void CGameState::init(StartInfo * si, Mapa * map, int Seed)
 		if(!vti->town)
 			vti->town = &VLC->townh->towns[vti->subID];
 		if (vti->name.length()==0) // if town hasn't name we draw it
-			vti->name=vti->town->names[ran()%vti->town->names.size()];
+			vti->name = vti->town->Names()[ran()%vti->town->Names().size()];
 
 		//init buildings
 		if(vti->builtBuildings.find(-50)!=vti->builtBuildings.end()) //give standard set of buildings
@@ -1456,7 +1456,7 @@ float CGameState::getMarketEfficiency( int player, int mode/*=0*/ )
 	return ret;
 }
 
-std::set<int3> CGameState::tilesToReveal(int3 pos, int radious, int player)
+std::set<int3> CGameState::tilesToReveal(int3 pos, int radious, int player) const
 {		
 	std::set<int3> ret;
 	int xbeg = pos.x - radious - 2;
@@ -1479,7 +1479,7 @@ std::set<int3> CGameState::tilesToReveal(int3 pos, int radious, int player)
 			int deltaY = (pos.y-yd)*(pos.y-yd);
 			if(deltaX+deltaY<radious*radious)
 			{
-				if(player<0 || players[player].fogOfWarMap[xd][yd][pos.z]==0)
+				if(player<0 || players.find(player)->second.fogOfWarMap[xd][yd][pos.z]==0)
 				{
 					ret.insert(int3(xd,yd,pos.z));
 				}

+ 1 - 1
CGameState.h

@@ -195,7 +195,7 @@ private:
 	int battleGetStack(int pos); //returns ID of stack at given tile
 	UpgradeInfo getUpgradeInfo(CArmedInstance *obj, int stackPos);
 	float getMarketEfficiency(int player, int mode=0);
-	std::set<int3> tilesToReveal(int3 pos, int radious, int player); //if player==-1 => adds all tiles in radious
+	std::set<int3> tilesToReveal(int3 pos, int radious, int player) const; //if player==-1 => adds all tiles in radious
 public:
 	int getDate(int mode=0) const; //mode=0 - total days in game, mode=1 - day of week, mode=2 - current week, mode=3 - current month
 	template <typename Handler> void serialize(Handler &h, const int version)

+ 0 - 1015
CLua.cpp

@@ -1,1015 +0,0 @@
-#include "stdafx.h"
-#include <sstream>
-#include <boost/bind.hpp>
-#include <boost/function.hpp>
-#include <boost/algorithm/string.hpp>
-#include <boost/algorithm/string/replace.hpp>
-#include "hch/CHeroHandler.h"
-#include "hch/CObjectHandler.h"
-#include "hch/CTownHandler.h"
-#include "hch/CArtHandler.h"
-#include "hch/CDefObjInfoHandler.h"
-//#include "lua.h"
-//#include "lualib.h"
-//#include "lauxlib.h"
-//#include "lobject.h"
-//#include "lgc.h"
-//#include "lapi.h"
-#include "CLua.h"
-#include "CGameState.h"
-#include "lib/VCMI_Lib.h"
-#include "map.h"
-#include "server/CScriptCallback.h"
-#include "lib/NetPacks.h"
-#pragma warning (disable : 4311)
-#define DEFOS const CGObjectInstance *os = cb->getObj(objid)
-
-bool getGlobalFunc(lua_State * L, std::string fname)
-{
-	//unsigned int hash = lua_calchash(fname.c_str(), fname.size());
-	//lua_pushhstring(L, hash, fname.c_str(), fname.size());
-	//lua_gettable(L, LUA_GLOBALSINDEX);
-	//return lua_isfunction(L, -1);
-	return false;
-}
-
-
-
-void CObjectScript::newObject(int objid) {
-};
-
-void CObjectScript::onHeroVisit(int objid, int heroID) {
-};
-
-void CObjectScript::onHeroLeave(int objid, int heroID) {
-};
-
-std::string CObjectScript::hoverText(int objid) {
-    return "";
-};
-
-void CObjectScript::newTurn () {
-};
-
-void CObjectScript::equipArtefact(int HID, int AID, int slot, bool putOn) {
-}; //putOn==0 means that artifact is taken off
-
-void CObjectScript::battleStart(int phase) {
-}; //phase==0 - very start, before initialization of battle; phase==1 - just before battle starts
-
-void CObjectScript::battleNewTurn (int turn) {
-}; //turn==-1 is for tactic stage
-
-void CObjectScript::heroLevelUp (int HID) {
-}; //add possibility of changing available sec. skills
-//CObjectScript
-
-
-
-CObjectScript::CObjectScript()
-{
-	language = UNDEF;
-	//std::cout << "Tworze obiekt objectscript "<<this<<std::endl;
-}
-
-CObjectScript::~CObjectScript()
-{
-	//std::cout << "Usuwam obiekt objectscript "<<this<<std::endl;
-}
-
-CScript::CScript()
-{
-	//std::cout << "Tworze obiekt CScript "<<this<<std::endl;
-}
-CScript::~CScript()
-{
-	//std::cout << "Usuwam obiekt CScript "<<this<<std::endl;
-}
-
-#define LST (is)
-CLua::CLua(std::string initpath)
-{
-	opened=false;
-	open(initpath);
-}
-CLua::CLua()
-{
-	//std::cout << "Tworze obiekt clua "<<this<<std::endl;
-	opened=false;
-}
-void CLua::open(std::string initpath)
-{
-	//LST = lua_open();
-	//opened = true;
-	//LUA_OPEN_LIB(LST, luaopen_base);
-	//LUA_OPEN_LIB(LST, luaopen_io);
-	//if ((luaL_loadfile (LST, initpath.c_str())) == 0)
-	//{
-	//	lua_pcall (LST, 0, LUA_MULTRET, 0);
-	//}
-	//else
-	//{
-	//	std::string temp = "Cannot open script ";
-	//	temp += initpath;
-	//	throw std::exception(temp.c_str());
-	//}
-}
-void CLua::registerCLuaCallback()
-{
-}
-
-CLua::~CLua()
-{
-	////std::cout << "Usuwam obiekt clua "<<this<<std::endl;
-	//if (opened)
-	//{
-	//	std::cout << "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"<<std::endl;
-	//	lua_close(LST);
-	//}
-}
-
-void CLua::findF(std::string fname)
-{
-	// lua_getfield(is, LUA_GLOBALSINDEX, fname.c_str()); /* function to be called */
-}
-void CLua::findF2(std::string fname)
-{
-	//lua_pushstring (is, fname.c_str());
-	//lua_gettable (is, LUA_GLOBALSINDEX); 
-}
-void CLua::findFS(std::string fname)
-{
-	//lua_settop(is, 0);
-	//if (!getGlobalFunc(is,fname)) 
-	//{
-	//	lua_settop(is, 0);
-	//	throw new std::exception((fname + ": function not defined").c_str()); // the call is not defined
-	//}
-}
-#undef LST
-
-CLuaObjectScript::CLuaObjectScript(std::string filename)
-{
-	language = LUA;
-	open(filename);
-	//binit = bnewobject = bonherovisit = brightext = false;
-	//std::cout << "Tworze obiekt CLuaObjectScript "<<this<<std::endl;
-}
-CLuaObjectScript::~CLuaObjectScript()
-{
-	//std::cout << "Usuwam obiekt CLuaObjectScript "<<this<<std::endl;
-}
-
-void CLuaObjectScript::init()
-{
-}
-
-std::string CLuaObjectScript::genFN(std::string base, int ID)
-{
-	std::stringstream sts;
-	sts<<base<<"_"<<ID;
-	return sts.str();
-}
-
-void CLuaObjectScript::newObject(int objid)
-{
-	//findF(genFN("newObject",os->ID));
-	//lua_pushinteger(is, (int)os);
-	//if (lua_pcall (is, 1, 0, 0))
-	//{
-	//	lua_settop(is, 0);
-	//	throw new  std::exception(("Failed to call "+genFN("newObject",os->ID)+" function in lua script.").c_str());
-	//}
-	//lua_settop(is, 0);
-	return;
-}
-void CLuaObjectScript::onHeroVisit(int objid, int heroID)
-{
-	//findF(genFN("heroVisit",os->ID));
-	//lua_pushinteger(is, (int)os);
-	//lua_pushinteger(is, heroID);
-	//if (lua_pcall (is, 2, 0, 0))
-	//{
-	//	lua_settop(is, 0);
-	//	throw new  std::exception(("Failed to call "+genFN("heroVisit",os->ID)+" function in lua script.").c_str());
-	//}
-	//lua_settop(is, 0);
-}
-//std::string CLuaObjectScript::hoverText(int objid)
-//{
-//	//findF(genFN("hoverText",os->ID));
-//	//lua_pushinteger(is, (int)os);
-//	//if (lua_pcall (is, 1, 1, 0))
-//	//{
-//	//	lua_settop(is, 0);
-//	//	throw new  std::exception(("Failed to call "+genFN("hoverText",os->ID)+" function in lua script.").c_str());
-//	//}
-//	//std::string ret = lua_tostring(is,1);
-//	//lua_settop(is, 0);
-//	return "";
-//}
-
-void CVisitableOPH::newObject(int objid)
-{
-	visitors.insert
-		(std::pair<int,std::set<int> >(objid,std::set<int>()));
-
-	DEFOS;
-	MetaString hovername;
-	int pom;
-	switch(os->ID)
-	{
-	case 51:
-		pom = 8; 
-		break;
-	case 23:
-		pom = 7;
-		break;
-	case 61:
-		pom = 11; 
-		break;
-	case 32:
-		pom = 4; 
-		break;
-	case 100:
-		pom = 5; 
-		break;
-	case 102:
-		typeOfTree[objid] = rand()%3;
-		return;
-	default:
-		std::cout << "Unsupported ID in CVisitableOPH::hoverText" << std::endl;
-		return;
-	}
-	hovername << std::pair<ui8,ui32>(3,os->ID) << " " << std::pair<ui8,ui32>(2,pom);
-	cb->setHoverName(objid,&hovername);
-
-	//int heroID = cb->getSelectedHero();
-	//if (heroID>=0)
-	//{
-		//add += ( (visitors[os].find(heroID) == visitors[os].end()) 
-		//		? 
-		//	(VLC->generaltexth->allTexts[353])  //not visited
-		//		: 
-		//	( VLC->generaltexth->allTexts[352]) ); //visited
-	//}
-};
-
-void CVisitableOPH::onHeroVisit(int objid, int heroID)
-{
-	DEFOS;
-	if (visitors.find(objid)!=visitors.end())
-	{
-		if(visitors[objid].find(heroID)==visitors[objid].end())
-		{
-			onNAHeroVisit(objid,heroID, false);
-			if(os->ID != 102)
-				visitors[objid].insert(heroID);
-		}
-		else
-		{
-			onNAHeroVisit(objid,heroID, true);
-		}
-	}
-	else
-	{
-#ifndef __GNUC__
-		throw new std::exception("Skrypt nie zainicjalizowal instancji tego obiektu. :(");
-#else
-		throw new std::exception();
-#endif
-	}
-};
-void CVisitableOPH::onNAHeroVisit(int objid, int heroID, bool alreadyVisited)
-{
-	const CGObjectInstance *os = cb->getObj(objid);
-	int id=0, subid=0, ot=0, val=1;
-	switch(os->ID)
-	{
-	case 51:
-		subid=0;
-		ot=80;
-		break;
-	case 23:
-		subid=1;
-		ot=39;
-		break;
-	case 61:
-		subid=2;
-		ot=100;
-		break;
-	case 32:
-		subid=3;
-		ot=59;
-		break;
-	case 100:
-		id=5;
-		ot=143;
-		val=1000;
-		break;
-	case 102:
-		id = 5;
-		subid = 1;
-		ot = 146;
-		val = 1;
-		break;
-	}
-	if (!alreadyVisited)
-	{
-		switch (os->ID)
-		{
-		case 51:
-		case 23:
-		case 61:
-		case 32:
-			{
-				cb->changePrimSkill(heroID,subid,val);
-				InfoWindow iw;
-				iw.components.push_back(Component(0,subid,val,0));
-				iw.text << std::pair<ui8,ui32>(11,ot);
-				iw.player = cb->getOwner(heroID);
-				cb->showInfoDialog(&iw);
-				break;
-			}
-		case 100: //give exp
-			{
-				InfoWindow iw;
-				iw.components.push_back(Component(id,subid,val,0));
-				iw.player = cb->getOwner(heroID);
-				iw.text << std::pair<ui8,ui32>(11,ot);
-				cb->showInfoDialog(&iw);
-				cb->changePrimSkill(heroID,4,val);
-				break;
-			}
-		case 102:
-			{
-				const CGHeroInstance *h = cb->getHero(heroID);
-				val = VLC->heroh->reqExp(h->level+val) - VLC->heroh->reqExp(h->level);
-				if(!typeOfTree[objid])
-				{
-					visitors[objid].insert(heroID);
-					InfoWindow iw;
-					iw.components.push_back(Component(id,subid,1,0));
-					iw.player = cb->getOwner(heroID);
-					iw.text << std::pair<ui8,ui32>(11,148);
-					cb->showInfoDialog(&iw);
-					cb->changePrimSkill(heroID,4,val);
-					break;
-				}
-				else
-				{
-					int res, resval;
-					if(typeOfTree[objid]==1)
-					{
-						res = 6;
-						resval = 2000;
-						ot = 149;
-					}
-					else
-					{
-						res = 5;
-						resval = 10;
-						ot = 151;
-					}
-
-					if(cb->getResource(h->tempOwner,res) < resval) //not enough resources
-					{
-						ot++;
-						InfoWindow iw;
-						iw.player = h->tempOwner;
-						iw.text << std::pair<ui8,ui32>(11,ot);
-						cb->showInfoDialog(&iw);
-						return;
-					}
-
-					YesNoDialog sd;
-					sd.player = cb->getOwner(heroID);
-					sd.text << std::pair<ui8,ui32>(11,ot);
-					sd.components.push_back(Component(id,subid,val,0));
-					cb->showYesNoDialog(&sd,CFunctionList<void(ui32)>(boost::bind(&CVisitableOPH::treeSelected,this,objid,heroID,res,resval,val,_1)));
-				}
-				break;
-			}
-		}
-	}
-	else
-	{
-		ot++;
-		InfoWindow iw;
-		iw.player = cb->getOwner(heroID);
-		iw.text << std::pair<ui8,ui32>(11,ot);
-		cb->showInfoDialog(&iw);
-	}
-}
-
-std::vector<int> CVisitableOPH::yourObjects()
-{
-	std::vector<int> ret;
-	ret.push_back(51);//camp 
-	ret.push_back(23);//tower
-	ret.push_back(61);//axis
-	ret.push_back(32);//garden
-	ret.push_back(100);//stone
-	ret.push_back(102);//tree
-	return ret;
-}
-
-void CVisitableOPH::treeSelected( int objid, int heroID, int resType, int resVal, int expVal, ui32 result )
-{
-	if(result==0) //player agreed to give res for exp
-	{
-		cb->giveResource(cb->getOwner(heroID),resType,-resVal); //take resource
-		cb->changePrimSkill(heroID,4,expVal); //give exp
-		visitors[objid].insert(heroID); //set state to visited
-	}
-}
-void CVisitableOPW::onNAHeroVisit(int objid, int heroID, bool alreadyVisited)
-{
-	DEFOS;
-	int mid;
-	switch (os->ID)
-	{
-	case 55:
-		mid = 92;
-		break;
-	case 112:
-		mid = 170;
-		break;
-	case 109:
-		mid = 164;
-		break;
-	}
-	if (alreadyVisited)
-	{
-		if (os->ID!=112)
-			mid++;
-		else 
-			mid--;
-
-		InfoWindow iw;
-		iw.player = cb->getHero(heroID)->tempOwner;
-		iw.text << std::pair<ui8,ui32>(11,mid);
-		cb->showInfoDialog(&iw);
-	}
-	else
-	{
-		int type, sub, val;
-		type = 2;
-		switch (os->ID)
-		{
-		case 55:
-			if (rand()%2)
-			{
-				sub = 5;
-				val = 5;
-			}
-			else
-			{
-				sub = 6;
-				val = 500;
-			}
-			break;
-		case 112:
-			mid = 170;
-			sub = (rand() % 5) + 1;
-			val = (rand() % 4) + 3;
-			break;
-		case 109:
-			mid = 164;
-			sub = 6;
-			if(cb->getDate(2)<2)
-				val = 500;
-			else
-				val = 1000;
-		}
-		int player = cb->getOwner(heroID);
-		cb->giveResource(player,sub,val);
-		InfoWindow iw;
-		iw.player = player;
-		iw.components.push_back(Component(type,sub,val,0));
-		iw.text << std::pair<ui8,ui32>(11,mid);
-		cb->showInfoDialog(&iw);
-		visited[objid] = true;
-		MetaString ms; //set text to "visited"
-		ms << std::pair<ui8,ui32>(3,os->ID) << " " << std::pair<ui8,ui32>(1,352);
-		cb->setHoverName(objid,&ms);
-	}
-}
-void CVisitableOPW::newTurn ()
-{
-	if (cb->getDate(1)==1) //first day of week
-	{
-		for (std::map<int,bool>::iterator i = visited.begin(); i != visited.end(); i++)
-		{
-			(*i).second = false;
-			MetaString ms; //set text to "not visited"
-			ms << std::pair<ui8,ui32>(3,cb->getObj(i->first)->ID) << " " << std::pair<ui8,ui32>(1,353);
-			cb->setHoverName(i->first,&ms);
-		}
-
-	}
-} 
-void CVisitableOPW::newObject(int objid)
-{
-	visited.insert(std::pair<int,bool>(objid,false));
-	DEFOS;
-	MetaString ms;
-	ms << std::pair<ui8,ui32>(3,os->ID) << " " << std::pair<ui8,ui32>(1,visited[objid] ? 352 : 353);
-	cb->setHoverName(objid,&ms);
-}
-
-void CVisitableOPW::onHeroVisit(int objid, int heroID)
-{
-	if(visited[objid])
-		onNAHeroVisit(objid,heroID,true);
-	else 
-		onNAHeroVisit(objid,heroID,false);
-}
-
-std::vector<int> CVisitableOPW::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret(3);
-	ret.push_back(55); //mystical garden
-	ret.push_back(112); //windmill
-	ret.push_back(109); //water wheel
-	return ret;
-}
-
-void CMines::newObject(int objid)
-{
-	ourObjs.push_back(objid);
-	cb->setOwner(objid,NEUTRAL_PLAYER);
-	DEFOS;
-	MetaString ms;
-	ms << std::pair<ui8,ui32>(3,os->ID);
-	cb->setHoverName(objid,&ms);
-}
-void CMines::onHeroVisit(int objid, int heroID)
-{
-	//TODO: this is code for standard mines, no support for abandoned mine (subId==7)
-	DEFOS;
-	if(os->subID==7)
-		return;
-	const CGHeroInstance *h = cb->getHero(heroID);
-	if(h->tempOwner == os->tempOwner)
-		return; //TODO: leaving garrison
-	cb->setOwner(objid,h->tempOwner);
-	MetaString ms;
-	ms << std::pair<ui8,ui32>(9,os->subID) << " " << std::pair<ui8,ui32>(6,23+h->tempOwner);
-	cb->setHoverName(objid,&ms);
-	ms.clear();
-
-	int vv=1; //amount of resource per turn	
-	if (os->subID==0 || os->subID==2)
-		vv++;
-	else if (os->subID==6)
-		vv = 1000;
-
-	InfoWindow iw;
-	iw.text << std::pair<ui8,ui32>(10,os->subID);
-	iw.player = h->tempOwner;
-	iw.components.push_back(Component(2,os->subID,vv,-1));
-	cb->showInfoDialog(&iw);
-}
-std::vector<int> CMines::yourObjects()
-{
-	std::vector<int> ret;
-	ret.push_back(53);
-	return ret;
-}
-void CMines::newTurn ()
-{
-	const CGObjectInstance * obj;
-	for (unsigned i=0;i<ourObjs.size();i++)
-	{
-		obj = cb->getObj(ourObjs[i]);
-		if (obj->tempOwner == NEUTRAL_PLAYER)
-			continue;
-		int vv = 1;
-		if (obj->subID==0 || obj->subID==2)
-			vv++;
-		else if (obj->subID==6)
-			vv = 1000;
-		cb->giveResource(obj->tempOwner,obj->subID,vv);
-	}
-}
-
-CPickable::CPickable(CScriptCallback * CB):CCPPObjectScript(CB) {
-
-};
-
-void CPickable::newObject(int objid)
-{
-	cb->setBlockVis(objid,true);
-
-	MetaString ms;
-	DEFOS;
-	switch (os->ID)
-	{
-	case 79:
-		ms << std::pair<ui8,ui32>(4,os->subID);
-		break;
-	case 5:
-		ms << std::pair<ui8,ui32>(5,os->subID);
-		break;
-	default:
-		ms << std::pair<ui8,ui32>(3,os->ID);
-		break;
-	}
-
-	cb->setHoverName(objid,&ms);
-}
-void CPickable::onHeroVisit(int objid, int heroID)
-{
-	DEFOS;
-	switch(os->ID)
-	{
-	case 5: //artifact
-		{
-			cb->giveHeroArtifact(os->subID,heroID,-2);
-			InfoWindow iw;
-			iw.player = cb->getOwner(heroID);
-			iw.components.push_back(Component(4,os->subID,0,0));
-			iw.text << std::pair<ui8,ui32>(12,os->subID);
-			cb->showInfoDialog(&iw);
-			break;
-		}
-	case 12: //campfire
-		{
-			int val = (rand()%3) + 4, //4 - 6
-				res = rand()%6, 
-				owner = cb->getOwner(heroID);
-			cb->giveResource(owner,res,val); //non-gold resource
-			cb->giveResource(owner,6,val*100);//gold
-			InfoWindow iw;
-			iw.player = owner;
-			iw.components.push_back(Component(2,6,val*100,0));
-			iw.components.push_back(Component(2,res,val,0));
-			iw.text << std::pair<ui8,ui32>(11,23);
-			cb->showInfoDialog(&iw);
-			break;
-		}
-	case 79: //resource
-		{
-			//TODO: handle guards (when battles are finished)
-			CResourceObjInfo * t2 = static_cast<CResourceObjInfo *>(os->info);
-			int val;
-			if(t2->amount)
-				val = t2->amount;
-			else
-			{
-				switch(os->subID)
-				{
-				case 6:
-					val = 500 + (rand()%6)*100;
-					break;
-				case 0: case 2:
-					val = 6 + (rand()%5);
-					break;
-				default:
-					val = 3 + (rand()%3);
-					break;
-				}
-			}
-			if(t2->message.length())
-			{
-				InfoWindow iw;
-				iw.player = cb->getHero(heroID)->tempOwner;
-				iw.text << t2->message;
-				cb->showInfoDialog(&iw);
-			}
-
-			cb->giveResource(cb->getOwner(heroID),os->subID,val);
-
-			ShowInInfobox sii;
-			sii.player = cb->getOwner(heroID);
-			sii.c = Component(2,os->subID,val,0);
-			sii.text << std::pair<ui8,ui32>(11,113);
-			sii.text.replacements.push_back(VLC->objh->restypes[os->subID]);
-			cb->showCompInfo(&sii);
-			break;
-		}
-	case 101: //treasure chest
-		{
-			if (os->subID) //not OH3 treasure chest
-				break; 
-			int wyn = rand()%100, val=0;
-			if (wyn<32) //1k/0.5k
-			{
-				val = 1000;
-			}
-			else if(wyn<64) //1.5k/1k
-			{
-				val = 1500;
-			}
-			else if(wyn<95) //2k/1.5k
-			{
-				val = 2000;
-			}
-			else //random treasure artifact, or (if backapack is full) 1k/0.5k
-			{
-				if (1/*TODO: backpack is full*/)
-				{
-					val = 1000;
-				}
-				else
-				{
-					//TODO: give treasure artifact
-					break;
-				}
-			}
-			SelectionDialog sd;
-			sd.player = cb->getOwner(heroID);
-			sd.text << std::pair<ui8,ui32>(11,146);
-			sd.components.push_back(Component(2,6,val,0));
-			sd.components.push_back(Component(5,0,val-500,0));
-			boost::function<void(ui32)> fun = boost::bind(&CPickable::chosen,this,_1,heroID,val);
-			cb->showSelectionDialog(&sd,fun);
-			break;
-		}
-	}
-	cb->removeObject(objid);
-}
-void CPickable::chosen(ui32 which, int heroid, int val)
-{
-	switch(which)
-	{
-	case 0: //player pick gold
-		cb->giveResource(cb->getOwner(heroid),6,val);
-		break;
-	case 1: //player pick exp
-		cb->changePrimSkill(heroid, 4, val-500);
-		break;
-	default:
-		throw std::string("Unhandled choice");
-	}
-}
-
-std::vector<int> CPickable::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret;
-	ret.push_back(79); //resource
-	ret.push_back(5); //artifact
-	ret.push_back(12); //resource
-	ret.push_back(101); //treasure chest / commander stone
-	return ret;
-}
-//CPickable
-CTownScript::CTownScript(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-void CTownScript::onHeroVisit(int objid, int heroID)
-{
-	DEFOS;
-	if(cb->getOwner(objid)!=cb->getOwner(heroID))
-	{
-		return;
-	}
-	cb->heroVisitCastle(objid,heroID);
-}
-
-void CTownScript::newObject(int objid)
-{
-	MetaString ms;
-	const CGTownInstance * n = cb->getTown(objid);
-	ms << n->name << ", " << n->town->name;
-	cb->setHoverName(objid,&ms);
-}
-
-void CTownScript::onHeroLeave(int objid, int heroID)
-{
-	cb->stopHeroVisitCastle(objid,heroID);
-}
-
-std::vector<int> CTownScript::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret(1);
-	ret.push_back(98); //town
-	return ret;
-}
-//CTownScript
-CHeroScript::CHeroScript(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-void CHeroScript::newObject(int objid)
-{
-	cb->setBlockVis(objid,true);
-	MetaString ms;
-	ms << std::pair<ui8,ui32>(1,15);
-	ms.replacements.push_back(cb->getHero(objid)->name);
-	ms.replacements.push_back(cb->getHero(objid)->type->heroClass->name);
-	cb->setHoverName(objid,&ms);
-}
-
-void CHeroScript::onHeroVisit(int objid, int heroID)
-{
-	//TODO: check for allies
-	const CGHeroInstance *my = cb->getHero(objid), 
-		*vis = cb->getHero(heroID);
-	if(my->tempOwner == vis->tempOwner) //one of allied cases
-	{
-		//exchange
-	}
-	else
-	{
-		cb->startBattle(
-			&vis->army,
-			&my->army,
-			vis->pos,
-			vis,
-			my,
-			0);
-	}
-}
-std::vector<int> CHeroScript::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret;
-	ret.push_back(34); //hero
-	return ret;
-}
-//CHeroScript
-
-CMonsterS::CMonsterS(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-void CMonsterS::newObject(int objid)
-{
-	//os->blockVisit = true;
-	DEFOS;
-	switch(VLC->creh->creatures[os->subID].level)
-	{
-	case 1:
-		cb->setAmount(objid,rand()%31+20);
-		break;
-	case 2:
-		cb->setAmount(objid,rand()%16+15);
-		break;
-	case 3:
-		cb->setAmount(objid,rand()%16+10);
-		break;
-	case 4:
-		cb->setAmount(objid,rand()%11+10);
-		break;
-	case 5:
-		cb->setAmount(objid,rand()%9+8);
-		break;
-	case 6:
-		cb->setAmount(objid,rand()%8+5);
-		break;
-	case 7:
-		cb->setAmount(objid,rand()%7+3);
-		break;
-	case 8:
-		cb->setAmount(objid,rand()%4+2);
-		break;
-	case 9:
-		cb->setAmount(objid,rand()%3+2);
-		break;
-	case 10:
-		cb->setAmount(objid,rand()%3+1);
-		break;
-
-	}
-
-	MetaString ms;
-	int pom = CCreature::getQuantityID(((CCreatureObjInfo*)(os->info))->number);
-	pom = 174 + 3*pom + 1;
-	ms << std::pair<ui8,ui32>(6,pom) << " " << std::pair<ui8,ui32>(7,os->subID);
-	cb->setHoverName(objid,&ms);
-}
-void CMonsterS::onHeroVisit(int objid, int heroID)
-{
-	DEFOS;
-	CCreatureSet set;
-	//TODO: zrobic secik w sposob wyrafinowany
-	set.slots[0] = std::pair<ui32,si32>(os->subID,((CCreatureObjInfo*)(os->info))->number);
-	cb->startBattle(heroID,set,os->pos,boost::bind(&CMonsterS::endBattleWith,this,os,_1));
-}
-std::vector<int> CMonsterS::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret;
-	ret.push_back(54); //monster
-	return ret;
-}
-
-void CMonsterS::endBattleWith(const CGObjectInstance *monster, BattleResult *result )
-{
-	if(result->winner==0)
-	{
-		cb->removeObject(monster->id);
-	}
-	else
-	{
-		int killedAmount=0;
-		for(std::set<std::pair<ui32,si32> >::iterator i=result->casualties[1].begin(); i!=result->casualties[1].end(); i++)
-			if(i->first == monster->subID)
-				killedAmount += i->second;
-		cb->setAmount(monster->id,((CCreatureObjInfo*)(monster->info))->number - killedAmount);
-	}
-}
-//CMonsterS
-
-
-CCreatureGen::CCreatureGen(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-void CCreatureGen::newObject(int objid)
-{
-	DEFOS;
-	amount[objid] = VLC->creh->creatures[VLC->objh->cregens[os->subID]].growth;
-	MetaString ms;
-	ms << std::pair<ui8,ui32>(8,os->subID);
-	cb->setHoverName(objid,&ms);
-}
-
-void CCreatureGen::onHeroVisit(int objid, int heroID)
-{
-}
-
-std::vector<int> CCreatureGen::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret;
-	ret.push_back(17); //cregen1
-	return ret;
-}
-//CCreatureGen
-CTeleports::CTeleports(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-void CTeleports::newObject(int objid)
-{
-	DEFOS;
-	objs[os->ID][os->subID].push_back(objid);
-}
-
-void CTeleports::onHeroVisit(int objid, int heroID)
-{
-	DEFOS;
-	int destinationid=-1;
-	switch(os->ID)
-	{
-	case 43: //one way - find correspong exit monolith
-		if(vstd::contains(objs,44) && vstd::contains(objs[44],os->subID) && objs[44][os->subID].size())
-			destinationid = objs[44][os->subID][rand()%objs[44][os->subID].size()];
-		else
-			tlog2 << "Cannot find corresponding exit monolith for "<<objid << std::endl;
-		break;
-	case 45: //two way monolith - pick any other one
-		if(vstd::contains(objs,45) && vstd::contains(objs[45],os->subID) && objs[45][os->subID].size()>1)
-			while ((destinationid = objs[45][os->subID][rand()%objs[45][os->subID].size()])==objid);
-		else
-			tlog2 << "Cannot find corresponding exit monolith for "<<objid << std::endl;
-		break;
-	case 103: //find nearest subterranean gate on the other level
-		{
-			std::pair<int,double> best(-1,150000); //pair<id,dist>
-			for(int i=0; i<objs[103][0].size(); i++)
-			{
-				if(cb->getObj(objs[103][0][i])->pos.z == os->pos.z) continue; //gates on our level are not interesting
-				double hlp = cb->getObj(objs[103][0][i])->pos.dist2d(os->pos);
-				if(hlp<best.second)
-				{
-					best.first = objs[103][0][i];
-					best.second = hlp;
-				}
-			}
-			if(best.first<0)
-				return;
-			else 
-				destinationid = best.first;
-			break;
-		}
-	}
-	if(destinationid < 0)
-	{
-		tlog2 << "Cannot find exit... :( \n";
-		return;
-	}
-	cb->moveHero(heroID,(os->ID!=103)
-		?(CGHeroInstance::convertPosition(cb->getObj(destinationid)->pos,true))
-		:(cb->getObj(destinationid)->pos),
-	true);
-}
-
-std::vector<int> CTeleports::yourObjects() //returns IDs of objects which are handled by script
-{
-	std::vector<int> ret;
-	ret.push_back(43); 
-	ret.push_back(44); 
-	ret.push_back(45); 
-	ret.push_back(103); 
-	return ret;
-}
-//CTeleports
-CCPPObjectScript::CCPPObjectScript(CScriptCallback * CB) {
-    cb=CB;
-};
-
-CVisitableOPH::CVisitableOPH(CScriptCallback * CB):CCPPObjectScript(CB) {//:CCPPObjectScript(CB) {
-};
-
-CVisitableOPW::CVisitableOPW(CScriptCallback * CB):CCPPObjectScript(CB) {
-};
-
-CMines::CMines(CScriptCallback * CB):CCPPObjectScript(CB) {
-};

+ 0 - 206
CLua.h

@@ -1,206 +0,0 @@
-#pragma once
-#include "global.h"
-#include "client/FunctionList.h"
-
-#ifndef _MSC_VER
-extern "C" {
-#endif
-
-//#include "lstate.h"
-
-#ifndef _MSC_VER
-}
-#endif
-
-#include <set>
-#include <map>
-class CLua;
-struct SDL_Surface;
-class CGObjectInstance;
-class CGameInfo;
-class CGHeroInstance;
-class CScriptCallback;
-class SComponent;
-class CSelectableComponent;
-class CGameState;
-struct Mapa;
-struct lua_State;
-struct BattleResult;
-enum ESLan{UNDEF=-1,CPP,ERM,LUA};
-
-
-class CObjectScript
-{
-public:
-        int owner, language;
-	std::string filename;
-
-	int getOwner(){return owner;} //255 - neutral /  254 - not flaggable
-	CObjectScript();
-	virtual ~CObjectScript();
-
-
-	//functions to be called in script
-	//virtual void init(){}; //called when game is ready
-	virtual void newObject(int objid);
-	virtual void onHeroVisit(int objid, int heroID);
-	virtual void onHeroLeave(int objid, int heroID);
-	virtual std::string hoverText(int objid);
-	virtual void newTurn ();
-
-
-	//TODO: implement functions below:
-	virtual void equipArtefact(int HID, int AID, int slot, bool putOn); //putOn==0 means that artifact is taken off
-	virtual void battleStart(int phase); //phase==0 - very start, before initialization of battle; phase==1 - just before battle starts
-	virtual void battleNewTurn (int turn); //turn==-1 is for tactic stage
-	//virtual void battleAction (int type,int destination, int stack, int owner, int){};
-	//virtual void mouseClick (down,left,screen?, pos??){};
-	virtual void heroLevelUp (int HID); //add possibility of changing available sec. skills
-
-};
-class CScript
-{
-public:
-	CScript();
-	virtual ~CScript();
-};
-class CLua :public CScript
-{
-protected:
-	lua_State * is; /// tez niebezpieczne!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! (ale chwilowo okielznane)
-	bool opened;
-public:
-	CLua(std::string initpath);
-	void open(std::string initpath);
-	void registerCLuaCallback();
-	CLua();
-	virtual ~CLua();
-
-	void findF(std::string fname);
-	void findF2(std::string fname);
-	void findFS(std::string fname);
-
-
-	friend class CGameState;
-};
-
-class CLuaObjectScript : public CLua, public CObjectScript
-{
-public:
-	CLuaObjectScript(std::string filename);
-	virtual ~CLuaObjectScript();
-	static std::string genFN(std::string base, int ID);
-
-	void init();
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-};
-class CCPPObjectScript: public CObjectScript
-{
-public:
-	CScriptCallback * cb;
-	CCPPObjectScript(CScriptCallback * CB);//{cb=CB;};
-	virtual std::vector<int> yourObjects()=0; //returns IDs of objects which are handled by script
-	template <typename Handler> void serialize(Handler &h, const int version)
-	{
-		//TODO: write
-	}
-};
-class CVisitableOPH : public CCPPObjectScript  //once per hero
-{
-public:
-	CVisitableOPH(CScriptCallback * CB);//{};
-	std::map<int, int> typeOfTree; //0 - level for free; 1 - 2000 gold; 2 - 10 gems
-	std::map<int,std::set<int> > visitors;
-
-	void onNAHeroVisit(int objid, int heroID, bool alreadyVisited);
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	void treeSelected(int objid, int heroID, int resType, int resVal, int expVal, ui32 result);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-};
-
-class CVisitableOPW : public CCPPObjectScript  //once per week
-{
-public:
-	CVisitableOPW(CScriptCallback * CB);
-	std::map<int,bool> visited;
-	void onNAHeroVisit(int objid, int heroID, bool alreadyVisited);
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-	void newTurn ();
-};
-
-class CMines : public CCPPObjectScript  //flaggable, and giving resource at each day
-{
-public:
-	CMines(CScriptCallback * CB);
-
-	std::vector<int> ourObjs;
-
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-	void newTurn ();
-};
-
-class CPickable : public CCPPObjectScript //pickable - resources, artifacts, etc
-{
-public:
-	CPickable(CScriptCallback * CB);//:CCPPObjectScript(CB);
-	void chosen(ui32 which, int heroid, int val); //val - value of treasure in gold
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-};
-
-class CTownScript : public CCPPObjectScript  //pickable - resources, artifacts, etc
-{
-public:
-	CTownScript(CScriptCallback * CB);//:CCPPObjectScript(CB){};
-	void onHeroVisit(int objid, int heroID);
-	void onHeroLeave(int objid, int heroID);
-	void newObject(int objid);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-};
-
-class CHeroScript : public CCPPObjectScript
-{
-public:
-	CHeroScript(CScriptCallback * CB);//:CCPPObjectScript(CB){};
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-};
-
-class CMonsterS : public CCPPObjectScript
-{
-public:
-	CMonsterS(CScriptCallback * CB);//:CCPPObjectScript(CB){};
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-	void endBattleWith(const CGObjectInstance *monster, BattleResult *result);
-};
-
-class CCreatureGen : public CCPPObjectScript
-{
-public:
-	std::map<int, int> amount; //amount of creatures in each dwelling
-	CCreatureGen(CScriptCallback * CB);//:CCPPObjectScript(CB){};
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-};
-
-class CTeleports : public CCPPObjectScript
-{
-public:
-	std::map<int,std::map<int, std::vector<int> > > objs; //map[ID][subID] => vector of ids
-
-	void newObject(int objid);
-	void onHeroVisit(int objid, int heroID);
-	std::vector<int> yourObjects(); //returns IDs of objects which are handled by script
-	CTeleports(CScriptCallback * CB);//:CCPPObjectScript(CB){};
-};

+ 8 - 8
CPlayerInterface.cpp

@@ -85,17 +85,17 @@ void CGarrisonSlot::hover (bool on)
 			{
 				if(owner->highlighted == this)
 				{
-					temp = CGI->townh->tcommands[4];
+					temp = CGI->generaltexth->tcommands[4];
 					boost::algorithm::replace_first(temp,"%s",creature->nameSing);
 				}
 				else if (owner->highlighted->creature == creature)
 				{
-					temp = CGI->townh->tcommands[2];
+					temp = CGI->generaltexth->tcommands[2];
 					boost::algorithm::replace_first(temp,"%s",creature->nameSing);
 				}
 				else if (owner->highlighted->creature)
 				{
-					temp = CGI->townh->tcommands[7];
+					temp = CGI->generaltexth->tcommands[7];
 					boost::algorithm::replace_first(temp,"%s",owner->highlighted->creature->nameSing);
 					boost::algorithm::replace_first(temp,"%s",creature->nameSing);
 				}
@@ -110,11 +110,11 @@ void CGarrisonSlot::hover (bool on)
 			{
 				if(upg)
 				{
-					temp = CGI->townh->tcommands[32];
+					temp = CGI->generaltexth->tcommands[32];
 				}
 				else
 				{
-					temp = CGI->townh->tcommands[12];
+					temp = CGI->generaltexth->tcommands[12];
 				}
 				boost::algorithm::replace_first(temp,"%s",creature->nameSing);
 			};
@@ -129,17 +129,17 @@ void CGarrisonSlot::hover (bool on)
 				  && owner->highlighted->upg != upg	//we're moving it to the other garrison
 				  )
 				{
-					temp = CGI->townh->tcommands[5]; //cannot move last stack!
+					temp = CGI->generaltexth->tcommands[5]; //cannot move last stack!
 				}
 				else
 				{
-					temp = CGI->townh->tcommands[6];
+					temp = CGI->generaltexth->tcommands[6];
 					boost::algorithm::replace_first(temp,"%s",owner->highlighted->creature->nameSing);
 				}
 			}
 			else
 			{
-				temp = CGI->townh->tcommands[11];
+				temp = CGI->generaltexth->tcommands[11];
 			}
 		}
 		LOCPLINT->statusbar->print(temp);

+ 1 - 1
client/Client.cpp

@@ -476,7 +476,7 @@ void CClient::process(int what)
 			*serv >> shn;
 			tlog5 << "Setting a name of " << shn.id <<" object to "<< toString(shn.name) <<std::endl;
 			gs->mx->lock();
-			gs->map->objects[shn.id]->hoverName = toString(shn.name);
+			//gs->map->objects[shn.id]->hoverName = toString(shn.name);
 			gs->mx->unlock();
 			break;
 		}

+ 32 - 66
hch/CBuildingHandler.cpp

@@ -1,17 +1,12 @@
 #define VCMI_DLL
 #include "../stdafx.h"
 #include "CBuildingHandler.h"
+#include "CGeneralTextHandler.h"
 #include "CLodHandler.h"
+#include "../lib/VCMI_Lib.h"
 #include <sstream>
 #include <fstream>
 extern CLodHandler * bitmaph;
-std::string readTo(std::string &in, unsigned int &it, char end)
-{
-	int pom = it;
-	int last = in.find_first_of(end,it);
-	it+=(1+last-it);
-	return in.substr(pom,last-pom);
-}
 unsigned int readNr(std::string &in, unsigned int &it)
 {
 	int last=it;
@@ -35,7 +30,8 @@ CBuilding * readBg(std::string &buf, unsigned int& it)
 	nb->resources.resize(RESOURCE_QUANTITY);
 	for(int res=0;res<7;res++)
 		nb->resources[res] = readNr(buf,it);
-	nb->refName = readTo(buf,it,'\n');
+	/*nb->refName = */readTo(buf,it,'\n');
+	//reference name is ommitted, it's seems to be useless
 	return nb;
 }
 void CBuildingHandler::loadBuildings()
@@ -53,6 +49,8 @@ void CBuildingHandler::loadBuildings()
 		for(int bg = 0; bg<9; bg++)
 		{
 			CBuilding *nb = readBg(buf,it);
+			nb->tid = i;
+			nb->bid = bg+17;
 			buildings[i][bg+17] = nb;
 		}
 	}
@@ -63,7 +61,11 @@ void CBuildingHandler::loadBuildings()
 	{
 		CBuilding *nb = readBg(buf,it);
 		for(int f=0;f<F_NUMBER;f++)
+		{
 			buildings[f][bg] = new CBuilding(*nb);
+			buildings[f][bg]->tid = f;
+			buildings[f][bg]->bid = bg;
+		}
 		delete nb;
 	}
 
@@ -76,69 +78,13 @@ void CBuildingHandler::loadBuildings()
 		for(int bg = 0; bg<14; bg++)
 		{
 			CBuilding *nb = readBg(buf,it);
+			nb->tid = i;
+			nb->bid = bg+30;
 			buildings[i][bg+30] = nb;
 		}
 	}
 	/////done reading BUILDING.TXT*****************************
 
-	buf = bitmaph->getTextFile("BLDGNEUT.TXT");
-	andame = buf.size(), it=0;
-
-	for(int b=0;b<15;b++)
-	{
-		std::string name = readTo(buf,it,'\t'),
-			description = readTo(buf,it,'\n');
-		for(int fi=0;fi<F_NUMBER;fi++)
-		{
-			buildings[fi][b]->name = name;
-			buildings[fi][b]->description = description;
-		}
-	}
-	temp = readTo(buf,it,'\n');temp = readTo(buf,it,'\n');temp = readTo(buf,it,'\n');//silo,blacksmith,moat - useless???
-	//shipyard with the ship
-	std::string name = readTo(buf,it,'\t'),
-		description = readTo(buf,it,'\n');
-	for(int fi=0;fi<F_NUMBER;fi++)
-	{
-		buildings[fi][20]->name = name;
-		buildings[fi][20]->description = description;
-	}
-
-	for(int fi=0;fi<F_NUMBER;fi++)
-	{
-		buildings[fi][16]->name = readTo(buf,it,'\t'),
-		buildings[fi][16]->description = readTo(buf,it,'\n');
-	}
-	/////done reading "BLDGNEUT.TXT"******************************
-
-	buf = bitmaph->getTextFile("BLDGSPEC.TXT");
-	andame = buf.size(), it=0;
-	for(int f=0;f<F_NUMBER;f++)
-	{
-		for(int b=0;b<9;b++)
-		{
-			buildings[f][17+b]->name = readTo(buf,it,'\t');
-			buildings[f][17+b]->description = readTo(buf,it,'\n');
-		}
-		buildings[f][26] = new CBuilding();//grail
-		buildings[f][26]->name = readTo(buf,it,'\t');
-		buildings[f][26]->description = readTo(buf,it,'\n');
-		buildings[f][15]->name = readTo(buf,it,'\t'); //resource silo
-		buildings[f][15]->description = readTo(buf,it,'\n');//resource silo
-	}
-	/////done reading BLDGSPEC.TXT*********************************
-
-	buf = bitmaph->getTextFile("DWELLING.TXT");
-	andame = buf.size(), it=0;
-	for(int f=0;f<F_NUMBER;f++)
-	{
-		for(int b=0;b<14;b++)
-		{
-			buildings[f][30+b]->name = readTo(buf,it,'\t');
-			buildings[f][30+b]->description = readTo(buf,it,'\n');
-		}
-	}
-
 	char line[100]; //bufor
 	std::ifstream ofs("config/hall.txt");
 	int castles;
@@ -183,3 +129,23 @@ void CBuildingHandler::loadBuildings()
 	}
 
 }
+
+const std::string & CBuilding::Name()
+{
+	if(name.length())
+		return name;
+	else if(vstd::contains(VLC->generaltexth->buildings,tid) && vstd::contains(VLC->generaltexth->buildings[tid],bid))
+		return VLC->generaltexth->buildings[tid][bid].first;
+	tlog2 << "Warning: Cannot find name text for building " << bid << "for " << tid << "town.\n";
+	return "";
+}
+
+const std::string & CBuilding::Description()
+{
+	if(description.length())
+		return description;
+	else if(vstd::contains(VLC->generaltexth->buildings,tid) && vstd::contains(VLC->generaltexth->buildings[tid],bid))
+		return VLC->generaltexth->buildings[tid][bid].second;
+	tlog2 << "Warning: Cannot find description text for building " << bid << "for " << tid << "town.\n";
+	return "";
+}

+ 16 - 4
hch/CBuildingHandler.h

@@ -7,12 +7,18 @@
 class DLL_EXPORT CBuilding //a typical building encountered in every castle ;]
 {
 public:
-	std::string name;
-	std::string refName; //reference name, for identification
+	int tid, bid; //town ID and structure ID
 	std::vector<int> resources;
+	std::string name;
 	std::string description;
-	//EbuildingType type; //type of building (occures in many castles or is specific for one castle)
-	//bool isDwelling; //true, if this building is a dwelling
+
+	const std::string &Name();
+	const std::string &Description();
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & tid & bid & resources & name & description;
+	}
 };
 
 class DLL_EXPORT CBuildingHandler
@@ -20,7 +26,13 @@ class DLL_EXPORT CBuildingHandler
 public:
 	std::map<int, std::map<int, CBuilding*> > buildings; ///< first int is the castle ID, second the building ID (in ERM-U format)
 	std::map<int, std::pair<std::string,std::vector< std::vector< std::vector<int> > > > > hall; //map<castle ID, pair<hall bg name, std::vector< std::vector<building id> >[5]> - external vector is the vector of buildings in the row, internal is the list of buildings for the specific slot
+
 	void loadBuildings(); //main loader
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & buildings & hall;
+	}
 };
 
 #endif //CBUILDINGHANDLER_H

+ 35 - 7
hch/CCreatureHandler.h

@@ -12,18 +12,18 @@ class DLL_EXPORT CCreature
 {
 public:
 	std::string namePl, nameSing, nameRef; //name in singular and plural form; and reference name
-	std::vector<int> cost; //cost[res_id] - amount of that resource
-	std::set<int> upgrades; // IDs of creatures to which this creature can be upgraded
-	int fightValue, AIValue, growth, hordeGrowth, hitPoints, speed, attack, defence, shots, spells;
-	int damageMin, damageMax;
-	int ammMin, ammMax;
-	int level; // 0 - unknown
+	std::vector<ui32> cost; //cost[res_id] - amount of that resource
+	std::set<ui32> upgrades; // IDs of creatures to which this creature can be upgraded
+	ui32 fightValue, AIValue, growth, hordeGrowth, hitPoints, speed, attack, defence, shots, spells;
+	ui32 damageMin, damageMax;
+	ui32 ammMin, ammMax;
+	ui8 level; // 0 - unknown
 	std::string abilityText; //description of abilities
 	std::string abilityRefs; //references to abilities, in textformat
 	std::string animDefName;
 	ui32 idNumber;
 	std::set<EAbilities> abilities;
-	int faction; //-1 = neutral
+	si8 faction; //-1 = neutral
 
 	///animation info
 	float timeBetweenFidgets, walkAnimationTime, attackAnimationTime, flightAnimationDistance;
@@ -37,6 +37,20 @@ public:
 	bool isShooting() const; //returns true if unit can shoot
 	si32 maxAmount(const std::vector<si32> &res) const; //how many creatures can be bought
 	static int getQuantityID(const int & quantity); //0 - a few, 1 - several, 2 - pack, 3 - lots, 4 - horde, 5 - throng, 6 - swarm, 7 - zounds, 8 - legion
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & namePl & nameSing & nameRef
+			& cost & upgrades 
+			& fightValue & AIValue & growth & hordeGrowth & hitPoints & speed & attack & defence & shots & spells
+			& damageMin & damageMax & ammMin & ammMax & level
+			& abilityText & abilityRefs & animDefName
+			& idNumber & abilities & faction
+
+			& timeBetweenFidgets & walkAnimationTime & attackAnimationTime & flightAnimationDistance
+			& upperRightMissleOffsetX & rightMissleOffsetX & lowerRightMissleOffsetX & upperRightMissleOffsetY & rightMissleOffsetY & lowerRightMissleOffsetY
+			& missleFrameAngles & troopCountLocationOffset & attackClimaxFrame;
+	}
 };
 
 
@@ -53,5 +67,19 @@ public:
 	void loadAnimationInfo();
 	void loadUnitAnimInfo(CCreature & unit, std::string & src, int & i);
 	CCreatureHandler();
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		//TODO: should be optimized, not all these informations needs to be serialized (same for ccreature)
+		h & notUsedMonsters & creatures & nameToID & idToProjectile & idToProjectileSpin;
+
+		if(!h.saving)
+		{
+			for (int i=0; i<creatures.size(); i++) //recreate levelCreatures map
+			{
+				levelCreatures[creatures[i].level].push_back(&creatures[i]);
+			}
+		}
+	}
 };
 #endif //CCREATUREHANDLER_H

+ 1 - 1
hch/CDefHandler.cpp

@@ -256,7 +256,7 @@ SDL_Surface * CDefHandler::getSprite (int SIndex, unsigned char * FDef, BMPPalet
 	unsigned char SegmentType, SegmentLength;//, BL, BR; //TODO use me
 
 	i=BaseOffset=SEntries[SIndex].offset;
-//	int prSize=readNormalNr(i,4,FDef);i+=4; //TODO use me
+	int prSize=readNormalNr(i,4,FDef);i+=4; //TODO use me
 	int defType2 = readNormalNr(i,4,FDef);i+=4;
 	FullWidth = readNormalNr(i,4,FDef);i+=4;
 	FullHeight = readNormalNr(i,4,FDef);i+=4;

+ 12 - 0
hch/CDefObjInfoHandler.h

@@ -41,6 +41,18 @@ public:
 	std::map<int,CGDefInfo*> castles;
 	//std::vector<DefObjInfo> objs;
 	void load();
+
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & gobjs;
+
+		if(!h.saving) //recrete castles map
+			for(std::map<int,std::map<int,CGDefInfo*> >::iterator i=gobjs.begin(); i!=gobjs.end(); i++)
+				for(std::map<int,CGDefInfo*>::iterator j=i->second.begin(); j!=i->second.end(); j++)
+					if(j->second->id == 98)
+						castles[j->second->subid]=j->second;
+	}
 };
 
 #endif //COBJINFOECTHANDLER_H

+ 103 - 0
hch/CGeneralTextHandler.cpp

@@ -6,7 +6,15 @@
 #include <boost/algorithm/string.hpp>
 #include <boost/algorithm/string/replace.hpp>
 #include <fstream>
+#include <sstream>
 
+std::string readTo(std::string &in, unsigned int &it, char end)
+{
+	int pom = it;
+	int last = in.find_first_of(end,it);
+	it+=(1+last-it);
+	return in.substr(pom,last-pom);
+}
 void CGeneralTextHandler::load()
 {
 	std::string buf = bitmaph->getTextFile("GENRLTXT.TXT"), tmp;
@@ -165,4 +173,99 @@ void CGeneralTextHandler::loadTexts()
 	{
 		loadToIt(hTxts[iii].biography,buf,i,3);
 	}
+
+	unsigned it;
+	buf = bitmaph->getTextFile("BLDGNEUT.TXT");
+	andame = buf.size(), it=0;
+
+	for(int b=0;b<15;b++)
+	{
+		std::string name = readTo(buf,it,'\t'),
+			description = readTo(buf,it,'\n');
+		for(int fi=0;fi<F_NUMBER;fi++)
+		{
+			buildings[fi][b].first = name;
+			buildings[fi][b].second = description;
+		}
+	}
+	buf1 = readTo(buf,it,'\n');buf1 = readTo(buf,it,'\n');buf1 = readTo(buf,it,'\n');//silo,blacksmith,moat - useless???
+	//shipyard with the ship
+	std::string name = readTo(buf,it,'\t'),
+		description = readTo(buf,it,'\n');
+	for(int fi=0;fi<F_NUMBER;fi++)
+	{
+		buildings[fi][20].first = name;
+		buildings[fi][20].second = description;
+	}
+
+	for(int fi=0;fi<F_NUMBER;fi++)
+	{
+		buildings[fi][16].first = readTo(buf,it,'\t'),
+			buildings[fi][16].second = readTo(buf,it,'\n');
+	}
+	/////done reading "BLDGNEUT.TXT"******************************
+
+	buf = bitmaph->getTextFile("BLDGSPEC.TXT");
+	andame = buf.size(), it=0;
+	for(int f=0;f<F_NUMBER;f++)
+	{
+		for(int b=0;b<9;b++)
+		{
+			buildings[f][17+b].first = readTo(buf,it,'\t');
+			buildings[f][17+b].second = readTo(buf,it,'\n');
+		}
+		buildings[f][26].first = readTo(buf,it,'\t');
+		buildings[f][26].second = readTo(buf,it,'\n');
+		buildings[f][15].first = readTo(buf,it,'\t'); //resource silo
+		buildings[f][15].second = readTo(buf,it,'\n');//resource silo
+	}
+	/////done reading BLDGSPEC.TXT*********************************
+
+	buf = bitmaph->getTextFile("DWELLING.TXT");
+	andame = buf.size(), it=0;
+	for(int f=0;f<F_NUMBER;f++)
+	{
+		for(int b=0;b<14;b++)
+		{
+			buildings[f][30+b].first = readTo(buf,it,'\t');
+			buildings[f][30+b].second = readTo(buf,it,'\n');
+		}
+	}
+
+	buf = bitmaph->getTextFile("TCOMMAND.TXT");
+	itr=0;
+	while(itr<buf.length()-1)
+	{
+		std::string tmp;
+		loadToIt(tmp, buf, itr, 3);
+		tcommands.push_back(tmp);
+	}
+
+	buf = bitmaph->getTextFile("HALLINFO.TXT");
+	itr=0;
+	while(itr<buf.length()-1)
+	{
+		std::string tmp;
+		loadToIt(tmp, buf, itr, 3);
+		hcommands.push_back(tmp);
+	}
+
+	std::istringstream ins, names;
+	ins.str(bitmaph->getTextFile("TOWNTYPE.TXT"));
+	names.str(bitmaph->getTextFile("TOWNNAME.TXT"));
+	int si=0;
+	char bufname[75];
+	while (!ins.eof())
+	{
+		ins.getline(bufname,50);
+		townTypes.push_back(std::string(bufname).substr(0,strlen(bufname)-1));
+		townNames.resize(si+1);
+
+		for (int i=0; i<NAMES_PER_TOWN; i++)
+		{
+			names.getline(bufname,50);
+			townNames[si].push_back(std::string(bufname).substr(0,strlen(bufname)-1));
+		}
+		si++;
+	}
 }

+ 9 - 0
hch/CGeneralTextHandler.h

@@ -4,6 +4,7 @@
 #include <string>
 #include <vector>
 DLL_EXPORT void loadToIt(std::string &dest, std::string &src, int &iter, int mode);
+std::string readTo(std::string &in, unsigned int &it, char end);
 class DLL_EXPORT CGeneralTextHandler //Handles general texts
 {
 public:
@@ -21,10 +22,18 @@ public:
 	std::vector<std::string> primarySkillNames;
 	std::vector<std::string> jktexts;
 	std::vector<std::string> heroscrn;
+
+	//artifacts
 	std::vector<std::string> artifEvents;
 	std::vector<std::string> artifNames;
 	std::vector<std::string> artifDescriptions;
 
+	//towns
+	std::vector<std::string> tcommands, hcommands; //texts for town screen and town hall screen
+	std::vector<std::vector<std::string> > townNames; //[type id] => vec of names of instances
+	std::vector<std::string> townTypes; //castle, rampart, tower, etc
+	std::map<int, std::map<int, std::pair<std::string, std::string> > > buildings; //map[town id][building id] => pair<name, description>
+
 	std::vector<std::pair<std::string,std::string> > zelp;
 	std::string lossCondtions[4];
 	std::string victoryConditions[14];

+ 486 - 177
hch/CObjectHandler.cpp

@@ -7,15 +7,40 @@
 #include "CDefObjInfoHandler.h"
 #include "CHeroHandler.h"
 #include "CSpellHandler.h"
+#include <boost/bind.hpp>
 #include <boost/algorithm/string/replace.hpp>
 #include <boost/random/linear_congruential.hpp>
 #include "CTownHandler.h"
 #include "CArtHandler.h"
 #include "../lib/VCMI_Lib.h"
+#include "../lib/IGameCallback.h"
+#include "../CGameState.h"
+#include "../lib/NetPacks.h"
+
+IGameCallback * IObjectInterface::cb = NULL;
 DLL_EXPORT void loadToIt(std::string &dest, std::string &src, int &iter, int mode);
 extern CLodHandler * bitmaph;
 extern boost::rand48 ran;
 
+
+void IObjectInterface::onHeroVisit(const CGHeroInstance * h) 
+{};
+
+void IObjectInterface::onHeroLeave(const CGHeroInstance * h) 
+{};
+
+void IObjectInterface::newTurn () 
+{};
+
+IObjectInterface::~IObjectInterface()
+{}
+
+IObjectInterface::IObjectInterface()
+{}
+
+void IObjectInterface::initObj()
+{}
+
 void CObjectHandler::loadObjects()
 {
 	VLC->objh = this;
@@ -110,11 +135,6 @@ void CObjectHandler::loadObjects()
 	}
 	tlog5 << "\t\tDone loading objects!\n";
 }
-
-bool CGObjectInstance::isHero() const
-{
-	return false;
-}
 int CGObjectInstance::getOwner() const
 {
 	//if (state)
@@ -123,6 +143,58 @@ int CGObjectInstance::getOwner() const
 		return tempOwner; //won't have owner
 }
 
+CGObjectInstance::CGObjectInstance(): animPhaseShift(rand()%0xff)
+{
+	pos = int3(-1,-1,-1);
+	//std::cout << "Tworze obiekt "<<this<<std::endl;
+	//state = new CLuaObjectScript();
+	ID = subID = id = -1;
+	defInfo = NULL;
+	state = NULL;
+	info = NULL;
+	tempOwner = 254;
+	blockVisit = false;
+}
+CGObjectInstance::~CGObjectInstance()
+{
+	//std::cout << "Usuwam obiekt "<<this<<std::endl;
+	//if (state)
+	//	delete state;
+	//state=NULL;
+}
+CGObjectInstance::CGObjectInstance(const CGObjectInstance & right)
+{
+	pos = right.pos;
+	ID = right.ID;
+	subID = right.subID;
+	id	= right.id;
+	defInfo = right.defInfo;
+	info = right.info;
+	blockVisit = right.blockVisit;
+	//state = new CLuaObjectScript(right.state->);
+	//*state = *right.state;
+	//state = right.state;
+	tempOwner = right.tempOwner;
+}
+CGObjectInstance& CGObjectInstance::operator=(const CGObjectInstance & right)
+{
+	pos = right.pos;
+	ID = right.ID;
+	subID = right.subID;
+	id	= right.id;
+	defInfo = right.defInfo;
+	info = right.info;
+	blockVisit = right.blockVisit;
+	//state = new CLuaObjectScript();
+	//*state = *right.state;
+	tempOwner = right.tempOwner;
+	return *this;
+}
+
+const std::string & CGObjectInstance::getHoverText() const
+{
+	return hoverName;
+}
 void CGObjectInstance::setOwner(int ow)
 {
 	//if (state)
@@ -177,11 +249,26 @@ bool CGObjectInstance::operator<(const CGObjectInstance & cmp) const  //screen p
 	return false;
 }
 
+void CGObjectInstance::initObj()
+{
+}
 
-bool CGHeroInstance::isHero() const
+int lowestSpeed(const CGHeroInstance * chi)
 {
-	return true;
+	if(!chi->army.slots.size())
+	{
+		tlog1 << "Error! Hero " << chi->id << " ("<<chi->name<<") has no army!\n";
+		return 20;
+	}
+	std::map<si32,std::pair<ui32,si32> >::const_iterator i = chi->army.slots.begin();
+	ui32 ret = VLC->creh->creatures[(*i++).second.first].speed;
+	for (;i!=chi->army.slots.end();i++)
+	{
+		ret = std::min(ret,VLC->creh->creatures[(*i).second.first].speed);
+	}
+	return ret;
 }
+
 unsigned int CGHeroInstance::getTileCost(const EterrainType & ttype, const Eroad & rdtype, const Eriver & rvtype) const
 {
 	unsigned int ret = type->heroClass->terrCosts[ttype];
@@ -202,9 +289,9 @@ unsigned int CGHeroInstance::getTileCost(const EterrainType & ttype, const Eroad
 			if(ret>150)
 				ret = 150;
 			break;
-                default:
-                    //TODO do something nasty here throw maybe? or some def value asing
-                    break;
+        default:
+            //TODO do something nasty here throw maybe? or some def value asing
+            break;
 		}
 		break;
 	case 2: //advanced
@@ -219,17 +306,17 @@ unsigned int CGHeroInstance::getTileCost(const EterrainType & ttype, const Eroad
 			if(ret>125)
 				ret = 125;
 			break;
-                default:
-                        //TODO look up
-                    break;
+        default:
+            //TODO look up
+            break;
 		}
 		break;
 	case 3: //expert
 		ret = 100;
 		break;
-        default:
-            //TODO look up
-            break;
+    default:
+        //TODO look up
+        break;
 	}
 
 	//calculating road influence
@@ -244,19 +331,19 @@ unsigned int CGHeroInstance::getTileCost(const EterrainType & ttype, const Eroad
 	case cobblestoneRoad:
 		ret*=0.5;
 		break;
-        default:
-            //TODO killllll me
-            break;
+    default:
+        //TODO killllll me
+        break;
 	}
 	return ret;
 }
-unsigned int CGHeroInstance::getLowestCreatureSpeed()
+unsigned int CGHeroInstance::getLowestCreatureSpeed() const
 {
 	unsigned int sl = 100;
 	for(size_t h=0; h < army.slots.size(); ++h)
 	{
-		if(VLC->creh->creatures[army.slots[h].first].speed<sl)
-			sl = VLC->creh->creatures[army.slots[h].first].speed;
+		if(VLC->creh->creatures[army.slots.find(h)->first].speed<sl)
+			sl = VLC->creh->creatures[army.slots.find(h)->first].speed;
 	}
 	return sl;
 }
@@ -332,22 +419,6 @@ int CGHeroInstance::getSecSkillLevel(const int & ID) const
 			return secSkills[i].second;
 	return 0;
 }
-int lowestSpeed(const CGHeroInstance * chi)
-{
-	if(!chi->army.slots.size())
-	{
-		tlog1 << "Error! Hero " << chi->id << " ("<<chi->name<<") has no army!\n";
-		return 20;
-	}
-	std::map<si32,std::pair<ui32,si32> >::const_iterator i = chi->army.slots.begin();
-	int ret = VLC->creh->creatures[(*i++).second.first].speed;
-	for (;i!=chi->army.slots.end();i++)
-	{
-		ret = std::min(ret,VLC->creh->creatures[(*i).second.first].speed);
-	}
-	return ret;
-}
-
 int CGHeroInstance::maxMovePoints(bool onLand) const
 {
 	int ret = 1270+70*lowestSpeed(this);
@@ -456,6 +527,149 @@ int CGHeroInstance::getSpellSecLevel(int spell) const
 	return bestslvl;
 }
 
+CGHeroInstance::CGHeroInstance()
+{
+	ID = 34;
+	tacticFormationEnabled = inTownGarrison = false;
+	mana = movement = portrait = level = -1;
+	isStanding = true;
+	moveDir = 4;
+	exp = 0xffffffff;
+	visitedTown = NULL;
+	type = NULL;
+	secSkills.push_back(std::make_pair(-1, -1));
+}
+
+void CGHeroInstance::initHero(int SUBID)
+{
+	subID = SUBID;
+	initHero();
+}
+
+void CGHeroInstance::initHero()
+{
+	if(!defInfo)
+	{
+		defInfo = new CGDefInfo();
+		defInfo->id = 34;
+		defInfo->subid = subID;
+		defInfo->printPriority = 0;
+		defInfo->visitDir = 0xff;
+	}
+	if(!type)
+		type = VLC->heroh->heroes[subID];
+	for(int i=0;i<6;i++)
+	{
+		defInfo->blockMap[i]=255;
+		defInfo->visitMap[i]=0;
+	}
+	defInfo->handler=NULL;
+	defInfo->blockMap[5] = 253;
+	defInfo->visitMap[5] = 2;
+
+	artifWorn[16] = 3;
+	if(type->heroType % 2 == 1) //it's a magical hero
+	{
+		artifWorn[17] = 0; //give him spellbook
+	}
+
+	if(portrait < 0 || portrait == 255)
+		portrait = subID;
+	if((!primSkills.size()) || (getPrimSkillLevel(0)<0))
+	{
+		primSkills.resize(4);
+		primSkills[0] = type->heroClass->initialAttack;
+		primSkills[1] = type->heroClass->initialDefence;
+		primSkills[2] = type->heroClass->initialPower;
+		primSkills[3] = type->heroClass->initialKnowledge;
+	}
+	if(secSkills.size() == 1 && secSkills[0] == std::pair<ui8,ui8>(-1, -1)) //set secondary skills to default
+		secSkills = type->secSkillsInit;
+	if(mana < 0)
+		mana = manaLimit();
+	if (!name.length())
+		name = type->name;
+	if (exp == 0xffffffff)
+	{
+		exp=40+  (ran())  % 50;
+		level = 1;
+	}
+	else
+	{
+		level = VLC->heroh->level(exp);
+	}
+
+	if (!army.slots.size()) //standard army//initial army
+	{
+		int pom, pom2=0;
+		for(int x=0;x<3;x++)
+		{
+			pom = (VLC->creh->nameToID[type->refTypeStack[x]]);
+			if(pom>=145 && pom<=149) //war machine
+			{
+				pom2++;
+				switch (pom)
+				{
+				case 145: //catapult
+					artifWorn[16] = 3;
+					break;
+				default:
+					artifWorn[9+CArtHandler::convertMachineID(pom,true)] = CArtHandler::convertMachineID(pom,true);
+					break;
+				}
+				continue;
+			}
+			army.slots[x-pom2].first = pom;
+			if((pom = (type->highStack[x]-type->lowStack[x])) > 0)
+				army.slots[x-pom2].second = (ran()%pom)+type->lowStack[x];
+			else 
+				army.slots[x-pom2].second = +type->lowStack[x];
+			army.formation = false;
+		}
+	}
+	hoverName = VLC->generaltexth->allTexts[15];
+	boost::algorithm::replace_first(hoverName,"%s",name);
+	boost::algorithm::replace_first(hoverName,"%s", type->heroClass->name);
+}
+
+CGHeroInstance::~CGHeroInstance()
+{
+}
+
+bool CGHeroInstance::needsLastStack() const
+{
+	return true;
+}
+void CGHeroInstance::onHeroVisit(const CGHeroInstance * h)
+{
+	//TODO: check for allies
+	if(tempOwner == h->tempOwner) //our hero
+	{
+		//exchange
+	}
+	else
+	{
+		cb->startBattleI(
+			&h->army,
+			&army,
+			h->pos,
+			h,
+			this,
+			0);
+	}
+}
+
+const std::string & CGHeroInstance::getBiography() const
+{
+	if (biography.length())
+		return biography;
+	else
+		return VLC->generaltexth->hTxts[subID].biography;		
+}
+void CGHeroInstance::initObj()
+{
+	cb->setBlockVis(id,true);
+}
 int CGTownInstance::getSightDistance() const //returns sight distance
 {
 	return 10;
@@ -556,187 +770,282 @@ CGTownInstance::CGTownInstance()
 	visitingHero = NULL;
 }
 
-CGObjectInstance::CGObjectInstance(): animPhaseShift(rand()%0xff)
+CGTownInstance::~CGTownInstance()
+{}
+
+int CGTownInstance::spellsAtLevel(int level, bool checkGuild) const
 {
-	pos = int3(-1,-1,-1);
-	//std::cout << "Tworze obiekt "<<this<<std::endl;
-	//state = new CLuaObjectScript();
-	ID = subID = id = -1;
-	defInfo = NULL;
-	state = NULL;
-	info = NULL;
-	tempOwner = 254;
-	blockVisit = false;
+	if(checkGuild && mageGuildLevel() < level)
+		return 0;
+	int ret = 6 - level; //how many spells are available at this level
+	if(subID == 2   &&   vstd::contains(builtBuildings,22)) //magic library in Tower
+		ret++; 
+	return ret;
 }
-CGObjectInstance::~CGObjectInstance()
+
+bool CGTownInstance::needsLastStack() const
 {
-	//std::cout << "Usuwam obiekt "<<this<<std::endl;
-	//if (state)
-	//	delete state;
-	//state=NULL;
+	if(garrisonHero)
+		return true;
+	else return false;
 }
-CGHeroInstance::CGHeroInstance()
+
+void CGTownInstance::onHeroVisit(const CGHeroInstance * h)
 {
-	ID = 34;
-	tacticFormationEnabled = inTownGarrison = false;
-	mana = movement = portrait = level = -1;
-	isStanding = true;
-	moveDir = 4;
-	exp = 0xffffffff;
-	visitedTown = NULL;
-	type = NULL;
-	secSkills.push_back(std::make_pair(-1, -1));
+	if(getOwner() != h->getOwner())
+	{
+		return;
+	}
+	cb->heroVisitCastle(id,h->id);
 }
 
-void CGHeroInstance::initHero(int SUBID)
+void CGTownInstance::onHeroLeave(const CGHeroInstance * h)
 {
-	subID = SUBID;
-	initHero();
+	cb->stopHeroVisitCastle(id,h->id);
 }
 
-void CGHeroInstance::initHero()
+void CGTownInstance::initObj()
 {
-	if(!defInfo)
+	MetaString ms;
+	ms << name << ", " << town->Name();
+	cb->setHoverName(id,&ms);
+}
+
+//std::vector<int> CVisitableOPH::yourObjects()
+//{
+//	std::vector<int> ret;
+//	ret.push_back(51);//camp 
+//	ret.push_back(23);//tower
+//	ret.push_back(61);//axis
+//	ret.push_back(32);//garden
+//	ret.push_back(100);//stone
+//	ret.push_back(102);//tree
+//	return ret;
+//}
+
+void CGVisitableOPH::onHeroVisit( const CGHeroInstance * h )
+{
+	if(visitors.find(h->id)==visitors.end())
 	{
-		defInfo = new CGDefInfo();
-		defInfo->id = 34;
-		defInfo->subid = subID;
-		defInfo->printPriority = 0;
-		defInfo->visitDir = 0xff;
+		onNAHeroVisit(h->id, false);
+		if(ID != 102) //not tree
+			visitors.insert(h->id);
 	}
-	if(!type)
-		type = VLC->heroh->heroes[subID];
-	for(int i=0;i<6;i++)
+	else
 	{
-		defInfo->blockMap[i]=255;
-		defInfo->visitMap[i]=0;
+		onNAHeroVisit(h->id, true);
 	}
-	defInfo->handler=NULL;
-	defInfo->blockMap[5] = 253;
-	defInfo->visitMap[5] = 2;
+}
 
-	artifWorn[16] = 3;
-	if(type->heroType % 2 == 1) //it's a magical hero
-	{
-		artifWorn[17] = 0; //give him spellbook
-	}
+void CGVisitableOPH::initObj()
+{
+	if(ID==102)
+		ttype = ran()%3;
+	else
+		ttype = -1;
+}
 
-	if(portrait < 0 || portrait == 255)
-		portrait = subID;
-	if((!primSkills.size()) || (getPrimSkillLevel(0)<0))
+void CGVisitableOPH::treeSelected( int heroID, int resType, int resVal, int expVal, ui32 result )
+{
+	if(result==0) //player agreed to give res for exp
 	{
-		primSkills.resize(4);
-		primSkills[0] = type->heroClass->initialAttack;
-		primSkills[1] = type->heroClass->initialDefence;
-		primSkills[2] = type->heroClass->initialPower;
-		primSkills[3] = type->heroClass->initialKnowledge;
+		cb->giveResource(cb->getOwner(heroID),resType,-resVal); //take resource
+		cb->changePrimSkill(heroID,4,expVal); //give exp
+		visitors.insert(heroID); //set state to visited
 	}
-	if(secSkills.size() == 1 && secSkills[0] == std::pair<ui8,ui8>(-1, -1)) //set secondary skills to default
-		secSkills = type->secSkillsInit;
-	if(mana < 0)
-		mana = manaLimit();
-	if (!name.length())
-		name = type->name;
-	if (exp == 0xffffffff)
-	{
-		exp=40+  (ran())  % 50;
-		level = 1;
-	}
-	else
+}
+void CGVisitableOPH::onNAHeroVisit(int heroID, bool alreadyVisited)
+{
+	int id=0, subid=0, ot=0, val=1;
+	switch(ID)
 	{
-		level = VLC->heroh->level(exp);
+	case 51:
+		subid=0;
+		ot=80;
+		break;
+	case 23:
+		subid=1;
+		ot=39;
+		break;
+	case 61:
+		subid=2;
+		ot=100;
+		break;
+	case 32:
+		subid=3;
+		ot=59;
+		break;
+	case 100:
+		id=5;
+		ot=143;
+		val=1000;
+		break;
+	case 102:
+		id = 5;
+		subid = 1;
+		ot = 146;
+		val = 1;
+		break;
 	}
-	
-	if (!army.slots.size()) //standard army//initial army
+	if (!alreadyVisited)
 	{
-		int pom, pom2=0;
-		for(int x=0;x<3;x++)
+		switch (ID)
 		{
-			pom = (VLC->creh->nameToID[type->refTypeStack[x]]);
-			if(pom>=145 && pom<=149) //war machine
+		case 51:
+		case 23:
+		case 61:
+		case 32:
 			{
-				pom2++;
-				switch (pom)
+				cb->changePrimSkill(heroID,subid,val);
+				InfoWindow iw;
+				iw.components.push_back(Component(0,subid,val,0));
+				iw.text << std::pair<ui8,ui32>(11,ot);
+				iw.player = cb->getOwner(heroID);
+				cb->showInfoDialog(&iw);
+				break;
+			}
+		case 100: //give exp
+			{
+				InfoWindow iw;
+				iw.components.push_back(Component(id,subid,val,0));
+				iw.player = cb->getOwner(heroID);
+				iw.text << std::pair<ui8,ui32>(11,ot);
+				cb->showInfoDialog(&iw);
+				cb->changePrimSkill(heroID,4,val);
+				break;
+			}
+		case 102:
+			{
+				const CGHeroInstance *h = cb->getHero(heroID);
+				val = VLC->heroh->reqExp(h->level+val) - VLC->heroh->reqExp(h->level);
+				if(!ttype)
 				{
-				case 145: //catapult
-					artifWorn[16] = 3;
-					break;
-				default:
-					artifWorn[9+CArtHandler::convertMachineID(pom,true)] = CArtHandler::convertMachineID(pom,true);
+					visitors.insert(heroID);
+					InfoWindow iw;
+					iw.components.push_back(Component(id,subid,1,0));
+					iw.player = cb->getOwner(heroID);
+					iw.text << std::pair<ui8,ui32>(11,148);
+					cb->showInfoDialog(&iw);
+					cb->changePrimSkill(heroID,4,val);
 					break;
 				}
-				continue;
+				else
+				{
+					int res, resval;
+					if(ttype==1)
+					{
+						res = 6;
+						resval = 2000;
+						ot = 149;
+					}
+					else
+					{
+						res = 5;
+						resval = 10;
+						ot = 151;
+					}
+
+					if(cb->getResource(h->tempOwner,res) < resval) //not enough resources
+					{
+						ot++;
+						InfoWindow iw;
+						iw.player = h->tempOwner;
+						iw.text << std::pair<ui8,ui32>(11,ot);
+						cb->showInfoDialog(&iw);
+						return;
+					}
+
+					YesNoDialog sd;
+					sd.player = cb->getOwner(heroID);
+					sd.text << std::pair<ui8,ui32>(11,ot);
+					sd.components.push_back(Component(id,subid,val,0));
+					cb->showYesNoDialog(&sd,boost::bind(&CGVisitableOPH::treeSelected,this,heroID,res,resval,val,_1));
+				}
+				break;
 			}
-			army.slots[x-pom2].first = pom;
-			if((pom = (type->highStack[x]-type->lowStack[x])) > 0)
-				army.slots[x-pom2].second = (ran()%pom)+type->lowStack[x];
-			else 
-				army.slots[x-pom2].second = +type->lowStack[x];
-			army.formation = false;
 		}
 	}
+	else
+	{
+		ot++;
+		InfoWindow iw;
+		iw.player = cb->getOwner(heroID);
+		iw.text << std::pair<ui8,ui32>(11,ot);
+		cb->showInfoDialog(&iw);
+	}
 }
 
-CGHeroInstance::~CGHeroInstance()
+const std::string & CGVisitableOPH::getHoverText() const
 {
+	int pom;
+	switch(ID)
+	{
+	case 51:
+		pom = 8; 
+		break;
+	case 23:
+		pom = 7;
+		break;
+	case 61:
+		pom = 11; 
+		break;
+	case 32:
+		pom = 4; 
+		break;
+	case 100:
+		pom = 5; 
+		break;
+	case 102:
+		pom = 18;
+		break;
+	default:
+		throw "Wrong CGVisitableOPH object ID!\n";
+	}
+	hoverName = VLC->objh->names[ID] + " " + VLC->objh->xtrainfo[pom];
+	const CGHeroInstance *h = cb->getSelectedHero(cb->getCurrentPlayer());
+	if(h)
+	{
+		hoverName += (vstd::contains(visitors,h->id)) 
+						? (VLC->generaltexth->allTexts[353])  //not visited
+						: ( VLC->generaltexth->allTexts[352]); //visited
+	}
+	return hoverName;
 }
 
-bool CGHeroInstance::needsLastStack() const
+bool CArmedInstance::needsLastStack() const
 {
-	return true;
+	return false;
 }
 
-const std::string & CGHeroInstance::getBiography()
+void CGCreature::onHeroVisit( const CGHeroInstance * h )
 {
-	if (biography.length())
-		return biography;
-	else
-		return VLC->generaltexth->hTxts[subID].biography;		
+	army.slots[0].first = subID;
+	cb->startBattleI(h->id,army,pos,boost::bind(&CGCreature::endBattle,this,_1));
 }
-CGTownInstance::~CGTownInstance()
-{}
 
-int CGTownInstance::spellsAtLevel(int level, bool checkGuild) const
+void CGCreature::endBattle( BattleResult *result )
 {
-	if(checkGuild && mageGuildLevel() < level)
-		return 0;
-	int ret = 6 - level; //how many spells are available at this level
-	if(subID == 2   &&   vstd::contains(builtBuildings,22)) //magic library in Tower
-		ret++; 
-	return ret;
+	if(result->winner==0)
+	{
+		cb->removeObject(id);
+	}
+	else
+	{
+		int killedAmount=0;
+		for(std::set<std::pair<ui32,si32> >::iterator i=result->casualties[1].begin(); i!=result->casualties[1].end(); i++)
+			if(i->first == subID)
+				killedAmount += i->second;
+		cb->setAmount(id, army.slots[0].second - killedAmount);
+	}
 }
 
-bool CGTownInstance::needsLastStack() const
-{
-	if(garrisonHero)
-		return true;
-	else return false;
-}
-CGObjectInstance::CGObjectInstance(const CGObjectInstance & right)
+void CGCreature::initObj()
 {
-	pos = right.pos;
-	ID = right.ID;
-	subID = right.subID;
-	id	= right.id;
-	defInfo = right.defInfo;
-	info = right.info;
-	blockVisit = right.blockVisit;
-	//state = new CLuaObjectScript(right.state->);
-	//*state = *right.state;
-	//state = right.state;
-	tempOwner = right.tempOwner;
-}
-CGObjectInstance& CGObjectInstance::operator=(const CGObjectInstance & right)
-{
-	pos = right.pos;
-	ID = right.ID;
-	subID = right.subID;
-	id	= right.id;
-	defInfo = right.defInfo;
-	info = right.info;
-	blockVisit = right.blockVisit;
-	//state = new CLuaObjectScript();
-	//*state = *right.state;
-	tempOwner = right.tempOwner;
-	return *this;
-}
+	si32 &amount = army.slots[0].second;
+	CCreature &c = VLC->creh->creatures[subID];
+	if(!amount)
+		if(c.ammMax == c.ammMin)
+			amount = c.ammMax;
+		else
+			amount = c.ammMin + (ran() % (c.ammMax - c.ammMin));
+}

+ 249 - 14
hch/CObjectHandler.h

@@ -8,6 +8,8 @@
 #include "CCreatureHandler.h"
 
 using boost::logic::tribool;
+class IGameCallback;
+struct BattleResult;
 class CCPPObjectScript;
 class CGObjectInstance;
 class CScript;
@@ -42,9 +44,25 @@ public:
 	}
 };
 
-class DLL_EXPORT CGObjectInstance
+class DLL_EXPORT IObjectInterface
 {
 public:
+	static IGameCallback *cb;
+
+	IObjectInterface();
+	virtual ~IObjectInterface();
+
+	virtual void onHeroVisit(const CGHeroInstance * h);
+	virtual void onHeroLeave(const CGHeroInstance * h);
+	virtual void newTurn();
+	virtual void initObj();
+};
+
+class DLL_EXPORT CGObjectInstance : protected IObjectInterface
+{
+protected:
+public:
+	mutable std::string hoverName;
 	int3 pos; //h3m pos
 	int ID, subID; //normal ID (this one from OH3 maps ;]) - eg. town=98; hero=34
 	si32 id;//number of object in CObjectHandler's vector		
@@ -52,12 +70,10 @@ public:
 	CCPPObjectScript * state;
 	CSpecObjInfo * info;
 	unsigned char animPhaseShift;
-	std::string hoverName;
 
 	ui8 tempOwner; //uzywane dla szybkosci, skrypt ma obowiazek aktualizowac te zmienna
 	ui8 blockVisit; //if non-zero then blocks the tile but is visitable from neighbouring tile
 
-	virtual bool isHero() const;
 	int getOwner() const;
 	void setOwner(int ow);
 	int getWidth() const; //returns width of object graphic in tiles
@@ -69,22 +85,32 @@ public:
 	virtual ~CGObjectInstance();
 	CGObjectInstance(const CGObjectInstance & right);
 	CGObjectInstance& operator=(const CGObjectInstance & right);
+	virtual const std::string & getHoverText() const;
+	//////////////////////////////////////////////////////////////////////////
+	void initObj();
+
+	friend class CGameHandler;
 };
 
 class  DLL_EXPORT CArmedInstance: public CGObjectInstance
 {
 public:
 	CCreatureSet army; //army
-	virtual bool needsLastStack() const=0; //true if last stack cannot be taken
+	virtual bool needsLastStack() const; //true if last stack cannot be taken
 };
 
 class DLL_EXPORT CGHeroInstance : public CArmedInstance
 {
 public:
+	//////////////////////////////////////////////////////////////////////////
+
 	mutable int moveDir; //format:	123
 					//		8 4
 					//		765
 	mutable ui8 isStanding, tacticFormationEnabled;
+
+	//////////////////////////////////////////////////////////////////////////
+
 	CHero * type;
 	ui32 exp; //experience point
 	int level; //current level of hero
@@ -97,35 +123,29 @@ public:
 	int movement; //remaining movement points
 	int identifier; //from the map file
 	bool sex;
-
 	struct DLL_EXPORT Patrol
 	{
 		Patrol(){patrolling=false;patrolRadious=-1;};
 		bool patrolling;
 		int patrolRadious;
 	} patrol;
-
-
 	bool inTownGarrison; // if hero is in town garrison 
 	CGTownInstance * visitedTown; //set if hero is visiting town or in the town garrison
-
 	std::vector<ui32> artifacts; //hero's artifacts from bag
 	std::map<ui16,ui32> artifWorn; //map<position,artifact_id>; positions: 0 - head; 1 - shoulders; 2 - neck; 3 - right hand; 4 - left hand; 5 - torso; 6 - right ring; 7 - left ring; 8 - feet; 9 - misc1; 10 - misc2; 11 - misc3; 12 - misc4; 13 - mach1; 14 - mach2; 15 - mach3; 16 - mach4; 17 - spellbook; 18 - misc5
 	std::set<ui32> spells; //known spells (spell IDs)
 
-	const std::string &getBiography();
+	//////////////////////////////////////////////////////////////////////////
+
+	const std::string &getBiography() const;
 	bool needsLastStack()const;
-	virtual bool isHero() const;
 	unsigned int getTileCost(const EterrainType & ttype, const Eroad & rdtype, const Eriver & rvtype) const;
-	unsigned int getLowestCreatureSpeed();
+	unsigned int getLowestCreatureSpeed() const;
 	unsigned int getAdditiveMoveBonus() const;
 	float getMultiplicativeMoveBonus() const;
-	static int3 convertPosition(int3 src, bool toh3m); //toh3m=true: manifest->h3m; toh3m=false: h3m->manifest
 	int3 getPosition(bool h3m) const; //h3m=true - returns position of hero object; h3m=false - returns position of hero 'manifestation'
 	int getSightDistance() const; //returns sight distance of this hero
 	int manaLimit() const; //maximum mana value for this hero (basically 10*knowledge)
-	//void setPosition(int3 Pos, bool h3m); //as above, but sets position
-
 	bool canWalkOnSea() const;
 	int getCurrentLuck() const;
 	int getCurrentMorale() const;
@@ -136,10 +156,18 @@ public:
 	void setArtAtPos(ui16 pos, int art);
 	const CArtifact * getArt(int pos) const;
 	int getSpellSecLevel(int spell) const; //returns level of secondary ability (fire, water, earth, air magic) known to this hero and applicable to given spell; -1 if error
+	static int3 convertPosition(int3 src, bool toh3m); //toh3m=true: manifest->h3m; toh3m=false: h3m->manifest
+
+	//////////////////////////////////////////////////////////////////////////
+
 	void initHero(); 
 	void initHero(int SUBID); 
 	CGHeroInstance();
 	virtual ~CGHeroInstance();
+
+	//////////////////////////////////////////////////////////////////////////
+	void initObj();
+	void onHeroVisit(const CGHeroInstance * h);
 };
 
 class DLL_EXPORT CGTownInstance : public CArmedInstance
@@ -183,6 +211,213 @@ public:
 
 	CGTownInstance();
 	virtual ~CGTownInstance();
+
+	//////////////////////////////////////////////////////////////////////////
+
+
+	void onHeroVisit(const CGHeroInstance * h);
+	void onHeroLeave(const CGHeroInstance * h);
+	void initObj();
+};
+
+class DLL_EXPORT CGVisitableOPH : public CGObjectInstance //objects visitable only once per hero
+{
+public:
+	std::set<si32> visitors; //ids of heroes who have visited this obj
+	si8 ttype; //tree type - used only by trees of knowledge: 0 - give level for free; 1 - take 2000 gold; 2 - take 10 gems
+	const std::string & getHoverText() const;
+
+	void onHeroVisit(const CGHeroInstance * h);
+	void onNAHeroVisit(int heroID, bool alreadyVisited);
+	void initObj();
+	void treeSelected(int heroID, int resType, int resVal, int expVal, ui32 result); //handle player's anwer to the Tree of Knowledge dialog
+};
+
+class DLL_EXPORT CGEvent : public CGObjectInstance //event objects
+{
+public:
+	bool areGuarders; //true if there are
+	CCreatureSet guarders;
+	bool isMessage; //true if there is a message
+	std::string message;
+	unsigned int gainedExp;
+	int manaDiff; //amount of gained / lost mana
+	int moraleDiff; //morale modifier
+	int luckDiff; //luck modifier
+	int wood, mercury, ore, sulfur, crystal, gems, gold; //gained / lost resources
+	unsigned int attack; //added attack points
+	unsigned int defence; //added defence points
+	unsigned int power; //added power points
+	unsigned int knowledge; //added knowledge points
+	std::vector<int> abilities; //gained abilities
+	std::vector<int> abilityLevels; //levels of gained abilities
+	std::vector<int> artifacts; //gained artifacts
+	std::vector<int> spells; //gained spells
+	CCreatureSet creatures; //gained creatures
+	unsigned char availableFor; //players whom this event is available for
+	bool computerActivate; //true if computre player can activate this event
+	bool humanActivate; //true if human player can activate this event
+};
+
+class DLL_EXPORT CGCreature : public CArmedInstance //creatures on map
+{
+public:
+	ui32 identifier; //unique code for this monster (used in missions)
+	ui8 character; //chracter of this set of creatures (0 - the most friendly, 4 - the most hostile)
+	std::string message; //message printed for attacking hero
+	std::vector<ui32> resources; //[res_id], resources given to hero that has won with monsters
+	si32 gainedArtifact; //ID of artifact gained to hero, -1 if none
+	ui8 neverFlees; //if true, the troops will never flee
+	ui8 notGrowingTeam; //if true, number of units won't grow
+
+	void onHeroVisit(const CGHeroInstance * h);
+	void endBattle(BattleResult *result);
+	void initObj();
+}; 
+
+
+class DLL_EXPORT CGSignBottle : public CGObjectInstance //signs and ocean bottles
+{
+	//TODO: generate default message if sign is 'empty'
+public:
+	std::string message;
+};
+
+class DLL_EXPORT CGSeerHut : public CGObjectInstance
+{
+public:
+	unsigned char missionType; //type of mission: 0 - no mission; 1 - reach level; 2 - reach main statistics values; 3 - win with a certain hero; 4 - win with a certain creature; 5 - collect some atifacts; 6 - have certain troops in army; 7 - collect resources; 8 - be a certain hero; 9 - be a certain player
+	bool isDayLimit; //if true, there is a day limit
+	int lastDay; //after this day (first day is 0) mission cannot be completed
+	int m1level; //for mission 1	
+	int m2attack, m2defence, m2power, m2knowledge;//for mission 2
+	unsigned char m3bytes[4];//for mission 3
+	unsigned char m4bytes[4];//for mission 4
+	std::vector<int> m5arts;//for mission 5 - artifact ID
+	std::vector<CCreature *> m6cre;//for mission 6
+	std::vector<int> m6number;
+	int m7wood, m7mercury, m7ore, m7sulfur, m7crystal, m7gems, m7gold;	//for mission 7
+	int m8hero;//for mission 8 - hero ID
+	int m9player; //for mission 9 - number; from 0 to 7
+
+	std::string firstVisitText, nextVisitText, completedText;
+
+	char rewardType; //type of reward: 0 - no reward; 1 - experience; 2 - mana points; 3 - morale bonus; 4 - luck bonus; 5 - resources; 6 - main ability bonus (attak, defence etd.); 7 - secondary ability gain; 8 - artifact; 9 - spell; 10 - creature
+	//for reward 1
+	int r1exp;
+	//for reward 2
+	int r2mana;
+	//for reward 3
+	int r3morale;
+	//for reward 4
+	int r4luck;
+	//for reward 5
+	unsigned char r5type; //0 - wood, 1 - mercury, 2 - ore, 3 - sulfur, 4 - crystal, 5 - gems, 6 - gold
+	int r5amount;
+	//for reward 6
+	unsigned char r6type; //0 - attack, 1 - defence, 2 - power, 3 - knowledge
+	int r6amount;
+	//for reward 7
+	int r7ability; //ability id
+	unsigned char r7level; //1 - basic, 2 - advanced, 3 - expert
+	//for reward 8
+	int r8art;//artifact id
+	//for reward 9
+	int r9spell;//spell id
+	//for reward 10
+	int r10creature; //creature id
+	int r10amount;
+};
+
+class DLL_EXPORT CGWitchHut : public CGObjectInstance
+{
+public:
+	std::vector<int> allowedAbilities;
+};
+
+
+class DLL_EXPORT CGScholar : public CGObjectInstance
+{
+public:
+	ui8 bonusType; //255 - random, 0 - primary skill, 1 - secondary skill, 2 - spell
+
+	ui8 r0type;
+	ui32 r1; //Ability ID
+	ui32 r2; //Spell ID
+};
+
+class DLL_EXPORT CGGarrison : public CArmedInstance
+{
+public:
+	bool removableUnits;
+};
+
+class DLL_EXPORT CGArtifact : public CArmedInstance
+{
+public:
+	std::string message;
+	ui32 spell; //if it's spell scroll
+};
+
+class DLL_EXPORT CGResource : public CArmedInstance
+{
+public:
+	int amount; //0 if random
+	std::string message;
+};
+
+class DLL_EXPORT CGShrine : public CGObjectInstance
+{
+public:
+	unsigned char spell; //number of spell or 255 if random
+};
+
+class DLL_EXPORT CGPandoraBox : public CArmedInstance
+{
+public:
+	std::string message;
+
+	//gained things:
+	unsigned int gainedExp;
+	int manaDiff;
+	int moraleDiff;
+	int luckDiff;
+	int wood, mercury, ore, sulfur, crystal, gems, gold;
+	int attack, defence, power, knowledge;
+	std::vector<int> abilities;
+	std::vector<int> abilityLevels;
+	std::vector<int> artifacts;
+	std::vector<int> spells;
+	CCreatureSet creatures;
+};
+
+class DLL_EXPORT CGQuestGuard : public CArmedInstance
+{
+public:
+	char missionType; //type of mission: 0 - no mission; 1 - reach level; 2 - reach main statistics values; 3 - win with a certain hero; 4 - win with a certain creature; 5 - collect some atifacts; 6 - have certain troops in army; 7 - collect resources; 8 - be a certain hero; 9 - be a certain player
+	bool isDayLimit; //if true, there is a day limit
+	int lastDay; //after this day (first day is 0) mission cannot be completed
+	//for mission 1
+	int m1level;
+	//for mission 2
+	int m2attack, m2defence, m2power, m2knowledge;
+	//for mission 3
+	unsigned char m3bytes[4];
+	//for mission 4
+	unsigned char m4bytes[4];
+	//for mission 5
+	std::vector<int> m5arts; //artifacts id
+	//for mission 6
+	std::vector<CCreature *> m6cre;
+	std::vector<int> m6number;
+	//for mission 7
+	int m7wood, m7mercury, m7ore, m7sulfur, m7crystal, m7gems, m7gold;
+	//for mission 8
+	int m8hero; //hero id
+	//for mission 9
+	int m9player; //number; from 0 to 7
+
+	std::string firstVisitText, nextVisitText, completedText;
 };
 
 class DLL_EXPORT CObjectHandler

+ 13 - 1
hch/CSpellHandler.h

@@ -10,6 +10,7 @@ public:
 	ui32 id;
 	std::string name;
 	std::string abbName; //abbreviated name
+	std::vector<std::string> descriptions; //descriptions of spell for skill levels: 0 - none, 1 - basic, etc
 	si32 level;
 	bool earth;
 	bool water;
@@ -20,11 +21,17 @@ public:
 	std::vector<si32> powers; //[er skill level: 0 - none, 1 - basic, etc
 	std::vector<si32> probabilities; //% chance to gain for castles 
 	std::vector<si32> AIVals; //AI values: per skill level: 0 - none, 1 - basic, etc
-	std::vector<std::string> descriptions; //descriptions of spell for skill levels: 0 - none, 1 - basic, etc
 	std::string attributes; //reference only attributes
 	bool combatSpell; //is this spell combat (true) or adventure (false)
 	bool creatureAbility; //if true, only creatures can use this spell
 	si8 positiveness; //1 if spell is positive for influenced stacks, 0 if it is indifferent, -1 if it's negative
+
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & id & name & abbName & descriptions & level & earth & water & fire & air & power & costs 
+			& powers & probabilities & AIVals & attributes & combatSpell & creatureAbility & positiveness;
+	}
 };
 
 class DLL_EXPORT CSpellHandler
@@ -32,6 +39,11 @@ class DLL_EXPORT CSpellHandler
 public:
 	std::vector<CSpell> spells;
 	void loadSpells();
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & spells;
+	}
 };
 
 #endif //CSPELLHANDLER_H

+ 100 - 104
hch/CTownHandler.cpp

@@ -4,6 +4,7 @@
 #include "CLodHandler.h"
 #include <sstream>
 #include "../lib/VCMI_Lib.h"
+#include "CGeneralTextHandler.h"
 extern CLodHandler * bitmaph;
 void loadToIt(std::string &dest, std::string &src, int &iter, int mode);
 CTownHandler::CTownHandler()
@@ -11,51 +12,104 @@ CTownHandler::CTownHandler()
 	VLC->townh = this;
 }
 CTownHandler::~CTownHandler()
-{}
+{
+	for( std::map<int,std::map<int, Structure*> >::iterator i= structures.begin(); i!=structures.end(); i++)
+		for( std::map<int, Structure*>::iterator j = i->second.begin(); j!=i->second.end(); j++)
+			delete j->second;
+}
 void CTownHandler::loadNames()
 {
-	std::istringstream ins, names;
-	ins.str(bitmaph->getTextFile("TOWNTYPE.TXT"));
-	names.str(bitmaph->getTextFile("TOWNNAME.TXT"));
-	int si=0;
+	int si, itr;
 	char bufname[75];
-	while (!ins.eof())
+	for (si=0; si<F_NUMBER; si++)
 	{
 		CTown town;
-		ins.getline(bufname,50);
-		town.name = std::string(bufname);
-		town.name = town.name.substr(0,town.name.size()-1);
-		for (int i=0; i<NAMES_PER_TOWN; i++)
-		{
-			names.getline(bufname,50);
-			std::string pom(bufname);
-			town.names.push_back(pom.substr(0,pom.length()-1));
-		}
-		town.typeID=si++;
+		town.typeID=si;
 		town.bonus=towns.size();
 		if (town.bonus==8) town.bonus=3;
-		if (town.name.length())
-			towns.push_back(town);
+		towns.push_back(town);
+	}
+
+	loadStructures();
+
+
+	std::ifstream of;
+	for(int x=0;x<towns.size();x++)
+		towns[x].basicCreatures.resize(7);
+
+	of.open("config/basicCres.txt");
+	while(!of.eof())
+	{
+		int tid, lid, cid; //town,level,creature
+		of >> tid >> lid >> cid;
+		if(lid < towns[tid].basicCreatures.size())
+			towns[tid].basicCreatures[lid]=cid;
+	}
+	of.close();
+	of.clear();
+
+	for(int x=0;x<towns.size();x++)
+		towns[x].upgradedCreatures.resize(7);
+
+	of.open("config/creatures_upgr.txt");
+	while(!of.eof())
+	{
+		int tid, lid, cid; //town,level,creature
+		of >> tid >> lid >> cid;
+		if(lid < towns[tid].upgradedCreatures.size())
+			towns[tid].upgradedCreatures[lid]=cid;
+	}
+	of.close();
+	of.clear();
+
+	of.open("config/building_horde.txt");
+	while(!of.eof())
+	{
+		int tid, lid, cid; //town,horde serial,creature level
+		of >> tid >> lid >> cid;
+		towns[tid].hordeLvl[--lid] = cid;
 	}
+	of.close();
+	of.clear();
 
-	std::string  strs = bitmaph->getTextFile("TCOMMAND.TXT");
-	int itr=0;
-	while(itr<strs.length()-1)
+	of.open("config/mageLevel.txt");
+	of >> si;
+	for(itr=0; itr<si; itr++)
 	{
-		std::string tmp;
-		loadToIt(tmp, strs, itr, 3);
-		tcommands.push_back(tmp);
+		of >> towns[itr].mageLevel >> towns[itr].primaryRes >> towns[itr].warMachine;
 	}
+	of.close();
+	of.clear();
 
-	strs = bitmaph->getTextFile("HALLINFO.TXT");
-	itr=0;
-	while(itr<strs.length()-1)
+	of.open("config/requirements.txt");
+	while(!of.eof())
 	{
-		std::string tmp;
-		loadToIt(tmp, strs, itr, 3);
-		hcommands.push_back(tmp);
+		int ile, town, build, pom;
+		of >> ile;
+		for(int i=0;i<ile;i++)
+		{
+			of >> town;
+			while(true)
+			{
+				of.getline(bufname,75);if(!(*bufname))of.getline(bufname,75);
+				std::istringstream ifs(bufname);
+				ifs >> build;
+				if(build<0)
+					break;
+				while(!ifs.eof())
+				{
+					ifs >> pom;
+					requirements[town][build].insert(pom);
+				}
+			}
+		}
 	}
+	of.close();
+	of.clear();
+}
 
+void CTownHandler::loadStructures()
+{
 	//read buildings coords
 	std::ifstream of("config/buildings.txt");
 	while(!of.eof())
@@ -133,7 +187,7 @@ void CTownHandler::loadNames()
 	of.clear();
 
 	//read groups
-	itr = 0;
+	int itr = 0;
 	of.open("config/buildings4.txt");
 	of >> format;
 	if(format!=1)
@@ -209,78 +263,20 @@ void CTownHandler::loadNames()
 		}
 		of.close();
 		of.clear();
-
-		for(int x=0;x<towns.size();x++)
-			towns[x].basicCreatures.resize(7);
-
-		of.open("config/basicCres.txt");
-		while(!of.eof())
-		{
-			int tid, lid, cid; //town,level,creature
-			of >> tid >> lid >> cid;
-			if(lid < towns[tid].basicCreatures.size())
-				towns[tid].basicCreatures[lid]=cid;
-		}
-		of.close();
-		of.clear();
-
-		for(int x=0;x<towns.size();x++)
-			towns[x].upgradedCreatures.resize(7);
-
-		of.open("config/creatures_upgr.txt");
-		while(!of.eof())
-		{
-			int tid, lid, cid; //town,level,creature
-			of >> tid >> lid >> cid;
-			if(lid < towns[tid].upgradedCreatures.size())
-				towns[tid].upgradedCreatures[lid]=cid;
-		}
-		of.close();
-		of.clear();
-
-		of.open("config/building_horde.txt");
-		while(!of.eof())
-		{
-			int tid, lid, cid; //town,horde serial,creature level
-			of >> tid >> lid >> cid;
-			towns[tid].hordeLvl[--lid] = cid;
-		}
-		of.close();
-		of.clear();
-
-		of.open("config/mageLevel.txt");
-		of >> si;
-		for(itr=0; itr<si; itr++)
-		{
-			of >> towns[itr].mageLevel >> towns[itr].primaryRes >> towns[itr].warMachine;
-		}
-		of.close();
-		of.clear();
-
-		of.open("config/requirements.txt");
-		while(!of.eof())
-		{
-			int ile, town, build, pom;
-			of >> ile;
-			for(int i=0;i<ile;i++)
-			{
-				of >> town;
-				while(true)
-				{
-					of.getline(bufname,75);if(!(*bufname))of.getline(bufname,75);
-					std::istringstream ifs(bufname);
-					ifs >> build;
-					if(build<0)
-						break;
-					while(!ifs.eof())
-					{
-						ifs >> pom;
-						requirements[town][build].insert(pom);
-					}
-				}
-			}
-		}
-		of.close();
-		of.clear();
 	}
 }
+const std::string & CTown::Name() const
+{
+	if(name.length())
+		return name;
+	else
+		return VLC->generaltexth->townTypes[typeID];
+}
+
+const std::vector<std::string> & CTown::Names() const
+{
+	if(names.size())
+		return names;
+	else 
+		return VLC->generaltexth->townNames[typeID];
+}

+ 23 - 2
hch/CTownHandler.h

@@ -8,8 +8,9 @@ class CHero;
 class CGTownInstance;
 class DLL_EXPORT CTown
 {
-public:
 	std::string name; //name of type
+public:
+
 	std::vector<std::string> names; //names of the town instances
 	std::vector<int> basicCreatures; //level (from 0) -> ID
 	std::vector<int> upgradedCreatures; //level (from 0) -> ID
@@ -18,6 +19,18 @@ public:
 	int bonus; //pic number
 	ui16 primaryRes, warMachine;
 	ui8 typeID;
+
+
+	const std::vector<std::string> & Names() const;
+	const std::string & Name() const;
+	void Name(const std::string & val) { name = val; }
+
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & names & basicCreatures & upgradedCreatures & hordeLvl & mageLevel & bonus 
+			& primaryRes & warMachine & typeID;
+	}
 };
 
 struct DLL_EXPORT Structure
@@ -26,6 +39,7 @@ struct DLL_EXPORT Structure
 	int3 pos;
 	std::string defName, borderName, areaName, name;
 	int townID, group;
+
 	bool operator<(const Structure & p2) const
 	{
 		if(pos.z != p2.pos.z)
@@ -39,13 +53,20 @@ class DLL_EXPORT CTownHandler
 {
 public:
 	std::vector<CTown> towns;
-	std::vector<std::string> tcommands, hcommands;
 	std::map<int,std::map<int, Structure*> > structures; // <town ID, <structure ID, structure>>
 	std::map<int, std::map<int,std::set<int> > > requirements; //requirements[town_id][structure_id] -> set of required buildings
 
 	CTownHandler();
 	~CTownHandler();
 	void loadNames();
+	void loadStructures();
+
+	template <typename Handler> void serialize(Handler &h, const int version)
+	{
+		h & towns & requirements;
+		if(!h.saving)
+			loadStructures();
+	}
 };
 
 #endif //CTOWNHANDLER_H

+ 52 - 0
lib/IGameCallback.h

@@ -0,0 +1,52 @@
+#pragma once
+
+#include "../global.h"
+#include <vector>
+#include <set>
+#include "../client/FunctionList.h"
+
+class CGObjectInstance;
+class CGTownInstance;
+class CGHeroInstance;
+struct SelectionDialog;
+struct YesNoDialog;
+struct InfoWindow;
+struct MetaString;
+struct ShowInInfobox;
+struct BattleResult;
+
+class IGameCallback
+{
+public:
+	virtual ~IGameCallback(){};
+
+	virtual int getOwner(int heroID)=0;
+	virtual int getResource(int player, int which)=0;
+	virtual int getSelectedHero()=0;
+	virtual int getDate(int mode=0)=0;
+	virtual const CGObjectInstance* getObj(int objid)=0;
+	virtual const CGHeroInstance* getHero(int objid)=0;
+	virtual const CGTownInstance* getTown(int objid)=0;
+	virtual const CGHeroInstance* getSelectedHero(int player)=0; //NULL if no hero is selected
+	virtual int getCurrentPlayer()=0;
+
+	//do sth
+	virtual void changeSpells(int hid, bool give, const std::set<ui32> &spells)=0;
+	virtual void removeObject(int objid)=0;
+	virtual void setBlockVis(int objid, bool bv)=0;
+	virtual void setOwner(int objid, ui8 owner)=0;
+	virtual void setHoverName(int objid, MetaString * name)=0;
+	virtual void changePrimSkill(int ID, int which, int val, bool abs=false)=0;
+	virtual void showInfoDialog(InfoWindow *iw)=0;
+	virtual void showYesNoDialog(YesNoDialog *iw, const CFunctionList<void(ui32)> &callback)=0;
+	virtual void showSelectionDialog(SelectionDialog *iw, const CFunctionList<void(ui32)> &callback)=0; //returns question id
+	virtual void giveResource(int player, int which, int val)=0;
+	virtual void showCompInfo(ShowInInfobox * comp)=0;
+	virtual void heroVisitCastle(int obj, int heroID)=0;
+	virtual void stopHeroVisitCastle(int obj, int heroID)=0;
+	virtual void giveHeroArtifact(int artid, int hid, int position)=0; //pos==-1 - first free slot in backpack=0; pos==-2 - default if available or backpack
+	virtual void startBattleI(const CCreatureSet * army1, const CCreatureSet * army2, int3 tile, const CGHeroInstance *hero1, const CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb)=0; //use hero=NULL for no hero
+	virtual void startBattleI(int heroID, CCreatureSet army, int3 tile, boost::function<void(BattleResult*)> cb)=0; //for hero<=>neutral army
+	virtual void setAmount(int objid, ui32 val)=0;
+	virtual void moveHero(int hid, int3 pos, bool instant)=0;
+};

+ 5 - 1
lib/VCMI_lib.vcproj

@@ -42,7 +42,7 @@
 				AdditionalOptions="/MP2"
 				Optimization="0"
 				AdditionalIncludeDirectories="G:\vcmt\repa\include"
-				MinimalRebuild="true"
+				MinimalRebuild="false"
 				BasicRuntimeChecks="3"
 				RuntimeLibrary="3"
 				WarningLevel="2"
@@ -388,6 +388,10 @@
 				RelativePath="..\hch\CTownHandler.h"
 				>
 			</File>
+			<File
+				RelativePath=".\IGameCallback.h"
+				>
+			</File>
 			<File
 				RelativePath=".\Interprocess.h"
 				>

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 249 - 319
map.cpp


+ 6 - 195
map.h

@@ -17,177 +17,13 @@ enum EDefType {TOWN_DEF, HERO_DEF, CREATURES_DEF, SEERHUT_DEF, RESOURCE_DEF, TER
 	EVENTOBJ_DEF, SIGN_DEF, GARRISON_DEF, ARTIFACT_DEF, WITCHHUT_DEF, SCHOLAR_DEF, PLAYERONLY_DEF, 
 	SHRINE_DEF, SPELLSCROLL_DEF, PANDORA_DEF, GRAIL_DEF, CREGEN_DEF, CREGEN2_DEF, CREGEN3_DEF, 
 	BORDERGUARD_DEF, HEROPLACEHOLDER_DEF};
-class DLL_EXPORT CSpecObjInfo //class with object - specific info (eg. different information for creatures and heroes); use inheritance to make object - specific classes
-{
-};
-class DLL_EXPORT CEventObjInfo : public CSpecObjInfo
-{
-public:
-	bool areGuarders; //true if there are
-	CCreatureSet guarders;
-	bool isMessage; //true if there is a message
-	std::string message;
-	unsigned int gainedExp;
-	int manaDiff; //amount of gained / lost mana
-	int moraleDiff; //morale modifier
-	int luckDiff; //luck modifier
-	int wood, mercury, ore, sulfur, crystal, gems, gold; //gained / lost resources
-	unsigned int attack; //added attack points
-	unsigned int defence; //added defence points
-	unsigned int power; //added power points
-	unsigned int knowledge; //added knowledge points
-	std::vector<int> abilities; //gained abilities
-	std::vector<int> abilityLevels; //levels of gained abilities
-	std::vector<int> artifacts; //gained artifacts
-	std::vector<int> spells; //gained spells
-	CCreatureSet creatures; //gained creatures
-	unsigned char availableFor; //players whom this event is available for
-	bool computerActivate; //true if computre player can activate this event
-	bool humanActivate; //true if human player can activate this event
-};
-class DLL_EXPORT CCreatureObjInfo : public CSpecObjInfo
-{
-public:
-	unsigned char bytes[4]; //mysterious bytes identifying creature
-	unsigned int number; //number of units (0 - random)
-	unsigned char character; //chracter of this set of creatures (0 - the most friendly, 4 - the most hostile)
-	std::string message; //message printed for attacking hero
-	int wood, mercury, ore, sulfur, crytal, gems, gold; //resources gained to hero that has won with monsters
-	int gainedArtifact; //ID of artifact gained to hero
-	bool neverFlees; //if true, the troops will never flee
-	bool notGrowingTeam; //if true, number of units won't grow
-};
-class DLL_EXPORT CSignObjInfo : public CSpecObjInfo
-{
-public:
-	std::string message; //message
-};
-class DLL_EXPORT CSeerHutObjInfo : public CSpecObjInfo
-{
-public:
-	unsigned char missionType; //type of mission: 0 - no mission; 1 - reach level; 2 - reach main statistics values; 3 - win with a certain hero; 4 - win with a certain creature; 5 - collect some atifacts; 6 - have certain troops in army; 7 - collect resources; 8 - be a certain hero; 9 - be a certain player
-	bool isDayLimit; //if true, there is a day limit
-	int lastDay; //after this day (first day is 0) mission cannot be completed
-	int m1level; //for mission 1	
-	int m2attack, m2defence, m2power, m2knowledge;//for mission 2
-	unsigned char m3bytes[4];//for mission 3
-	unsigned char m4bytes[4];//for mission 4
-	std::vector<int> m5arts;//for mission 5 - artifact ID
-	std::vector<CCreature *> m6cre;//for mission 6
-	std::vector<int> m6number;
-	int m7wood, m7mercury, m7ore, m7sulfur, m7crystal, m7gems, m7gold;	//for mission 7
-	int m8hero;//for mission 8 - hero ID
-	int m9player; //for mission 9 - number; from 0 to 7
 
-	std::string firstVisitText, nextVisitText, completedText;
-
-	char rewardType; //type of reward: 0 - no reward; 1 - experience; 2 - mana points; 3 - morale bonus; 4 - luck bonus; 5 - resources; 6 - main ability bonus (attak, defence etd.); 7 - secondary ability gain; 8 - artifact; 9 - spell; 10 - creature
-	//for reward 1
-	int r1exp;
-	//for reward 2
-	int r2mana;
-	//for reward 3
-	int r3morale;
-	//for reward 4
-	int r4luck;
-	//for reward 5
-	unsigned char r5type; //0 - wood, 1 - mercury, 2 - ore, 3 - sulfur, 4 - crystal, 5 - gems, 6 - gold
-	int r5amount;
-	//for reward 6
-	unsigned char r6type; //0 - attack, 1 - defence, 2 - power, 3 - knowledge
-	int r6amount;
-	//for reward 7
-	int r7ability; //ability id
-	unsigned char r7level; //1 - basic, 2 - advanced, 3 - expert
-	//for reward 8
-	int r8art;//artifact id
-	//for reward 9
-	int r9spell;//spell id
-	//for reward 10
-	int r10creature; //creature id
-	int r10amount;
-};
-class DLL_EXPORT CWitchHutObjInfo : public CSpecObjInfo
-{
-public:
-	std::vector<int> allowedAbilities;
-};
-class DLL_EXPORT CScholarObjInfo : public CSpecObjInfo
-{
-public:
-	unsigned char bonusType; //255 - random, 0 - primary skill, 1 - secondary skill, 2 - spell
-
-	unsigned char r0type;
-	int r1; //Ability ID
-	int r2; //Spell ID
-};
-class DLL_EXPORT CGarrisonObjInfo : public CSpecObjInfo
-{
-public:
-	unsigned char player; //255 - nobody; 0 - 7 - players
-	CCreatureSet units;
-	bool movableUnits; //if true, units can be moved
-};
-class DLL_EXPORT CArtifactObjInfo : public CSpecObjInfo
-{
-public:
-	bool areGuards;
-	std::string message;
-	CCreatureSet guards;
-};
-class DLL_EXPORT CResourceObjInfo : public CSpecObjInfo
-{
-public:
-	bool randomAmount;
-	int amount; //if not random
-	bool areGuards;
-	CCreatureSet guards;
-	std::string message;
-};
-class DLL_EXPORT CPlayerOnlyObjInfo : public CSpecObjInfo
+class DLL_EXPORT CSpecObjInfo
 {
 public:
-	unsigned char player; //FF - nobody, 0 - 7
-};
-class DLL_EXPORT CShrineObjInfo : public CSpecObjInfo
-{
-public:
-	unsigned char spell; //number of spell or 255
-};
-class DLL_EXPORT CSpellScrollObjinfo : public CSpecObjInfo
-{
-public:
-	std::string message;
-	int spell;
-	bool areGuarders;
-	CCreatureSet guarders;
+	virtual ~CSpecObjInfo(){};
 };
-class DLL_EXPORT CPandorasBoxObjInfo : public CSpecObjInfo
-{
-public:
-	std::string message;
-	bool areGuarders;
-	CCreatureSet guarders;
 
-	//gained things:
-	unsigned int gainedExp;
-	int manaDiff;
-	int moraleDiff;
-	int luckDiff;
-	int wood, mercury, ore, sulfur, crystal, gems, gold;
-	int attack, defence, power, knowledge;
-	std::vector<int> abilities;
-	std::vector<int> abilityLevels;
-	std::vector<int> artifacts;
-	std::vector<int> spells;
-	CCreatureSet creatures;
-};
-
-class DLL_EXPORT CGrailObjInfo : public CSpecObjInfo
-{
-public:
-	int radius; //place grail at the distance lesser or equal radius from this place
-};
 class DLL_EXPORT CCreGenObjInfo : public CSpecObjInfo
 {
 public:
@@ -211,34 +47,6 @@ public:
 	unsigned char player; //owner
 	unsigned char minLevel, maxLevel; //minimal and maximal level of creature in dwelling: <0, 6>
 };
-class DLL_EXPORT CBorderGuardObjInfo : public CSpecObjInfo //copied form seer huts, seems to be similar
-{
-public:
-	char missionType; //type of mission: 0 - no mission; 1 - reach level; 2 - reach main statistics values; 3 - win with a certain hero; 4 - win with a certain creature; 5 - collect some atifacts; 6 - have certain troops in army; 7 - collect resources; 8 - be a certain hero; 9 - be a certain player
-	bool isDayLimit; //if true, there is a day limit
-	int lastDay; //after this day (first day is 0) mission cannot be completed
-	//for mission 1
-	int m1level;
-	//for mission 2
-	int m2attack, m2defence, m2power, m2knowledge;
-	//for mission 3
-	unsigned char m3bytes[4];
-	//for mission 4
-	unsigned char m4bytes[4];
-	//for mission 5
-	std::vector<int> m5arts; //artifacts id
-	//for mission 6
-	std::vector<CCreature *> m6cre;
-	std::vector<int> m6number;
-	//for mission 7
-	int m7wood, m7mercury, m7ore, m7sulfur, m7crystal, m7gems, m7gold;
-	//for mission 8
-	int m8hero; //hero id
-	//for mission 9
-	int m9player; //number; from 0 to 7
-
-	std::string firstVisitText, nextVisitText, completedText;
-};
 
 struct DLL_EXPORT Sresource
 {
@@ -519,6 +327,9 @@ struct DLL_EXPORT Mapa
 	std::vector<bool> allowedHeroes; //allowedHeroes[hero_ID] - if the hero is allowed
 	std::vector<CMapEvent> events;
 
+	int3 grailPos;
+	int grailRadious;
+
 	std::vector<CGObjectInstance*> objects;
 	std::vector<CGHeroInstance*> heroes;
 	std::vector<CGTownInstance*> towns;
@@ -536,7 +347,7 @@ struct DLL_EXPORT Mapa
 	void loadPlayerInfo( int &pom, unsigned char * bufor, int &i);
 	void loadHero( CGObjectInstance * &nobj, unsigned char * bufor, int &i);
 	void loadTown( CGObjectInstance * &nobj, unsigned char * bufor, int &i);
-	int loadSeerHut( unsigned char * bufor, int i, CGObjectInstance * nobj);
+	int loadSeerHut( unsigned char * bufor, int i, CGObjectInstance *& nobj);
 
 
 	void addBlockVisTiles(CGObjectInstance * obj);

+ 253 - 46
server/CGameHandler.cpp

@@ -1,5 +1,4 @@
 #include "../CGameState.h"
-#include "../CLua.h"
 #include "../StartInfo.h"
 #include "../hch/CArtHandler.h"
 #include "../hch/CBuildingHandler.h"
@@ -14,7 +13,6 @@
 #include "../lib/VCMI_Lib.h"
 #include "../map.h"
 #include "CGameHandler.h"
-#include "CScriptCallback.h"
 #include <boost/bind.hpp>
 #include <boost/date_time/posix_time/posix_time_types.hpp> //no i/o just types
 #include <boost/foreach.hpp>
@@ -170,15 +168,15 @@ void PlayerStatuses::removeQuery(ui8 player, ui32 id)
 	}
 	cv.notify_all();
 }
-void CGameHandler::handleCPPObjS(std::map<int,CCPPObjectScript*> * mapa, CCPPObjectScript * script)
-{
-	std::vector<int> tempv = script->yourObjects();
-	for (unsigned i=0;i<tempv.size();i++)
-	{
-		(*mapa)[tempv[i]]=script;
-	}
-	cppscripts.insert(script);
-}
+//void CGameHandler::handleCPPObjS(std::map<int,CCPPObjectScript*> * mapa, CCPPObjectScript * script)
+//{
+//	std::vector<int> tempv = script->yourObjects();
+//	for (unsigned i=0;i<tempv.size();i++)
+//	{
+//		(*mapa)[tempv[i]]=script;
+//	}
+//	cppscripts.insert(script);
+//}
 template <typename T>
 void callWith(std::vector<T> args, boost::function<void(T)> fun, ui32 which)
 {
@@ -413,7 +411,8 @@ void CGameHandler::handleConnection(std::set<int> players, CConnection &c)
 					std::string fname;
 					c >> fname;
 					CSaveFile save(fname);
-					save << VLC->heroh << this;
+					save << VLC->arth << VLC->buildh << VLC->creh << VLC->dobjinfo << VLC->heroh  
+						<< VLC->spellh << VLC->townh << this;
 					//save << this;
 					break;
 				}
@@ -486,8 +485,8 @@ void CGameHandler::handleConnection(std::set<int> players, CConnection &c)
 							{
 								//if(gs->checkFunc(obj->ID,"heroVisit")) //script function
 								//	gs->objscr[obj->ID]["heroVisit"]->onHeroVisit(obj,h->subID);
-								if(obj->state) //hard-coded function
-									obj->state->onHeroVisit(obj->id,h->id);
+								//if(obj->state) //hard-coded function
+									obj->onHeroVisit(h);
 							}
 						}
 						tlog5 << "Blocing visit at " << hmpos << std::endl;
@@ -500,8 +499,8 @@ void CGameHandler::handleConnection(std::set<int> players, CConnection &c)
 						BOOST_FOREACH(CGObjectInstance *obj, gs->map->terrain[start.x-1][start.y][start.z].visitableObjects)
 						{
 							//TODO: allow to handle this in script-languages
-							if(obj->state) //hard-coded function
-								obj->state->onHeroLeave(obj->id,h->id);
+							//if(obj->state) //hard-coded function
+								obj->onHeroLeave(h);
 						}
 						tmh.fowRevealed = gs->tilesToReveal(h->getPosition(false),h->getSightDistance(),h->tempOwner);
 						sendAndApply(&tmh);
@@ -511,8 +510,8 @@ void CGameHandler::handleConnection(std::set<int> players, CConnection &c)
 						{
 							//if(gs->checkFunc(obj->ID,"heroVisit")) //script function
 							//	gs->objscr[obj->ID]["heroVisit"]->onHeroVisit(obj,h->subID);
-							if(obj->state) //hard-coded function
-								obj->state->onHeroVisit(obj->id,h->id);
+							//if(obj->state) //hard-coded function
+								obj->onHeroVisit(h);
 						}
 					}
 					tlog5 << "Movement end!\n";
@@ -1510,12 +1509,17 @@ CGameHandler::~CGameHandler(void)
 }
 void CGameHandler::init(StartInfo *si, int Seed)
 {
+	IObjectInterface::cb = this;
 	Mapa *map = new Mapa(si->mapname);
 	tlog0 << "Map loaded!" << std::endl;
 	gs = new CGameState();
 	tlog0 << "Gamestate created!" << std::endl;
 	gs->init(si,map,Seed);	
 	tlog0 << "Gamestate initialized!" << std::endl;
+
+
+	for(int i=0; i<gs->map->objects.size(); i++)
+		gs->map->objects[i]->initObj();
 	/****************************LUA OBJECT SCRIPTS************************************************/
 	//std::vector<std::string> * lf = CLuaHandler::searchForScripts("scripts/lua/objects"); //files
 	//for (int i=0; i<lf->size(); i++)
@@ -1622,10 +1626,8 @@ void CGameHandler::newTurn()
 	}	
 	sendAndApply(&n);
 	tlog5 << "Info about turn " << n.day << "has been sent!" << std::endl;
-	for (std::set<CCPPObjectScript *>::iterator i=cppscripts.begin();i!=cppscripts.end();i++)
-	{
-		(*i)->newTurn();
-	}
+	for(size_t i = 0; i<gs->map->objects.size(); i++)
+		gs->map->objects[i]->newTurn();
 }
 void CGameHandler::run()
 {	
@@ -1657,38 +1659,38 @@ void CGameHandler::run()
 	/****************************SCRIPTS************************************************/
 	//std::map<int, std::map<std::string, CObjectScript*> > * skrypty = &objscr; //alias for easier access
 	/****************************C++ OBJECT SCRIPTS************************************************/
-	std::map<int,CCPPObjectScript*> scripts;
-	CScriptCallback * csc = new CScriptCallback();
-	csc->gh = this;
-	handleCPPObjS(&scripts,new CVisitableOPH(csc));
-	handleCPPObjS(&scripts,new CVisitableOPW(csc));
-	handleCPPObjS(&scripts,new CPickable(csc));
-	handleCPPObjS(&scripts,new CMines(csc));
-	handleCPPObjS(&scripts,new CTownScript(csc));
-	handleCPPObjS(&scripts,new CHeroScript(csc));
-	handleCPPObjS(&scripts,new CMonsterS(csc));
-	handleCPPObjS(&scripts,new CCreatureGen(csc));
-	handleCPPObjS(&scripts,new CTeleports(csc));
+	//std::map<int,CCPPObjectScript*> scripts;
+	//CScriptCallback * csc = new CScriptCallback();
+	//csc->gh = this;
+	//handleCPPObjS(&scripts,new CVisitableOPH(csc));
+	//handleCPPObjS(&scripts,new CVisitableOPW(csc));
+	//handleCPPObjS(&scripts,new CPickable(csc));
+	//handleCPPObjS(&scripts,new CMines(csc));
+	//handleCPPObjS(&scripts,new CTownScript(csc));
+	//handleCPPObjS(&scripts,new CHeroScript(csc));
+	//handleCPPObjS(&scripts,new CMonsterS(csc));
+	//handleCPPObjS(&scripts,new CCreatureGen(csc));
+	//handleCPPObjS(&scripts,new CTeleports(csc));
 
 	/****************************INITIALIZING OBJECT SCRIPTS************************************************/
 	//std::string temps("newObject");
-	for (unsigned i=0; i<gs->map->objects.size(); i++)
-	{
+	//for (unsigned i=0; i<gs->map->objects.size(); i++)
+	//{
 		//c++ scripts
-		if (scripts.find(gs->map->objects[i]->ID) != scripts.end())
-		{
-			gs->map->objects[i]->state = scripts[gs->map->objects[i]->ID];
-			gs->map->objects[i]->state->newObject(gs->map->objects[i]->id);
-		}
-		else 
-		{
-			gs->map->objects[i]->state = NULL;
-		}
+		//if (scripts.find(gs->map->objects[i]->ID) != scripts.end())
+		//{
+		//	gs->map->objects[i]->state = scripts[gs->map->objects[i]->ID];
+		//	gs->map->objects[i]->state->newObject(gs->map->objects[i]->id);
+		//}
+		//else 
+		//{
+		//	gs->map->objects[i]->state = NULL;
+		//}
 
 		//// lua scripts
 		//if(checkFunc(map->objects[i]->ID,temps))
 		//	(*skrypty)[map->objects[i]->ID][temps]->newObject(map->objects[i]);
-	}
+	//}
 	for(std::map<ui8,PlayerState>::iterator i = gs->players.begin(); i != gs->players.end(); i++)
 		states.addPlayer(i->first);
 
@@ -1905,3 +1907,208 @@ void CGameHandler::giveSpells( const CGTownInstance *t, const CGHeroInstance *h
 	if(cs.spells.size())
 		sendAndApply(&cs);
 }
+
+void CGameHandler::setBlockVis(int objid, bool bv)
+{
+	SetObjectProperty sop(objid,2,bv);
+	sendAndApply(&sop);
+}
+void CGameHandler::removeObject(int objid)
+{
+	RemoveObject ro;
+	ro.id = objid;
+	sendAndApply(&ro);
+}
+
+void CGameHandler::setAmount(int objid, ui32 val)
+{
+	SetObjectProperty sop(objid,3,val);
+	sendAndApply(&sop);
+}
+
+void CGameHandler::moveHero(int hid, int3 pos, bool instant)
+{
+	if(!instant)
+	{
+		tlog1 << "Not supported call to CGameHandler::moveHero\n";
+		return;
+	}
+	CGHeroInstance *h = const_cast<CGHeroInstance *>(getHero(hid));
+	//check if destination tile is free
+	BOOST_FOREACH(CGObjectInstance* obj, gs->map->terrain[pos.x-1][pos.y][pos.z].blockingObjects)
+	{
+		if(obj->ID==34)
+		{
+			if(obj->tempOwner==h->tempOwner) 
+				return;//TODO: exchange
+			//TODO: check for ally
+			CGHeroInstance *dh = static_cast<CGHeroInstance *>(obj);
+			startBattleI(&h->army,&dh->army,pos,h,dh,0);
+			return;
+		}
+	}
+	TryMoveHero tmh;
+	tmh.start = h->pos;
+	tmh.end = pos;
+	tmh.id = hid;
+	tmh.movePoints = h->movement;
+	tmh.result = instant+1;
+	tmh.fowRevealed = gs->tilesToReveal(CGHeroInstance::convertPosition(pos,false),h->getSightDistance(),h->tempOwner);
+	sendAndApply(&tmh);
+}
+
+void CGameHandler::setOwner(int objid, ui8 owner)
+{
+	SetObjectProperty sop(objid,1,owner);
+	sendAndApply(&sop);
+}
+const CGObjectInstance* CGameHandler::getObj(int objid)
+{
+	return gs->map->objects[objid];
+}
+const CGHeroInstance* CGameHandler::getHero(int objid)
+{
+	return dynamic_cast<const CGHeroInstance*>(gs->map->objects[objid]);
+}
+const CGTownInstance* CGameHandler::getTown(int objid)
+{
+	return dynamic_cast<const CGTownInstance*>(gs->map->objects[objid]);
+}
+void CGameHandler::setHoverName(int objid, MetaString* name)
+{
+	SetHoverName shn(objid, *name);
+	sendAndApply(&shn);
+}
+
+int CGameHandler::getOwner(int heroID)
+{
+	return gs->map->objects[heroID]->tempOwner;
+}
+int CGameHandler::getResource(int player, int which)
+{
+	return gs->players.find(player)->second.resources[which];
+}
+void CGameHandler::showInfoDialog(InfoWindow *iw)
+{
+	sendToAllClients(iw);
+}
+void CGameHandler::showYesNoDialog( YesNoDialog *iw, const CFunctionList<void(ui32)> &callback )
+{
+	ask(iw,iw->player,callback);
+}
+void CGameHandler::showSelectionDialog(SelectionDialog *iw, const CFunctionList<void(ui32)> &callback)
+{
+	ask(iw,iw->player,callback);
+}
+
+int CGameHandler::getSelectedHero()
+{	
+	//int ret;
+	//if (LOCPLINT->adventureInt->selection->ID == HEROI_TYPE)
+	//	ret = ((CGHeroInstance*)(LOCPLINT->adventureInt->selection))->subID;
+	//else 
+	//	ret = -1;;
+	return -1;
+}
+
+const CGHeroInstance* CGameHandler::getSelectedHero( int player )
+{
+	return getHero(gs->players.find(player)->second.currentSelection);
+}
+
+int CGameHandler::getDate(int mode)
+{
+	return getDate(mode);
+}
+void CGameHandler::giveResource(int player, int which, int val)
+{
+	SetResource sr;
+	sr.player = player;
+	sr.resid = which;
+	sr.val = (gs->players.find(player)->second.resources[which]+val);
+	sendAndApply(&sr);
+}
+void CGameHandler::showCompInfo(ShowInInfobox * comp)
+{
+	sendToAllClients(comp);
+}
+void CGameHandler::heroVisitCastle(int obj, int heroID)
+{
+	HeroVisitCastle vc;
+	vc.hid = heroID;
+	vc.tid = obj;
+	vc.flags |= 1;
+	sendAndApply(&vc);
+	giveSpells(getTown(obj),getHero(heroID));
+}
+
+void CGameHandler::stopHeroVisitCastle(int obj, int heroID)
+{
+	HeroVisitCastle vc;
+	vc.hid = heroID;
+	vc.tid = obj;
+	sendAndApply(&vc);
+}
+void CGameHandler::giveHeroArtifact(int artid, int hid, int position) //pos==-1 - first free slot in backpack
+{
+	const CGHeroInstance* h = getHero(hid);
+
+	SetHeroArtifacts sha;
+	sha.hid = hid;
+	sha.artifacts = h->artifacts;
+	sha.artifWorn = h->artifWorn;
+	if(position<0)
+	{
+		if(position == -2)
+		{
+			int i;
+			for(i=0; i<VLC->arth->artifacts[artid].possibleSlots.size(); i++) //try to put artifact into first avaialble slot
+			{
+				if( !vstd::contains(sha.artifWorn,VLC->arth->artifacts[artid].possibleSlots[i]) )
+				{
+					sha.artifWorn[VLC->arth->artifacts[artid].possibleSlots[i]] = artid;
+					break;
+				}
+			}
+			if(i==VLC->arth->artifacts[artid].possibleSlots.size()) //if haven't find proper slot, use backpack
+				sha.artifacts.push_back(artid);
+		}
+		else //should be -1 => putartifact into backpack
+		{
+			sha.artifacts.push_back(artid);
+		}
+	}
+	else
+	{
+		if(!vstd::contains(sha.artifWorn,ui16(position)))
+			sha.artifWorn[position] = artid;
+		else
+			sha.artifacts.push_back(artid);
+	}
+	sendAndApply(&sha);
+}
+
+void CGameHandler::startBattleI(const CCreatureSet * army1, const CCreatureSet * army2, int3 tile, const CGHeroInstance *hero1, const CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb) //use hero=NULL for no hero
+{
+	boost::thread(boost::bind(&CGameHandler::startBattle,this,*(CCreatureSet *)army1,*(CCreatureSet *)army2,tile,(CGHeroInstance *)hero1,(CGHeroInstance *)hero2,cb));
+}
+void CGameHandler::startBattleI(int heroID, CCreatureSet army, int3 tile, boost::function<void(BattleResult*)> cb) //for hero<=>neutral army
+{
+	CGHeroInstance* h = const_cast<CGHeroInstance*>(getHero(heroID));
+	startBattleI(&h->army,&army,tile,h,NULL,cb);
+	//battle(&h->army,army,tile,h,NULL);
+}
+
+void CGameHandler::changeSpells( int hid, bool give, const std::set<ui32> &spells )
+{
+	ChangeSpells cs;
+	cs.hid = hid;
+	cs.spells = spells;
+	cs.learn = give;
+	sendAndApply(&cs);
+}
+
+int CGameHandler::getCurrentPlayer()
+{
+	return gs->currentPlayer;
+}

+ 40 - 6
server/CGameHandler.h

@@ -7,6 +7,7 @@
 #include "../client/FunctionList.h"
 #include "../CGameState.h"
 #include "../lib/Connection.h"
+#include "../lib/IGameCallback.h"
 #include <boost/function.hpp>
 #include <boost/thread.hpp>
 class CVCMIServer;
@@ -53,11 +54,12 @@ public:
 		h & players;
 	}
 };
-class CGameHandler
+
+class CGameHandler : public IGameCallback
 {
 	static ui32 QID;
 	CGameState *gs;
-	std::set<CCPPObjectScript *> cppscripts; //C++ scripts
+	//std::set<CCPPObjectScript *> cppscripts; //C++ scripts
 	//std::map<int, std::map<std::string, CObjectScript*> > objscr; //non-C++ scripts 
 
 	CVCMIServer *s;
@@ -65,26 +67,58 @@ class CGameHandler
 	PlayerStatuses states; //player color -> player state
 	std::set<CConnection*> conns;
 
-	void handleCPPObjS(std::map<int,CCPPObjectScript*> * mapa, CCPPObjectScript * script);
-	void changePrimSkill(int ID, int which, int val, bool abs=false);
 	void changeSecSkill(int ID, ui16 which, int val, bool abs=false);
 	void giveSpells(const CGTownInstance *t, const CGHeroInstance *h);
 	void moveStack(int stack, int dest);
 	void startBattle(CCreatureSet army1, CCreatureSet army2, int3 tile, CGHeroInstance *hero1, CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb); //use hero=NULL for no hero
 	void prepareAttack(BattleAttack &bat, CStack *att, CStack *def); //if last parameter is true, attack is by shooting, if false it's a melee attack
 	void prepareAttacked(BattleStackAttacked &bsa, CStack *def);
-
 	void checkForBattleEnd( std::vector<CStack*> &stacks );
 	void setupBattle( BattleInfo * curB, int3 tile, CCreatureSet &army1, CCreatureSet &army2, CGHeroInstance * hero1, CGHeroInstance * hero2 );
 
 public:
 	CGameHandler(void);
 	~CGameHandler(void);
+
+	//////////////////////////////////////////////////////////////////////////
+	//from IGameCallback
+	//get info
+	int getOwner(int heroID);
+	int getResource(int player, int which);
+	int getSelectedHero();
+	int getDate(int mode=0);
+	const CGObjectInstance* getObj(int objid);
+	const CGHeroInstance* getHero(int objid);
+	const CGTownInstance* getTown(int objid);
+	const CGHeroInstance* getSelectedHero(int player); //NULL if no hero is selected
+	int getCurrentPlayer();
+
+	//do sth
+	void changeSpells(int hid, bool give, const std::set<ui32> &spells);
+	void removeObject(int objid);
+	void setBlockVis(int objid, bool bv);
+	void setOwner(int objid, ui8 owner);
+	void setHoverName(int objid, MetaString * name);
+	void changePrimSkill(int ID, int which, int val, bool abs=false);
+	void showInfoDialog(InfoWindow *iw);
+	void showYesNoDialog(YesNoDialog *iw, const CFunctionList<void(ui32)> &callback);
+	void showSelectionDialog(SelectionDialog *iw, const CFunctionList<void(ui32)> &callback); //returns question id
+	void giveResource(int player, int which, int val);
+	void showCompInfo(ShowInInfobox * comp);
+	void heroVisitCastle(int obj, int heroID);
+	void stopHeroVisitCastle(int obj, int heroID);
+	void giveHeroArtifact(int artid, int hid, int position); //pos==-1 - first free slot in backpack; pos==-2 - default if available or backpack
+	void startBattleI(const CCreatureSet * army1, const CCreatureSet * army2, int3 tile, const CGHeroInstance *hero1, const CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb); //use hero=NULL for no hero
+	void startBattleI(int heroID, CCreatureSet army, int3 tile, boost::function<void(BattleResult*)> cb); //for hero<=>neutral army
+	void setAmount(int objid, ui32 val);
+	void moveHero(int hid, int3 pos, bool instant);
+	//////////////////////////////////////////////////////////////////////////
+
 	void init(StartInfo *si, int Seed);
 	void handleConnection(std::set<int> players, CConnection &c);
 	template <typename Handler> void serialize(Handler &h, const int version)
 	{
-		h & QID & gs & cppscripts & states;
+		h & QID & gs & states;
 	}
 	template <typename T> void applyAndAsk(Query<T> * sel, ui8 player, boost::function<void(ui32)> &callback)
 	{

+ 0 - 292
server/CScriptCallback.cpp

@@ -1,292 +0,0 @@
-#include "CScriptCallback.h"
-#include "../lib/Connection.h"
-#include "CVCMIServer.h"
-#include "CGameHandler.h"
-#include "../CGameState.h"
-#include "../map.h"
-#include "../hch/CArtHandler.h"
-#include "../hch/CObjectHandler.h"
-#include "../hch/CTownHandler.h"
-#include "../hch/CHeroHandler.h"
-#include "../lib/NetPacks.h"
-#include "../lib/VCMI_Lib.h"
-#include <boost/bind.hpp>
-#include <boost/foreach.hpp>
-#include <boost/thread.hpp>
-
-
-CScriptCallback::CScriptCallback(void)
-{
-}
-
-CScriptCallback::~CScriptCallback(void)
-{
-}
-void CScriptCallback::setBlockVis(int objid, bool bv)
-{
-	SetObjectProperty sop(objid,2,bv);
-	gh->sendAndApply(&sop);
-}
-void CScriptCallback::removeObject(int objid)
-{
-	RemoveObject ro;
-	ro.id = objid;
-	gh->sendAndApply(&ro);
-}
-
-void CScriptCallback::setAmount(int objid, ui32 val)
-{
-	SetObjectProperty sop(objid,3,val);
-	gh->sendAndApply(&sop);
-}
-
-void CScriptCallback::moveHero(int hid, int3 pos, bool instant)
-{
-	if(!instant)
-	{
-		tlog1 << "Not supported call to CScriptCallback::moveHero\n";
-		return;
-	}
-	CGHeroInstance *h = const_cast<CGHeroInstance *>(getHero(hid));
-	//check if destination tile is free
-	BOOST_FOREACH(CGObjectInstance* obj, gh->gs->map->terrain[pos.x-1][pos.y][pos.z].blockingObjects)
-	{
-		if(obj->ID==34)
-		{
-			if(obj->tempOwner==h->tempOwner) 
-				return;//TODO: exchange
-			//TODO: check for ally
-			CGHeroInstance *dh = static_cast<CGHeroInstance *>(obj);
-			startBattle(&h->army,&dh->army,pos,h,dh,0);
-			return;
-		}
-	}
-	TryMoveHero tmh;
-	tmh.start = h->pos;
-	tmh.end = pos;
-	tmh.id = hid;
-	tmh.movePoints = h->movement;
-	tmh.result = instant+1;
-	tmh.fowRevealed = gh->gs->tilesToReveal(CGHeroInstance::convertPosition(pos,false),h->getSightDistance(),h->tempOwner);
-	gh->sendAndApply(&tmh);
-}
-
-void CScriptCallback::setOwner(int objid, ui8 owner)
-{
-	SetObjectProperty sop(objid,1,owner);
-	gh->sendAndApply(&sop);
-}
-const CGObjectInstance* CScriptCallback::getObj(int objid)
-{
-	return gh->gs->map->objects[objid];
-}
-const CGHeroInstance* CScriptCallback::getHero(int objid)
-{
-	return static_cast<const CGHeroInstance*>(gh->gs->map->objects[objid]);
-}
-const CGTownInstance* CScriptCallback::getTown(int objid)
-{
-	return static_cast<const CGTownInstance*>(gh->gs->map->objects[objid]);
-}
-void CScriptCallback::setHoverName(int objid, MetaString* name)
-{
-	SetHoverName shn(objid, *name);
-	gh->sendAndApply(&shn);
-}
-int3 CScriptCallback::getPos(CGObjectInstance * ob)
-{
-	return ob->pos;
-}
-void CScriptCallback::changePrimSkill(int ID, int which, int val, bool abs)
-{
-	gh->changePrimSkill(ID, which, val, abs);
-}
-
-int CScriptCallback::getOwner(int heroID)
-{
-	return gh->gs->map->objects[heroID]->tempOwner;
-}
-int CScriptCallback::getResource(int player, int which)
-{
-	return gh->gs->players[player].resources[which];
-}
-void CScriptCallback::showInfoDialog(InfoWindow *iw)
-{
-	gh->sendToAllClients(iw);
-}
-void CScriptCallback::showYesNoDialog( YesNoDialog *iw, const CFunctionList<void(ui32)> &callback )
-{
-	gh->ask(iw,iw->player,callback);
-}
-void CScriptCallback::showSelectionDialog(SelectionDialog *iw, const CFunctionList<void(ui32)> &callback)
-{
-	gh->ask(iw,iw->player,callback);
-}
-
-int CScriptCallback::getSelectedHero()
-{	
-	//int ret;
-	//if (LOCPLINT->adventureInt->selection->ID == HEROI_TYPE)
-	//	ret = ((CGHeroInstance*)(LOCPLINT->adventureInt->selection))->subID;
-	//else 
-	//	ret = -1;;
-	return -1;
-}
-int CScriptCallback::getDate(int mode)
-{
-	return gh->gs->getDate(mode);
-}
-void CScriptCallback::giveResource(int player, int which, int val)
-{
-	SetResource sr;
-	sr.player = player;
-	sr.resid = which;
-	sr.val = (gh->gs->players[player].resources[which]+val);
-	gh->sendAndApply(&sr);
-}
-void CScriptCallback::showCompInfo(ShowInInfobox * comp)
-{
-	gh->sendToAllClients(comp);
-}
-void CScriptCallback::heroVisitCastle(int obj, int heroID)
-{
-	HeroVisitCastle vc;
-	vc.hid = heroID;
-	vc.tid = obj;
-	vc.flags |= 1;
-	gh->sendAndApply(&vc);
-	gh->giveSpells(getTown(obj),getHero(heroID));
-}
-
-void CScriptCallback::stopHeroVisitCastle(int obj, int heroID)
-{
-	HeroVisitCastle vc;
-	vc.hid = heroID;
-	vc.tid = obj;
-	gh->sendAndApply(&vc);
-}
-void CScriptCallback::giveHeroArtifact(int artid, int hid, int position) //pos==-1 - first free slot in backpack
-{
-	const CGHeroInstance* h = getHero(hid);
-
-	SetHeroArtifacts sha;
-	sha.hid = hid;
-	sha.artifacts = h->artifacts;
-	sha.artifWorn = h->artifWorn;
-	if(position<0)
-	{
-		if(position == -2)
-		{
-			int i;
-			for(i=0; i<VLC->arth->artifacts[artid].possibleSlots.size(); i++) //try to put artifact into first avaialble slot
-			{
-				if( !vstd::contains(sha.artifWorn,VLC->arth->artifacts[artid].possibleSlots[i]) )
-				{
-					sha.artifWorn[VLC->arth->artifacts[artid].possibleSlots[i]] = artid;
-					break;
-				}
-			}
-			if(i==VLC->arth->artifacts[artid].possibleSlots.size()) //if haven't find proper slot, use backpack
-				sha.artifacts.push_back(artid);
-		}
-		else //should be -1 => putartifact into backpack
-		{
-			sha.artifacts.push_back(artid);
-		}
-	}
-	else
-	{
-		if(!vstd::contains(sha.artifWorn,ui16(position)))
-			sha.artifWorn[position] = artid;
-		else
-			sha.artifacts.push_back(artid);
-	}
-	gh->sendAndApply(&sha);
-}
-
-void CScriptCallback::startBattle(const CCreatureSet * army1, const CCreatureSet * army2, int3 tile, const CGHeroInstance *hero1, const CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb) //use hero=NULL for no hero
-{
-	boost::thread(boost::bind(&CGameHandler::startBattle,gh,*(CCreatureSet *)army1,*(CCreatureSet *)army2,tile,(CGHeroInstance *)hero1,(CGHeroInstance *)hero2,cb));
-}
-void CScriptCallback::startBattle(int heroID, CCreatureSet army, int3 tile, boost::function<void(BattleResult*)> cb) //for hero<=>neutral army
-{
-	CGHeroInstance* h = const_cast<CGHeroInstance*>(getHero(heroID));
-	startBattle(&h->army,&army,tile,h,NULL,cb);
-	//gh->gs->battle(&h->army,army,tile,h,NULL);
-}
-
-void CScriptCallback::changeSpells( int hid, bool give, const std::set<ui32> &spells )
-{
-	ChangeSpells cs;
-	cs.hid = hid;
-	cs.spells = spells;
-	cs.learn = give;
-	gh->sendAndApply(&cs);
-}
-void CLuaCallback::registerFuncs(lua_State * L)
-{
-//	lua_newtable(L);
-//
-//#define REGISTER_C_FUNC(x) \
-//	lua_pushstring(L, #x);      \
-//	lua_pushcfunction(L, x);    \
-//	lua_rawset(L, -3)
-//
-//	REGISTER_C_FUNC(getPos);
-//	REGISTER_C_FUNC(changePrimSkill);
-//	REGISTER_C_FUNC(getGnrlText);
-//	REGISTER_C_FUNC(getSelectedHero);
-//
-//	lua_setglobal(L, "vcmi");
-//	#undef REGISTER_C_FUNC
-}
-int CLuaCallback::getPos(lua_State * L)//(CGObjectInstance * object);
-{	
-	//const int args = lua_gettop(L); // number of arguments
-	//if ((args < 1) || !lua_isnumber(L, 1) )
-	//	luaL_error(L,
-	//		"Incorrect arguments to getPos([Object address])");
-	//CGObjectInstance * object = (CGObjectInstance *)(lua_tointeger(L, 1));
-	//lua_pushinteger(L,object->pos.x);
-	//lua_pushinteger(L,object->pos.y);
-	//lua_pushinteger(L,object->pos.z);
-	return 3;
-}
-int CLuaCallback::changePrimSkill(lua_State * L)//(int ID, int which, int val);
-{	
-	//const int args = lua_gettop(L); // number of arguments
-	//if ((args < 1) || !lua_isnumber(L, 1) ||
-	//    ((args >= 2) && !lua_isnumber(L, 2)) ||
-	//    ((args >= 3) && !lua_isnumber(L, 3))		)
-	//{
-	//	luaL_error(L,
-	//		"Incorrect arguments to changePrimSkill([Hero ID], [Which Primary skill], [Change by])");
-	//}
-	//int ID = lua_tointeger(L, 1),
-	//	which = lua_tointeger(L, 2),
-	//	val = lua_tointeger(L, 3);
-
-	//CScriptCallback::changePrimSkill(ID,which,val);
-
-	return 0;
-}
-int CLuaCallback::getGnrlText(lua_State * L) //(int which),returns string
-{
-	//const int args = lua_gettop(L); // number of arguments
-	//if ((args < 1) || !lua_isnumber(L, 1) )
-	//	luaL_error(L,
-	//		"Incorrect arguments to getGnrlText([Text ID])");
-	//int which = lua_tointeger(L,1);
-	//lua_pushstring(L,CGI->generaltexth->allTexts[which].c_str());
-	return 1;
-}
-int CLuaCallback::getSelectedHero(lua_State * L) //(),returns int (ID of hero, -1 if no hero is seleceted)
-{
-	//int ret;
-	//if (LOCPLINT->adventureInt->selection->ID == HEROI_TYPE)
-	//	ret = ((CGHeroInstance*)(LOCPLINT->adventureInt->selection))->subID;
-	//else 
-	//	ret = -1;
-	//lua_pushinteger(L,ret);
-	return 1;
-}

+ 0 - 75
server/CScriptCallback.h

@@ -1,75 +0,0 @@
-#pragma once
-#include "../global.h"
-#include <vector>
-#include <set>
-#include "../client/FunctionList.h"
-class CVCMIServer;
-class CGameHandler;
-class SComponent;
-class CSelectableComponent;
-class IChosen;
-class CCreatureSet;
-class CGHeroInstance;
-class CGObjectInstance;
-class CGHeroInstance;
-class CGTownInstance;
-class CGameState;
-struct lua_State;
-struct MetaString;
-struct InfoWindow;
-struct ShowInInfobox;
-struct SelectionDialog;
-struct YesNoDialog;
-struct BattleResult;
-class CScriptCallback
-{
-	CScriptCallback(void);
-public:
-	~CScriptCallback(void);
-	CGameHandler *gh;
-
-	//get info
-	static int3 getPos(CGObjectInstance * ob);
-	int getOwner(int heroID);
-	int getResource(int player, int which);
-	int getSelectedHero();
-	int getDate(int mode=0);
-	const CGObjectInstance* getObj(int objid);
-	const CGHeroInstance* getHero(int objid);
-	const CGTownInstance* getTown(int objid);
-
-	//do sth
-	void changeSpells(int hid, bool give, const std::set<ui32> &spells);
-	void removeObject(int objid);
-	void setBlockVis(int objid, bool bv);
-	void setOwner(int objid, ui8 owner);
-	void setHoverName(int objid, MetaString * name);
-	void changePrimSkill(int ID, int which, int val, bool abs=false);
-	void showInfoDialog(InfoWindow *iw);
-	void showYesNoDialog(YesNoDialog *iw, const CFunctionList<void(ui32)> &callback);
-	void showSelectionDialog(SelectionDialog *iw, const CFunctionList<void(ui32)> &callback); //returns question id
-	void giveResource(int player, int which, int val);
-	void showCompInfo(ShowInInfobox * comp);
-	void heroVisitCastle(int obj, int heroID);
-	void stopHeroVisitCastle(int obj, int heroID);
-	void giveHeroArtifact(int artid, int hid, int position); //pos==-1 - first free slot in backpack; pos==-2 - default if available or backpack
-	void startBattle(const CCreatureSet * army1, const CCreatureSet * army2, int3 tile, const CGHeroInstance *hero1, const CGHeroInstance *hero2, boost::function<void(BattleResult*)> cb); //use hero=NULL for no hero
-	void startBattle(int heroID, CCreatureSet army, int3 tile, boost::function<void(BattleResult*)> cb); //for hero<=>neutral army
-	void setAmount(int objid, ui32 val);
-	void moveHero(int hid, int3 pos, bool instant);
-
-	//friends
-	friend class CGameHandler;
-};
-class CLuaCallback : public CScriptCallback
-{
-private:
-
-	static void registerFuncs(lua_State * L);
-	static int getPos(lua_State * L);//(CGObjectInstance * object);
-	static int changePrimSkill(lua_State * L);//(int ID, int which, int val);
-	static int getGnrlText(lua_State * L);//(int ID, int which, int val);
-	static int getSelectedHero(lua_State * L);//()
-
-	friend class CGameHandler;
-};

+ 0 - 16
server/VCMI_server.vcproj

@@ -253,14 +253,6 @@
 				RelativePath=".\CGameHandler.cpp"
 				>
 			</File>
-			<File
-				RelativePath="..\CLua.cpp"
-				>
-			</File>
-			<File
-				RelativePath=".\CScriptCallback.cpp"
-				>
-			</File>
 			<File
 				RelativePath=".\CVCMIServer.cpp"
 				>
@@ -275,14 +267,6 @@
 				RelativePath=".\CGameHandler.h"
 				>
 			</File>
-			<File
-				RelativePath="..\CLua.h"
-				>
-			</File>
-			<File
-				RelativePath=".\CScriptCallback.h"
-				>
-			</File>
 			<File
 				RelativePath=".\CVCMIServer.h"
 				>

برخی فایل ها در این مقایسه diff نمایش داده نمی شوند زیرا تعداد فایل ها بسیار زیاد است