浏览代码

To be released as 0.75d. Fixed town list with hotseat. Fixed colouring hero window. Minor fixes.

Michał W. Urbańczyk 15 年之前
父节点
当前提交
9588e39e84

+ 2 - 1
CCallback.cpp

@@ -328,7 +328,8 @@ std::vector < const CGTownInstance *> CCallback::getTownsInfo(bool onlyOur) cons
 	{
 		for (size_t j=0; j < (*i).second.towns.size(); ++j)
 		{
-			if ( ( isVisible((*i).second.towns[j],player) ) || (*i).first==player)
+			if ((*i).first==player  
+				|| (isVisible((*i).second.towns[j],player) && !onlyOur))
 			{
 				ret.push_back((*i).second.towns[j]);
 			}

+ 2 - 0
ChangeLog

@@ -3,6 +3,7 @@ GENERAL:
 * Victory and loss conditions are supported. It's now possible to win or lose the game.
 * Kingdom Overview screen is now available.
 * Replaced TTF fonts with original ones.
+* Implemented Grail (puzzle map, digging, constructing ultimate building)
 
 ADVENTURE MAP:
 * Implemented rivers animations (thx to GrayFace).
@@ -12,6 +13,7 @@ HERO:
 
 TOWN:
 * New left-bottom info panel functionalities.
+
 TOWNS:
 * new town structures supported:
 - Ballista Yard

+ 10 - 7
client/CAdvmapInterface.cpp

@@ -1442,7 +1442,8 @@ void CInfoBar::showComp(SComponent * comp, int time)
 	printAtMiddle(comp->subtitle,pos.x+91,pos.y+158,FONT_SMALL,zwykly);
 	printAtMiddleWB(comp->description,pos.x+94,pos.y+31,FONT_SMALL,26,zwykly);
 	SDL_FreeSurface(b);
-	activateTimer();
+	if(!(active & TIME))
+		activateTimer();
 	mode = 6;
 	toNextTick = time;
 }
@@ -1543,7 +1544,7 @@ townList(ADVOPT.tlistSize,ADVOPT.tlistX,ADVOPT.tlistY,ADVOPT.tlistAU,ADVOPT.tlis
 	heroList.init();
 	heroList.genList();
 	//townList.init();
-	townList.genList();
+	//townList.genList();
 
 	heroWindow = new CHeroWindow(this->player);
 
@@ -1643,7 +1644,8 @@ void CAdvMapInt::fnextHero()
 
 void CAdvMapInt::fendTurn()
 {
-	LOCPLINT->cingconsole->deactivate();
+	if(LOCPLINT->cingconsole->active)
+		LOCPLINT->cingconsole->deactivate();
 	LOCPLINT->makingTurn = false;
 	LOCPLINT->cb->endTurn();
 }
@@ -1795,7 +1797,7 @@ void CAdvMapInt::show(SDL_Surface *to)
 
 void CAdvMapInt::selectionChanged()
 {
-	const CGTownInstance *to = townList.items[townList.selected];
+	const CGTownInstance *to = LOCPLINT->towns[townList.selected];
 	select(to);
 }
 void CAdvMapInt::centerOn(int3 on)
@@ -1978,7 +1980,7 @@ void CAdvMapInt::select(const CArmedInstance *sel )
 	terrain.currentPath = NULL;
 	if(sel->ID==TOWNI_TYPE)
 	{
-		int pos = vstd::findPos(townList.items,sel);
+		int pos = vstd::findPos(LOCPLINT->towns,sel);
 		townList.selected = pos;
 		townList.fixPos();
 	}
@@ -2066,9 +2068,10 @@ void CAdvMapInt::setPlayer(int Player)
 	nextHero.setPlayerColor(player);
 	endTurn.setPlayerColor(player);
 	graphics->blueToPlayersAdv(resdatabar.bg,player);
+	heroWindow->setPlayer(player);
 
-	heroList.updateHList();
-	townList.genList();
+	//heroList.updateHList();
+	//townList.genList();
 }
 
 void CAdvMapInt::startTurn()

+ 5 - 5
client/CCastleInterface.cpp

@@ -444,12 +444,12 @@ CCastleInterface::CCastleInterface(const CGTownInstance * Town, int listPos)
 	resdatabar = new CResDataBar("ZRESBAR.bmp",pos.x+3,pos.y+575,32,2,85,85);
 
 	townlist->fun = boost::bind(&CCastleInterface::townChange,this);
-	townlist->genList();
-	townlist->selected = vstd::findPos(townlist->items,Town);
+	//townlist->genList();
+	townlist->selected = vstd::findPos(LOCPLINT->towns,Town);
 
 	townlist->from = townlist->selected - listPos;
 	amax(townlist->from, 0);
-	amin(townlist->from, townlist->items.size() - townlist->SIZE);
+	amin(townlist->from, LOCPLINT->towns.size() - townlist->SIZE);
 
 	graphics->blueToPlayersAdv(townInt,LOCPLINT->playerID);
 	exit->bitmapOffset = 4;
@@ -813,7 +813,7 @@ void CCastleInterface::showAll( SDL_Surface * to/*=NULL*/)
 
 void CCastleInterface::townChange()
 {
-	const CGTownInstance * nt = townlist->items[townlist->selected];
+	const CGTownInstance * nt = LOCPLINT->towns[townlist->selected];
 	int tpos = townlist->selected - townlist->from;
 	GH.popIntTotally(this);
 	GH.pushInt(new CCastleInterface(nt, tpos));
@@ -1342,7 +1342,7 @@ void CCastleInterface::keyPressed( const SDL_KeyboardEvent & key )
 		}
 		break;
 	case SDLK_DOWN:
-		if(townlist->selected < townlist->items.size() - 1)
+		if(townlist->selected < LOCPLINT->towns.size() - 1)
 		{
 			townlist->selected++;
 			townlist->from++;

+ 6 - 0
client/CHeroWindow.cpp

@@ -520,3 +520,9 @@ void CHeroWindow::dispose()
 	artifs->dispose();
 }
 
+void CHeroWindow::setPlayer(int Player)
+{
+	player = Player;
+
+	graphics->blueToPlayersAdv(background,player);
+}

+ 1 - 0
client/CHeroWindow.h

@@ -69,6 +69,7 @@ public:
 	void dismissCurrent(); //dissmissed currently displayed hero (curHero)
 	void questlog(); //show quest log in hero window
 	void switchHero(); //changes displayed hero
+	void setPlayer(int Player);
 
 	//friends
 	friend void CArtPlace::clickLeft(tribool down, bool previousState);

+ 19 - 5
client/CPlayerInterface.cpp

@@ -154,7 +154,11 @@ void CPlayerInterface::init(ICallback * CB)
 		SDL_Surface * pom = infoWin(tt[i]);
 		graphics->townWins.insert(std::pair<int,SDL_Surface*>(tt[i]->id,pom));
 	}
-	recreateWanderingHeroes();
+
+	if(!towns.size() && !wanderingHeroes.size())
+	{
+		recreateHeroTownList();
+	}
 }
 void CPlayerInterface::yourTurn()
 {
@@ -1121,18 +1125,28 @@ void CPlayerInterface::objectPropertyChanged(const SetObjectProperty * sop)
 		}
 
 		if(obj->ID == TOWNI_TYPE)
-			adventureInt->townList.genList();
+			if(obj->tempOwner == playerID)
+				towns.push_back(static_cast<const CGTownInstance *>(obj));
+			else
+				towns -= obj;
+
+		assert(cb->getTownsInfo().size() == towns.size());
 	}
 
 }
 
-void CPlayerInterface::recreateWanderingHeroes()
+void CPlayerInterface::recreateHeroTownList()
 {
 	wanderingHeroes.clear();
 	std::vector<const CGHeroInstance*> heroes = cb->getHeroesInfo();
 	for(size_t i = 0; i < heroes.size(); i++)
 		if(!heroes[i]->inTownGarrison)
 			wanderingHeroes.push_back(heroes[i]);
+
+	towns.clear();
+	std::vector<const CGTownInstance*> townInfo = cb->getTownsInfo();
+	for(size_t i = 0; i < townInfo.size(); i++)
+		towns.push_back(townInfo[i]);
 }
 
 const CGHeroInstance * CPlayerInterface::getWHero( int pos )
@@ -1873,9 +1887,9 @@ void CPlayerInterface::acceptTurn()
 	//select first hero if available.
 	//TODO: check if hero is slept
 	if(wanderingHeroes.size())
-		adventureInt->select(wanderingHeroes[0]);
+		adventureInt->select(wanderingHeroes.front());
 	else
-		adventureInt->select(adventureInt->townList.items[0]);
+		adventureInt->select(towns.front());
 
 	adventureInt->showAll(screen);
 }

+ 2 - 1
client/CPlayerInterface.h

@@ -133,10 +133,11 @@ public:
 
 
 	std::vector<const CGHeroInstance *> wanderingHeroes; //our heroes on the adventure map (not the garrisoned ones)
+	std::vector<const CGTownInstance *> towns; //our heroes on the adventure map (not the garrisoned ones)
 	std::map<const CGHeroInstance *, CGPath> paths; //maps hero => selected path in adventure map
 
 	void update();
-	void recreateWanderingHeroes();
+	void recreateHeroTownList();
 	const CGHeroInstance *getWHero(int pos); //returns NULL if position is not valid
 	int getLastIndex(std::string namePrefix);
 

+ 3 - 1
client/CPreGame.cpp

@@ -219,6 +219,7 @@ CGPreGame::~CGPreGame()
 
 void CGPreGame::openSel( CMenuScreen::EState type, bool multi )
 {
+	playerNames.clear();
 	playerNames.push_back(CGI->generaltexth->allTexts[434]); //we have only one player and his name is "Player"
 	GH.pushInt(new CSelectionScreen(type, multi));
 }
@@ -2054,7 +2055,7 @@ CMultiMode::CMultiMode()
 	txt->setText(CGI->generaltexth->allTexts[434]); //Player
 
 	btns[0] = new AdventureMapButton(CGI->generaltexth->zelp[266], bind(&CMultiMode::openHotseat, this), 373, 78, "MUBHOT.DEF");
-	btns[6] = new AdventureMapButton(CGI->generaltexth->zelp[288], bind(&CGuiHandler::popIntTotally, ref(GH), this), 373, 424, "MUBCANC.DEF");
+	btns[6] = new AdventureMapButton(CGI->generaltexth->zelp[288], bind(&CGuiHandler::popIntTotally, ref(GH), this), 373, 424, "MUBCANC.DEF", SDLK_ESCAPE);
 }
 
 void CMultiMode::openHotseat()
@@ -2083,6 +2084,7 @@ CHotSeatPlayers::CHotSeatPlayers(const std::string &firstPlayer)
 
 void CHotSeatPlayers::enterSelectionScreen()
 {
+	playerNames.clear();
 	for(int i = 0; i < ARRAY_COUNT(txt); i++)
 		if(txt[i]->text.length())
 			playerNames.push_back(txt[i]->text);

+ 25 - 25
client/GUIClasses.cpp

@@ -1436,7 +1436,7 @@ void CHeroList::updateHList(const CGHeroInstance *toRemove)
 	if(toRemove) //remove specific hero
 		LOCPLINT->wanderingHeroes -= toRemove;
 	else
-		LOCPLINT->recreateWanderingHeroes();
+		LOCPLINT->recreateHeroTownList();
 
 
 	if(selected >= LOCPLINT->wanderingHeroes.size())
@@ -1553,17 +1553,17 @@ CTownList::CTownList(int Size, int x, int y, std::string arrupg, std::string arr
 
 void CTownList::genList()
 {
-	items.clear();
-	int howMany = LOCPLINT->cb->howManyTowns();
-	for (int i=0;i<howMany;i++)
-	{
-		items.push_back(LOCPLINT->cb->getTownInfo(i,0));
-	}
+// 	LOCPLINT->towns.clear();
+// 	int howMany = LOCPLINT->cb->howManyTowns();
+// 	for (int i=0;i<howMany;i++)
+// 	{
+// 		LOCPLINT->towns.push_back(LOCPLINT->cb->getTownInfo(i,0));
+// 	}
 }
 
 void CTownList::select(int which)
 {
-	if (which>=items.size())
+	if (which>=LOCPLINT->towns.size())
 		return;
 	selected = which;
 	if(!fun.empty())
@@ -1582,7 +1582,7 @@ void CTownList::mouseMoved (const SDL_MouseMotionEvent & sEvent)
 	}
 	else if(isItIn(&arrdop,GH.current->motion.x,GH.current->motion.y))
 	{
-		if ((items.size()-from)  >  SIZE)
+		if ((LOCPLINT->towns.size()-from)  >  SIZE)
 			GH.statusbar->print(CGI->generaltexth->zelp[307].first);
 		else
 			GH.statusbar->clear();
@@ -1593,14 +1593,14 @@ void CTownList::mouseMoved (const SDL_MouseMotionEvent & sEvent)
 	hx-=pos.x;
 	hy-=pos.y; hy-=arrup->ourImages[0].bitmap->h;
 	int ny = hy/32;
-	if ((ny>=SIZE || ny<0) || (from+ny>=items.size()))
+	if ((ny>=SIZE || ny<0) || (from+ny>=LOCPLINT->towns.size()))
 	{
 		GH.statusbar->clear();
 		return;
 	};
 	std::string temp = CGI->generaltexth->tcommands[4];
-	boost::algorithm::replace_first(temp,"%s",items[from+ny]->name);
-	temp += ", "+items[from+ny]->town->Name();
+	boost::algorithm::replace_first(temp,"%s",LOCPLINT->towns[from+ny]->name);
+	temp += ", "+LOCPLINT->towns[from+ny]->town->Name();
 	GH.statusbar->print(temp);
 }
 
@@ -1620,7 +1620,7 @@ void CTownList::clickLeft(tribool down, bool previousState)
 		}
 		else if(isItIn(&arrdop,GH.current->motion.x,GH.current->motion.y))
 		{
-			if(items.size()-from > SIZE)
+			if(LOCPLINT->towns.size()-from > SIZE)
 			{
 				blitAt(arrdo->ourImages[1].bitmap,arrdop.x,arrdop.y,screenBuf);
 				pressed = false;
@@ -1638,7 +1638,7 @@ void CTownList::clickLeft(tribool down, bool previousState)
 		  && (ny+from)==selected 
 		  && adventureInt->selection->ID == TOWNI_TYPE
 		  )
-			LOCPLINT->openTownWindow(items[selected]);//print town screen
+			LOCPLINT->openTownWindow(LOCPLINT->towns[selected]);//print town screen
 		else
 			select(ny+from);
 	}
@@ -1666,8 +1666,8 @@ void CTownList::clickLeft(tribool down, bool previousState)
 			if (!down)
 			{
 				from++;
-				//if (from<items.size()-5)
-				//	from=items.size()-5;
+				//if (from<LOCPLINT->towns.size()-5)
+				//	from=LOCPLINT->towns.size()-5;
 
 				draw(screenBuf);
 			}
@@ -1687,7 +1687,7 @@ void CTownList::clickRight(tribool down, bool previousState)
 		{
 			adventureInt->handleRightClick(CGI->generaltexth->zelp[306].second,down,this);
 		}
-		else if(isItIn(&arrdop,GH.current->motion.x,GH.current->motion.y) && (items.size()-from>5))
+		else if(isItIn(&arrdop,GH.current->motion.x,GH.current->motion.y) && (LOCPLINT->towns.size()-from>5))
 		{
 			adventureInt->handleRightClick(CGI->generaltexth->zelp[307].second,down,this);
 		}
@@ -1696,16 +1696,16 @@ void CTownList::clickRight(tribool down, bool previousState)
 		hx-=pos.x;
 		hy-=pos.y; hy-=arrup->ourImages[0].bitmap->h;
 		int ny = hy/32;
-		if ((ny>=SIZE || ny<0) || (from+ny>=items.size()))
+		if ((ny>=SIZE || ny<0) || (from+ny>=LOCPLINT->towns.size()))
 		{
 			return;
 		}
 
 		//show popup
 		CInfoPopup * ip = new CInfoPopup(
-			graphics->townWins[items[from+ny]->id],
-			GH.current->motion.x-graphics->townWins[items[from+ny]->id]->w,
-			GH.current->motion.y-graphics->townWins[items[from+ny]->id]->h,
+			graphics->townWins[LOCPLINT->towns[from+ny]->id],
+			GH.current->motion.x-graphics->townWins[LOCPLINT->towns[from+ny]->id]->w,
+			GH.current->motion.y-graphics->townWins[LOCPLINT->towns[from+ny]->id]->h,
 			false);
 		GH.pushInt(ip);
 	}
@@ -1729,13 +1729,13 @@ void CTownList::draw(SDL_Surface * to)
 	for (int iT=0+from;iT<SIZE+from;iT++)
 	{
 		int i = iT-from;
-		if (iT>=items.size())
+		if (iT>=LOCPLINT->towns.size())
 		{
 			blitAt(graphics->getPic(-1),posporx,pospory+i*32,to);
 			continue;
 		}
 
-		blitAt(graphics->getPic(items[iT]->subID,items[iT]->hasFort(),items[iT]->builded),posporx,pospory+i*32,to);
+		blitAt(graphics->getPic(LOCPLINT->towns[iT]->subID,LOCPLINT->towns[iT]->hasFort(),LOCPLINT->towns[iT]->builded),posporx,pospory+i*32,to);
 
 		if ((selected == iT) && (adventureInt->selection->ID == TOWNI_TYPE))
 		{
@@ -1747,7 +1747,7 @@ void CTownList::draw(SDL_Surface * to)
 	else
 		blitAt(arrup->ourImages[2].bitmap,arrupp.x,arrupp.y,to);
 
-	if (items.size()-from>SIZE)
+	if (LOCPLINT->towns.size()-from>SIZE)
 		blitAt(arrdo->ourImages[0].bitmap,arrdop.x,arrdop.y,to);
 	else
 		blitAt(arrdo->ourImages[2].bitmap,arrdop.x,arrdop.y,to);
@@ -1760,7 +1760,7 @@ void CTownList::show( SDL_Surface * to )
 
 int CTownList::size()
 {
-	return items.size();
+	return LOCPLINT->towns.size();
 }
 
 CCreaturePic::CCreaturePic(const CCreature *cre, bool Big)

+ 0 - 1
client/GUIClasses.h

@@ -380,7 +380,6 @@ class CTownList
 {
 public:
 	boost::function<void()> fun; //function called on selection change
-	std::vector<const CGTownInstance*> items; //towns on list
 	int posporx,pospory;
 
 	CTownList(int Size, int x, int y, std::string arrupg, std::string arrdog); //c-tor

+ 2 - 14
hch/CObjectHandler.h

@@ -279,12 +279,7 @@ public:
 			& sex & inTownGarrison & artifacts & artifWorn & spells & patrol & bonuses
 			& moveDir;
 
-		ui8 standardType = (VLC->heroh->heroes[subID] == type);
-		h & standardType;
-		if(!standardType)
-			h & type;
-		else if(!h.saving)
-			type = VLC->heroh->heroes[subID];
+		h & type;
 		//visitied town pointer will be restored by map serialization method
 	}
 	//////////////////////////////////////////////////////////////////////////
@@ -470,14 +465,7 @@ public:
 		for (std::vector<CGTownBuilding*>::iterator i = bonusingBuildings.begin(); i!=bonusingBuildings.end(); i++)
 			(*i)->town = this;
 
-
-		ui8 standardType = (&VLC->townh->towns[subID] == town);
-		h & standardType;
-		if(!standardType)
-			h & town;
-		else if(!h.saving)
-			town = &VLC->townh->towns[subID];
-
+		h & town;
 		//garrison/visiting hero pointers will be restored in the map serialization
 	}
 

+ 43 - 18
lib/Connection.cpp

@@ -229,9 +229,33 @@ bool CConnection::isOpen() const
 }
 
 CSaveFile::CSaveFile( const std::string &fname )
-	:sfile(new std::ofstream(fname.c_str(),std::ios::binary))
+	:sfile(NULL)
 {
 	registerTypes(*this);
+	openNextFile(fname);
+}
+
+CSaveFile::~CSaveFile()
+{
+	delete sfile;
+}
+
+int CSaveFile::write( const void * data, unsigned size )
+{
+	sfile->write((char *)data,size);
+	return size;
+}
+
+void CSaveFile::close()
+{
+	delete sfile;
+	sfile = NULL;
+}
+
+void CSaveFile::openNextFile(const std::string &fname)
+{
+	close();
+	sfile = new std::ofstream(fname.c_str(),std::ios::binary);
 	if(!(*sfile))
 	{
 		tlog1 << "Error: cannot open to write " << fname << std::endl;
@@ -244,21 +268,33 @@ CSaveFile::CSaveFile( const std::string &fname )
 	}
 }
 
-CSaveFile::~CSaveFile()
+CLoadFile::CLoadFile( const std::string &fname, bool requireLatest )
+:sfile(NULL)
+{
+	registerTypes(*this);
+	openNextFile(fname, requireLatest);
+}
+
+CLoadFile::~CLoadFile()
 {
 	delete sfile;
 }
 
-int CSaveFile::write( const void * data, unsigned size )
+int CLoadFile::read( const void * data, unsigned size )
 {
-	sfile->write((char *)data,size);
+	sfile->read((char *)data,size);
 	return size;
 }
 
-CLoadFile::CLoadFile( const std::string &fname, bool requireLatest )
-:sfile(new std::ifstream(fname.c_str(),std::ios::binary))
+void CLoadFile::close()
 {
-	registerTypes(*this);
+	delete sfile;
+	sfile = NULL;
+}
+
+void CLoadFile::openNextFile(const std::string &fname, bool requireLatest)
+{
+	sfile = new std::ifstream(fname.c_str(),std::ios::binary);
 	if(!(*sfile))
 	{
 		tlog1 << "Error: cannot open to read " << fname << std::endl;
@@ -287,17 +323,6 @@ CLoadFile::CLoadFile( const std::string &fname, bool requireLatest )
 	}
 }
 
-CLoadFile::~CLoadFile()
-{
-	delete sfile;
-}
-
-int CLoadFile::read( const void * data, unsigned size )
-{
-	sfile->read((char *)data,size);
-	return size;
-}
-
 CTypeList::CTypeList()
 {
 	registerTypes(*this);

+ 7 - 1
lib/Connection.h

@@ -21,7 +21,7 @@
 #include <boost/mpl/int.hpp>
 #include <boost/mpl/identity.hpp>
 
-const ui32 version = 718;
+const ui32 version = 719;
 class CConnection;
 class CGObjectInstance;
 class CGameState;
@@ -682,6 +682,9 @@ public:
 	CSaveFile(const std::string &fname);
 	~CSaveFile();
 	int write(const void * data, unsigned size);
+
+	void close();
+	void openNextFile(const std::string &fname);
 };
 
 class DLL_EXPORT CLoadFile
@@ -697,6 +700,9 @@ public:
 	CLoadFile(const std::string &fname, bool requireLatest = true);
 	~CLoadFile();
 	int read(const void * data, unsigned size);
+
+	void close();
+	void openNextFile(const std::string &fname, bool requireLatest);
 };
 
 class DLL_EXPORT CConnection

+ 2 - 2
lib/HeroBonus.h

@@ -113,8 +113,8 @@ struct DLL_EXPORT HeroBonus
 
 };
 
-static const HeroBonus::BonusType MORALE_AFFECTING[] =  {HeroBonus::LUCK, HeroBonus::MORALE_AND_LUCK};
-static const HeroBonus::BonusType LUCK_AFFECTING[] =  {HeroBonus::MORALE, HeroBonus::MORALE_AND_LUCK};
+static const HeroBonus::BonusType MORALE_AFFECTING[] =  {HeroBonus::MORALE, HeroBonus::MORALE_AND_LUCK};
+static const HeroBonus::BonusType LUCK_AFFECTING[] =  {HeroBonus::LUCK, HeroBonus::MORALE_AND_LUCK};
 typedef std::vector<std::pair<int,std::string> > TModDescr; //modifiers values and their descriptions
 
 class BonusList : public std::list<HeroBonus>