2
0
Эх сурвалжийг харах

Implemented #715 (load game from sys options). Fixed #224. Minor improvements.

Michał W. Urbańczyk 13 жил өмнө
parent
commit
8baec8b093

+ 2 - 2
client/BattleInterface/CBattleInterface.cpp

@@ -1122,7 +1122,7 @@ void CBattleInterface::bSurrenderf()
 		const CGHeroInstance *opponent = curInt->cb->battleGetFightingHero(1);
 		std::string enemyHeroName = opponent ? opponent->name : "#ENEMY#"; //TODO: should surrendering without enemy hero be enabled?
 		std::string surrenderMessage = boost::str(boost::format(CGI->generaltexth->allTexts[32]) % enemyHeroName % cost); //%s states: "I will accept your surrender and grant you and your troops safe passage for the price of %d gold."
-		curInt->showYesNoDialog(surrenderMessage, std::vector<CComponent*>(), boost::bind(&CBattleInterface::reallySurrender,this), 0, false);
+		curInt->showYesNoDialog(surrenderMessage, boost::bind(&CBattleInterface::reallySurrender,this), 0, false);
 	}
 }
 
@@ -1134,7 +1134,7 @@ void CBattleInterface::bFleef()
 	if( curInt->cb->battleCanFlee() )
 	{
 		CFunctionList<void()> ony = boost::bind(&CBattleInterface::reallyFlee,this);
-		curInt->showYesNoDialog(CGI->generaltexth->allTexts[28],std::vector<CComponent*>(), ony, 0, false); //Are you sure you want to retreat?
+		curInt->showYesNoDialog(CGI->generaltexth->allTexts[28], ony, 0, false); //Are you sure you want to retreat?
 	}
 	else
 	{

+ 6 - 2
client/CAdvmapInterface.cpp

@@ -1177,7 +1177,7 @@ void CAdvMapInt::fendTurn()
 		for (int i = 0; i < LOCPLINT->wanderingHeroes.size(); i++)
 			if (!isHeroSleeping(LOCPLINT->wanderingHeroes[i]) && (LOCPLINT->wanderingHeroes[i]->movement > 0))
 			{
-				LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[55], std::vector<CComponent*>(), boost::bind(&CAdvMapInt::endingTurn, this), 0, false);
+				LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[55], boost::bind(&CAdvMapInt::endingTurn, this), 0, false);
 				return;
 			}
 	}
@@ -1470,6 +1470,10 @@ void CAdvMapInt::keyPressed(const SDL_KeyboardEvent & key)
 		if(isActive())
 			CAdventureOptions::showScenarioInfo();
 		return;
+	case SDLK_l:
+		if(isActive())
+			LOCPLINT->proposeLoadingGame();
+		return;
 	case SDLK_s:
 		if(isActive())
 			GH.pushInt(new CSavingScreen(CPlayerInterface::howManyPeople > 1));
@@ -1487,7 +1491,7 @@ void CAdvMapInt::keyPressed(const SDL_KeyboardEvent & key)
 	case SDLK_r:
 		if(isActive() && LOCPLINT->ctrlPressed())
 		{
-			LOCPLINT->showYesNoDialog("Are you sure you want to restart game?", std::vector<CComponent*>(), 
+			LOCPLINT->showYesNoDialog("Are you sure you want to restart game?",
 				[]{ LOCPLINT->sendCustomEvent(RESTART_GAME); },
 				[]{}, true);
 		}

+ 1 - 2
client/CCastleInterface.cpp

@@ -870,7 +870,7 @@ void CCastleBuildings::enterMagesGuild()
 			functionList += boost::bind(&CCastleBuildings::openMagesGuild,this);
 			std::vector<CComponent*> components(1, new CComponent(CComponent::artifact,0,0));
 
-			LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[214], components, functionList, 0, true);
+			LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[214], functionList, 0, true, components);
 		}
 	}
 	else
@@ -887,7 +887,6 @@ void CCastleBuildings::enterTownHall()
 		if(!vstd::contains(town->forbiddenBuildings, EBuilding::GRAIL))
 		{
 			LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[597], //Do you wish this to be the permanent home of the Grail?
-			                            std::vector<CComponent*>(),
 			                            boost::bind(&CCallback::buildBuilding, LOCPLINT->cb, town, EBuilding::GRAIL),
 			                            boost::bind(&CCastleBuildings::openTownHall, this), true);
 		}

+ 5 - 6
client/CCreatureWindow.cpp

@@ -95,7 +95,7 @@ CCreatureWindow::CCreatureWindow(const CStackInstance &st, int Type, boost::func
 				fs += Upg;
 				fs += boost::bind(&CCreatureWindow::close,this);
 				CFunctionList<void()> cfl;
-				cfl = boost::bind(&CPlayerInterface::showYesNoDialog, LOCPLINT, CGI->generaltexth->allTexts[207], boost::ref(upgResCost), fs, 0, false);
+				cfl = boost::bind(&CPlayerInterface::showYesNoDialog, LOCPLINT, CGI->generaltexth->allTexts[207], fs, 0, false, boost::ref(upgResCost));
 				upgrade = new CAdventureMapButton("",CGI->generaltexth->zelp[446].second,cfl,385, 148,"IVIEWCR.DEF",SDLK_u);
 			}
 			else
@@ -113,7 +113,7 @@ CCreatureWindow::CCreatureWindow(const CStackInstance &st, int Type, boost::func
 			fs[0] += Dsm; //dismiss
 			fs[0] += boost::bind(&CCreatureWindow::close,this);//close this window
 			CFunctionList<void()> cfl;
-			cfl = boost::bind(&CPlayerInterface::showYesNoDialog,LOCPLINT,CGI->generaltexth->allTexts[12],std::vector<CComponent*>(),fs[0],fs[1],false);
+			cfl = boost::bind(&CPlayerInterface::showYesNoDialog,LOCPLINT,CGI->generaltexth->allTexts[12],fs[0],fs[1],false,std::vector<CComponent*>());
 			dismiss = new CAdventureMapButton("",CGI->generaltexth->zelp[445].second,cfl,333, 148,"IVIEWCR2.DEF",SDLK_d);
 		}
 	}
@@ -506,8 +506,8 @@ CCreInfoWindow::CCreInfoWindow(const CStackInstance &stack, bool LClicked, boost
 			boost::function<void()> dialog = boost::bind(&CPlayerInterface::showYesNoDialog,
 				LOCPLINT,
 				CGI->generaltexth->allTexts[207],
-				boost::ref(upgResCost),
-				onUpgrade, 0, false);
+				onUpgrade, 0, false,
+				boost::ref(upgResCost));
 
 			upgrade = new CAdventureMapButton("", CGI->generaltexth->zelp[446].second, dialog, 76, 237, "IVIEWCR", SDLK_u);
 			upgrade->block(!LOCPLINT->cb->getResourceAmount().canAfford(upgradeCost));
@@ -522,8 +522,7 @@ CCreInfoWindow::CCreInfoWindow(const CStackInstance &stack, bool LClicked, boost
 			boost::function<void()> dialog = boost::bind(&CPlayerInterface::showYesNoDialog,
 				LOCPLINT,
 				CGI->generaltexth->allTexts[12],
-				std::vector<CComponent*>(),
-				onDismiss, 0, true);
+				onDismiss, 0, true, std::vector<CComponent*>());
 
 			dismiss = new CAdventureMapButton("", CGI->generaltexth->zelp[445].second, dialog, 21, 237, "IVIEWCR2",SDLK_d);
 		}

+ 1 - 1
client/CHeroWindow.cpp

@@ -286,7 +286,7 @@ void CHeroWindow::dismissCurrent()
 {
 	CFunctionList<void()> ony = boost::bind(&CHeroWindow::quit,this);
 	ony += boost::bind(&CCallback::dismissHero,LOCPLINT->cb,curHero);
-	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[22],std::vector<CComponent*>(), ony, 0, false);
+	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[22], ony, 0, false);
 }
 
 void CHeroWindow::questlog()

+ 20 - 14
client/CMT.cpp

@@ -697,6 +697,16 @@ static void listenForEvents()
 		}
 		else if(ev->type == SDL_USEREVENT)
 		{
+			auto endGame = []
+			{
+				client->endGame();
+				vstd::clear_pointer(client);
+
+				delete CGI->dobjinfo.get();
+				const_cast<CGameInfo*>(CGI)->dobjinfo = new CDefObjInfoHandler;
+				const_cast<CGameInfo*>(CGI)->dobjinfo->load();
+			};
+
 			switch(ev->user.code)
 			{
 			case CHANGE_SCREEN_RESOLUTION:
@@ -708,13 +718,7 @@ static void listenForEvents()
 				break;
 			}
 			case RETURN_TO_MAIN_MENU:
-				client->endGame();
-				vstd::clear_pointer(client);
-
-				delete CGI->dobjinfo.get();
-				const_cast<CGameInfo*>(CGI)->dobjinfo = new CDefObjInfoHandler;
-				const_cast<CGameInfo*>(CGI)->dobjinfo->load();
-
+				endGame();
 				CGPreGame::createIfNotPresent();
 				GH.curInt = CGP;
 				GH.defActionsDef = 63;
@@ -725,16 +729,18 @@ static void listenForEvents()
 			case RESTART_GAME:
 				{
 					StartInfo si = *client->getStartInfo();
-					client->endGame();
-					vstd::clear_pointer(client);
-
-					delete CGI->dobjinfo.get();
-					const_cast<CGameInfo*>(CGI)->dobjinfo = new CDefObjInfoHandler;
-					const_cast<CGameInfo*>(CGI)->dobjinfo->load();
-
+					endGame();
 					startGame(&si);
 				}
 				break;
+			case RETURN_TO_MENU_LOAD:
+				endGame();
+				CGPreGame::createIfNotPresent();
+				GH.defActionsDef = 63;
+				CGP->update();
+				CGP->menu->switchToTab(vstd::find_pos(CGP->menu->menuNameToEntry, "load"));
+				GH.curInt = CGP;
+				break;
 			default:
 				tlog1 << "Error: unknown user event. Code " << ev->user.code << std::endl;
 				assert(0);

+ 8 - 3
client/CPlayerInterface.cpp

@@ -953,7 +953,7 @@ void CPlayerInterface::showInfoDialog(const std::string &text, const std::vector
 	}
 }
 
-void CPlayerInterface::showYesNoDialog(const std::string &text, const std::vector<CComponent*> & components, CFunctionList<void()> onYes, CFunctionList<void()> onNo, bool DelComps)
+void CPlayerInterface::showYesNoDialog(const std::string &text, CFunctionList<void()> onYes, CFunctionList<void()> onNo, bool DelComps, const std::vector<CComponent*> & components)
 {
 	boost::unique_lock<boost::recursive_mutex> un(*pim);
 
@@ -976,7 +976,7 @@ void CPlayerInterface::showBlockingDialog( const std::string &text, const std::v
 		for(int i=0;i<components.size();i++)
 			intComps.push_back(new CComponent(components[i])); //will be deleted by close in window
 
-		showYesNoDialog(text,intComps,boost::bind(&CCallback::selectionMade,cb,1,askID),boost::bind(&CCallback::selectionMade,cb,0,askID),true);
+		showYesNoDialog(text, boost::bind(&CCallback::selectionMade,cb,1,askID),boost::bind(&CCallback::selectionMade,cb,0,askID),true, intComps);
 	}
 	else if(selection)
 	{
@@ -1315,7 +1315,7 @@ void CPlayerInterface::showArtifactAssemblyDialog (ui32 artifactID, ui32 assembl
 		text += CGI->generaltexth->allTexts[733];
 	}
 
-	showYesNoDialog(text, scs, onYes, onNo, true);
+	showYesNoDialog(text, onYes, onNo, true, scs);
 }
 
 void CPlayerInterface::requestRealized( PackageApplied *pa )
@@ -2407,6 +2407,11 @@ void CPlayerInterface::waitForAllDialogs(bool unlockPim /*= true*/)
 	waitWhileDialog(unlockPim);
 }
 
+void CPlayerInterface::proposeLoadingGame()
+{
+	showYesNoDialog(CGI->generaltexth->allTexts[68], [this] { sendCustomEvent(RETURN_TO_MENU_LOAD); }, 0, false);
+}
+
 CPlayerInterface::SpellbookLastSetting::SpellbookLastSetting()
 {
 	spellbookLastPageBattle = spellbokLastPageAdvmap = 0;

+ 4 - 2
client/CPlayerInterface.h

@@ -71,7 +71,8 @@ namespace boost
 	class recursive_mutex;
 };
 
-enum {CHANGE_SCREEN_RESOLUTION = 1, RETURN_TO_MAIN_MENU = 2, STOP_CLIENT = 3, RESTART_GAME};
+enum {CHANGE_SCREEN_RESOLUTION = 1, RETURN_TO_MAIN_MENU = 2, STOP_CLIENT = 3, RESTART_GAME,
+	RETURN_TO_MENU_LOAD};
 
 /// Central class for managing user interface logic
 class CPlayerInterface : public CGameInterface, public IUpdateable
@@ -215,7 +216,7 @@ public:
 	void init(CCallback * CB);
 	int3 repairScreenPos(int3 pos); //returns position closest to pos we can center screen on
 	void showInfoDialog(const std::string &text, const std::vector<CComponent*> & components = std::vector<CComponent*>(), int soundID = 0, bool delComps = false);
-	void showYesNoDialog(const std::string &text, const std::vector<CComponent*> & components, CFunctionList<void()> onYes, CFunctionList<void()> onNo, bool DelComps); //deactivateCur - whether current main interface should be deactivated; delComps - if components will be deleted on window close
+	void showYesNoDialog(const std::string &text, CFunctionList<void()> onYes, CFunctionList<void()> onNo, bool DelComps = false, const std::vector<CComponent*> & components = std::vector<CComponent*>()); //deactivateCur - whether current main interface should be deactivated; delComps - if components will be deleted on window close
 	void stopMovement();
 	bool moveHero(const CGHeroInstance *h, CGPath path);
 	void initMovement(const TryMoveHero &details, const CGHeroInstance * ho, const int3 &hp );//initializing objects and performing first step of move
@@ -230,6 +231,7 @@ public:
 	void requestReturningToMainMenu();
 	void requestStoppingClient();
 	void sendCustomEvent(int code);
+	void proposeLoadingGame();
 
 	CPlayerInterface(int Player);//c-tor
 	~CPlayerInterface();//d-tor

+ 3 - 3
client/CPreGame.cpp

@@ -799,7 +799,7 @@ void CSelectionScreen::startGame()
 		{
 			std::string hlp = CGI->generaltexth->allTexts[493]; //%s exists. Overwrite?
 			boost::algorithm::replace_first(hlp, "%s", sel->txt->text);
-			LOCPLINT->showYesNoDialog(hlp, std::vector<CComponent*>(), overWrite, 0, false);
+			LOCPLINT->showYesNoDialog(hlp, overWrite, 0, false);
 		}
 		else
 			overWrite();
@@ -1368,7 +1368,7 @@ void SelectionTab::printMaps(SDL_Surface *to)
 		}
 
 		//print name
-		CSDL_Ext::printAtMiddle(name, POS(213, 128), FONT_SMALL, itemColor, to);
+		CSDL_Ext::printAtMiddle(CSDL_Ext::trimToFit(name, 185, FONT_SMALL), POS(213, 128), FONT_SMALL, itemColor, to);
 
 	}
 #undef POS
@@ -1734,7 +1734,7 @@ void InfoCard::showAll(SDL_Surface * to)
 
 		//name
 		if (name.length())
-			printAtLoc(name, 26, 39, FONT_BIG, Colors::Jasmine, to);
+			printAtLoc(CSDL_Ext::trimToFit(name, 300, FONT_BIG), 26, 39, FONT_BIG, Colors::Jasmine, to);
 		else
 			printAtLoc("Unnamed", 26, 39, FONT_BIG, Colors::Jasmine, to);
 	}

+ 13 - 4
client/GUIClasses.cpp

@@ -3677,7 +3677,10 @@ CSystemOptionsWindow::CSystemOptionsWindow(const SDL_Rect &Pos, CPlayerInterface
 	rightGroup->add(282, 217, fsLabel); //CGI->generaltexth->allTexts[577]
 
 	//setting up buttons
-	// load = new CAdventureMapButton (CGI->generaltexth->zelp[321].first, CGI->generaltexth->zelp[321].second, boost::bind(&CSystemOptionsWindow::loadf, this), pos.x+246, pos.y+298, "SOLOAD.DEF", SDLK_l);
+	load = new CAdventureMapButton (CGI->generaltexth->zelp[321].first, CGI->generaltexth->zelp[321].second,
+									boost::bind(&CSystemOptionsWindow::bloadf, this), 246,  298, "SOLOAD.DEF", SDLK_l);
+	load->swappedImages = true;
+	load->update();
 
 	save = new CAdventureMapButton (CGI->generaltexth->zelp[322].first, CGI->generaltexth->zelp[322].second,
 	                                boost::bind(&CSystemOptionsWindow::bsavef, this), 357, 298, "SOSAVE.DEF", SDLK_s);
@@ -3814,7 +3817,7 @@ void CSystemOptionsWindow::toggleFullscreen(bool on)
 
 void CSystemOptionsWindow::bquitf()
 {
-	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[578], std::vector<CComponent*>(), boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_QUIT, 0), 0, false);
+	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[578], boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_QUIT, 0), 0, false);
 }
 
 void CSystemOptionsWindow::breturnf()
@@ -3824,7 +3827,13 @@ void CSystemOptionsWindow::breturnf()
 
 void CSystemOptionsWindow::bmainmenuf()
 {
-	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[578], std::vector<CComponent*>(), boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_USEREVENT, RETURN_TO_MAIN_MENU), 0, false);
+	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[578], boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_USEREVENT, RETURN_TO_MAIN_MENU), 0, false);
+}
+
+void CSystemOptionsWindow::bloadf()
+{
+	GH.popIntTotally(this);
+	LOCPLINT->proposeLoadingGame();
 }
 
 void CSystemOptionsWindow::bsavef()
@@ -3835,7 +3844,7 @@ void CSystemOptionsWindow::bsavef()
 
 void CSystemOptionsWindow::brestartf()
 {
-	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[578], std::vector<CComponent*>(), boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_USEREVENT, RESTART_GAME), 0, false);
+	LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[67], boost::bind(&CSystemOptionsWindow::pushSDLEvent, this, SDL_USEREVENT, RESTART_GAME), 0, false);
 }
 
 CTavernWindow::CTavernWindow(const CGObjectInstance *TavernObj)

+ 2 - 1
client/GUIClasses.h

@@ -679,10 +679,11 @@ private:
 	void setMapScrollingSpeed( int newSpeed );
 
 	//functions bound to buttons
+	void bloadf(); //load game
 	void bsavef(); //save game
 	void bquitf(); //quit game
 	void breturnf(); //return to game
-	void brestartf(); //return to game
+	void brestartf(); //restart game
 	void bmainmenuf(); //return to main menu
 
 	//functions for checkboxes

+ 1 - 2
client/UIFramework/CGuiHandler.cpp

@@ -346,8 +346,7 @@ void CGuiHandler::fakeMouseMove()
 void CGuiHandler::run()
 {
 	setThreadName(-1, "CGuiHandler::run");
-	bool iAmGui = true;
-	inGuiThread.reset(&iAmGui);
+	inGuiThread.reset(new bool(true));
 	try
 	{
 		if (settings["video"]["fullscreen"].Bool())

+ 17 - 0
client/UIFramework/SDL_Extensions.cpp

@@ -1299,6 +1299,23 @@ void CSDL_Ext::fillRect( SDL_Surface *dst, SDL_Rect *dstrect, Uint32 color )
 	SDL_FillRect(dst, &newRect, color);
 }
 
+std::string CSDL_Ext::trimToFit(std::string text, int widthLimit, EFonts font)
+{
+	int widthSoFar = 0;
+	for(auto i = text.begin(); i != text.end(); i++)
+	{
+		widthSoFar += graphics->fonts[font]->getCharWidth(*i);
+		if(widthSoFar > widthLimit)
+		{
+			//remove all characteres past limit
+			text.erase(i, text.end());
+			break;
+		}
+	}
+
+	return text;
+}
+
 SDL_Surface * CSDL_Ext::std32bppSurface = NULL;
 
 //instantiation of templates used in CAnimation and CCreatureAnimation, required for correct linking

+ 2 - 0
client/UIFramework/SDL_Extensions.h

@@ -186,4 +186,6 @@ namespace CSDL_Ext
 	SDL_Surface * copySurface(SDL_Surface * mod); //returns copy of given surface
 	void VflipSurf(SDL_Surface * surf); //fluipis given surface by vertical axis
 	void applyEffect(SDL_Surface * surf, const SDL_Rect * rect, int mode); //mode: 0 - sepia, 1 - grayscale
+
+	std::string trimToFit(std::string text, int widthLimit, EFonts font);
 };