2011-12-14 00:23:17 +03:00
# include "StdInc.h"
2009-05-20 12:02:50 +03:00
# include "CCastleInterface.h"
2011-12-14 00:23:17 +03:00
2009-05-20 13:08:56 +03:00
# include "../CCallback.h"
2010-12-20 23:22:53 +02:00
# include "../lib/CArtHandler.h"
# include "../lib/CBuildingHandler.h"
2011-03-22 15:19:07 +02:00
# include "../lib/CCreatureHandler.h"
2010-12-20 23:22:53 +02:00
# include "../lib/CGeneralTextHandler.h"
# include "../lib/CObjectHandler.h"
# include "../lib/CSpellHandler.h"
# include "../lib/CTownHandler.h"
2011-03-22 15:19:07 +02:00
# include "CAdvmapInterface.h"
# include "CAnimation.h"
# include "CBitmapHandler.h"
# include "CDefHandler.h"
# include "CGameInfo.h"
# include "CHeroWindow.h"
# include "CMessage.h"
2010-12-20 23:22:53 +02:00
# include "CMusicHandler.h"
2011-03-22 15:19:07 +02:00
# include "CPlayerInterface.h"
# include "Graphics.h"
2011-12-22 16:05:19 +03:00
# include "UIFramework/SDL_Extensions.h"
2011-12-14 00:23:17 +03:00
# include "../lib/GameConstants.h"
2011-12-17 21:59:59 +03:00
# include "UIFramework/CGuiHandler.h"
2011-12-22 16:05:19 +03:00
# include "UIFramework/CIntObjectClasses.h"
2011-03-22 15:19:07 +02:00
2008-08-17 12:11:16 +03:00
using namespace boost : : assign ;
2009-04-15 17:03:31 +03:00
/*
* CCastleInterface . cpp , part of VCMI engine
*
* Authors : listed in file AUTHORS in main folder
*
* License : GNU General Public License v2 .0 or later
* Full text of license available in license . txt file , in main folder
*
*/
2010-06-30 22:27:35 +03:00
int hordeToDwellingID ( int bid ) //helper, converts horde buiding ID into corresponding dwelling ID
{
const CGTownInstance * t = LOCPLINT - > castleInt - > town ;
switch ( bid )
{
case 18 : return t - > town - > hordeLvl [ 0 ] + 30 ;
case 19 : return t - > town - > hordeLvl [ 0 ] + 37 ;
case 24 : return t - > town - > hordeLvl [ 1 ] + 30 ;
case 25 : return t - > town - > hordeLvl [ 1 ] + 37 ;
default : return bid ;
}
}
2011-04-07 20:54:08 +03:00
CBuildingRect : : CBuildingRect ( CCastleBuildings * Par , const CGTownInstance * Town , const Structure * Str )
2011-02-06 19:26:27 +02:00
: CShowableAnim ( 0 , 0 , Str - > defName , CShowableAnim : : BASE | CShowableAnim : : USE_RLE ) ,
2011-04-07 20:54:08 +03:00
parent ( Par ) ,
town ( Town ) ,
str ( Str ) ,
stateCounter ( 80 )
2008-08-02 18:08:03 +03:00
{
2011-04-07 20:54:08 +03:00
recActions = ACTIVATE | DEACTIVATE | DISPOSE | SHARE_POS ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | RCLICK | HOVER ) ;
2011-03-22 15:19:07 +02:00
pos . x + = str - > pos . x ;
pos . y + = str - > pos . y ;
2010-11-15 17:15:00 +02:00
2011-02-06 19:26:27 +02:00
if ( ! str - > borderName . empty ( ) )
border = BitmapHandler : : loadBitmap ( str - > borderName , true ) ;
else
border = NULL ;
2009-10-13 07:07:26 +03:00
2011-02-06 19:26:27 +02:00
if ( ! str - > areaName . empty ( ) )
area = BitmapHandler : : loadBitmap ( str - > areaName ) ;
else
area = NULL ;
2008-01-19 13:55:04 +02:00
}
CBuildingRect : : ~ CBuildingRect ( )
{
2011-03-22 15:19:07 +02:00
SDL_FreeSurface ( border ) ;
SDL_FreeSurface ( area ) ;
2008-01-19 13:55:04 +02:00
}
2008-03-23 03:01:17 +02:00
2008-01-19 13:55:04 +02:00
bool CBuildingRect : : operator < ( const CBuildingRect & p2 ) const
{
if ( str - > pos . z ! = p2 . str - > pos . z )
return ( str - > pos . z ) < ( p2 . str - > pos . z ) ;
else
return ( str - > ID ) < ( p2 . str - > ID ) ;
}
2011-03-22 15:19:07 +02:00
2008-01-20 18:24:03 +02:00
void CBuildingRect : : hover ( bool on )
2008-01-19 13:55:04 +02:00
{
2008-01-24 00:15:33 +02:00
if ( on )
2008-01-20 18:24:03 +02:00
{
2011-02-06 19:26:27 +02:00
if ( ! ( active & MOVE ) )
2012-06-02 18:16:54 +03:00
addUsedEvents ( MOVE ) ;
2008-01-24 00:15:33 +02:00
}
2008-08-02 18:08:03 +03:00
else
2008-01-24 00:15:33 +02:00
{
2011-02-06 19:26:27 +02:00
if ( active & MOVE )
2012-06-02 18:16:54 +03:00
removeUsedEvents ( MOVE ) ;
2011-02-06 19:26:27 +02:00
2011-03-22 15:19:07 +02:00
if ( parent - > selectedBuilding = = this )
2008-01-27 22:37:10 +02:00
{
2011-03-22 15:19:07 +02:00
parent - > selectedBuilding = NULL ;
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2008-01-27 22:37:10 +02:00
}
2008-01-20 18:24:03 +02:00
}
2008-01-19 13:55:04 +02:00
}
2010-11-15 17:15:00 +02:00
2009-08-11 19:05:33 +03:00
void CBuildingRect : : clickLeft ( tribool down , bool previousState )
2008-01-19 13:55:04 +02:00
{
2011-03-22 15:19:07 +02:00
if ( previousState & & ! down & & area & & ( parent - > selectedBuilding = = this ) )
2010-11-15 17:15:00 +02:00
if ( ! CSDL_Ext : : isTransparent ( area , GH . current - > motion . x - pos . x , GH . current - > motion . y - pos . y ) ) //inside building image
2011-03-22 15:19:07 +02:00
parent - > buildingClicked ( str - > ID ) ;
2008-01-19 13:55:04 +02:00
}
2010-11-15 17:15:00 +02:00
2009-08-11 19:05:33 +03:00
void CBuildingRect : : clickRight ( tribool down , bool previousState )
2008-01-19 13:55:04 +02:00
{
2011-03-22 15:19:07 +02:00
if ( ( ! area ) | | ( ! ( ( bool ) down ) ) | | ( this ! = parent - > selectedBuilding ) )
2008-03-06 20:54:35 +02:00
return ;
2010-02-18 14:34:44 +02:00
if ( ! CSDL_Ext : : isTransparent ( area , GH . current - > motion . x - pos . x , GH . current - > motion . y - pos . y ) ) //inside building image
2008-03-06 20:54:35 +02:00
{
2010-06-30 22:27:35 +03:00
int bid = hordeToDwellingID ( str - > ID ) ;
2010-12-20 23:22:53 +02:00
const CBuilding * bld = CGI - > buildh - > buildings [ str - > townID ] . find ( bid ) - > second ;
2011-12-14 00:23:17 +03:00
if ( bid < EBuilding : : DWELL_FIRST )
2011-04-07 20:54:08 +03:00
{
2012-05-13 18:04:21 +03:00
std : : vector < CComponent * > comps ( 1 , new CComponent ( CComponent : : building , bld - > tid , bld - > bid ) ) ;
2009-05-22 02:50:45 +03:00
2011-04-07 20:54:08 +03:00
CRClickPopup : : createAndPush ( bld - > Description ( ) , comps ) ;
}
else
{
2011-12-14 00:23:17 +03:00
int level = ( bid - EBuilding : : DWELL_FIRST ) % GameConstants : : CREATURES_PER_TOWN ;
2011-04-07 20:54:08 +03:00
GH . pushInt ( new CDwellingInfoBox ( parent - > pos . x + parent - > pos . w / 2 , parent - > pos . y + parent - > pos . h / 2 , town , level ) ) ;
}
2008-03-06 20:54:35 +02:00
}
2008-01-19 13:55:04 +02:00
}
2010-06-30 22:27:35 +03:00
2011-12-14 00:23:17 +03:00
SDL_Color multiplyColors ( const SDL_Color & b , const SDL_Color & a , double f )
2011-03-22 15:19:07 +02:00
{
SDL_Color ret ;
ret . r = a . r * f + b . r * ( 1 - f ) ;
ret . g = a . g * f + b . g * ( 1 - f ) ;
ret . b = a . b * f + b . b * ( 1 - f ) ;
return ret ;
}
2011-12-22 16:05:19 +03:00
void CBuildingRect : : show ( SDL_Surface * to )
2010-11-15 17:15:00 +02:00
{
2011-12-14 00:23:17 +03:00
const ui32 stageDelay = 16 ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
const ui32 S1_TRANSP = 16 ; //0.5 sec building appear 0->100 transparency
const ui32 S2_WHITE_B = 32 ; //0.5 sec border glows from white to yellow
const ui32 S3_YELLOW_B = 48 ; //0.5 sec border glows from yellow to normal
const ui32 BUILDED = 80 ; // 1 sec delay, nothing happens
2011-03-22 15:19:07 +02:00
if ( stateCounter < S1_TRANSP )
{
setAlpha ( 255 * stateCounter / stageDelay ) ;
CShowableAnim : : show ( to ) ;
}
else
{
setAlpha ( 255 ) ;
CShowableAnim : : show ( to ) ;
}
if ( border & & stateCounter > S1_TRANSP )
{
if ( stateCounter = = BUILDED )
{
if ( parent - > selectedBuilding = = this )
blitAtLoc ( border , 0 , 0 , to ) ;
return ;
}
// key colors in glowing border
SDL_Color c1 = { 200 , 200 , 200 , 255 } ;
SDL_Color c2 = { 120 , 100 , 60 , 255 } ;
SDL_Color c3 = { 200 , 180 , 110 , 255 } ;
2011-12-14 00:23:17 +03:00
ui32 colorID = SDL_MapRGB ( border - > format , c3 . r , c3 . g , c3 . b ) ;
2011-03-22 15:19:07 +02:00
SDL_Color oldColor = border - > format - > palette - > colors [ colorID ] ;
SDL_Color newColor ;
if ( stateCounter < S2_WHITE_B )
2011-12-14 00:23:17 +03:00
newColor = multiplyColors ( c1 , c2 , static_cast < double > ( stateCounter % stageDelay ) / stageDelay ) ;
2011-03-22 15:19:07 +02:00
else
if ( stateCounter < S3_YELLOW_B )
2011-12-14 00:23:17 +03:00
newColor = multiplyColors ( c2 , c3 , static_cast < double > ( stateCounter % stageDelay ) / stageDelay ) ;
2011-03-22 15:19:07 +02:00
else
newColor = oldColor ;
2010-11-15 17:15:00 +02:00
2011-03-22 15:19:07 +02:00
SDL_SetColors ( border , & newColor , colorID , 1 ) ;
2010-11-15 17:15:00 +02:00
blitAtLoc ( border , 0 , 0 , to ) ;
2011-03-22 15:19:07 +02:00
SDL_SetColors ( border , & oldColor , colorID , 1 ) ;
}
if ( stateCounter < BUILDED )
stateCounter + + ;
2010-11-15 17:15:00 +02:00
}
2011-12-22 16:05:19 +03:00
void CBuildingRect : : showAll ( SDL_Surface * to )
2010-11-15 17:15:00 +02:00
{
2011-04-07 20:54:08 +03:00
if ( stateCounter = = 0 )
2011-02-20 11:24:53 +02:00
return ;
2011-03-22 15:19:07 +02:00
2011-02-06 19:26:27 +02:00
CShowableAnim : : showAll ( to ) ;
2011-04-07 20:54:08 +03:00
if ( ! active & & parent - > selectedBuilding = = this & & border )
2011-02-06 19:26:27 +02:00
blitAtLoc ( border , 0 , 0 , to ) ;
2010-11-15 17:15:00 +02:00
}
2010-06-30 22:27:35 +03:00
std : : string getBuildingSubtitle ( int tid , int bid ) //hover text for building
{
const CGTownInstance * t = LOCPLINT - > castleInt - > town ;
bid = hordeToDwellingID ( bid ) ;
2010-11-15 17:15:00 +02:00
2010-06-30 22:27:35 +03:00
if ( bid < 30 ) //non-dwellings - only buiding name
2010-08-16 12:54:09 +03:00
return CGI - > buildh - > buildings [ tid ] . find ( bid ) - > second - > Name ( ) ;
2010-06-30 22:27:35 +03:00
else //dwellings - recruit %creature%
{
2011-12-14 00:23:17 +03:00
int creaID = t - > creatures [ ( bid - 30 ) % GameConstants : : CREATURES_PER_TOWN ] . second . back ( ) ; //taking last of available creatures
2010-06-30 22:27:35 +03:00
return CGI - > generaltexth - > allTexts [ 16 ] + " " + CGI - > creh - > creatures [ creaID ] - > namePl ;
}
}
2008-09-25 17:09:31 +03:00
void CBuildingRect : : mouseMoved ( const SDL_MouseMotionEvent & sEvent )
2008-01-24 00:15:33 +02:00
{
2009-05-30 19:00:26 +03:00
if ( area & & isItIn ( & pos , sEvent . x , sEvent . y ) )
2008-01-24 00:15:33 +02:00
{
2008-03-15 19:48:05 +02:00
if ( CSDL_Ext : : SDL_GetPixel ( area , sEvent . x - pos . x , sEvent . y - pos . y ) = = 0 ) //hovered pixel is inside this building
2008-01-24 00:15:33 +02:00
{
2011-03-22 15:19:07 +02:00
if ( parent - > selectedBuilding = = this )
2008-01-27 22:37:10 +02:00
{
2011-03-22 15:19:07 +02:00
parent - > selectedBuilding = NULL ;
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2008-01-27 22:37:10 +02:00
}
2008-01-24 00:15:33 +02:00
}
2008-03-15 19:48:05 +02:00
else //inside the area of this building
2008-01-24 00:15:33 +02:00
{
2011-03-22 15:19:07 +02:00
if ( ! parent - > selectedBuilding //no building hovered
| | ( * parent - > selectedBuilding ) < ( * this ) ) //or we are on top
2008-01-24 00:15:33 +02:00
{
2011-03-22 15:19:07 +02:00
parent - > selectedBuilding = this ;
2010-06-30 22:27:35 +03:00
GH . statusbar - > print ( getBuildingSubtitle ( str - > townID , str - > ID ) ) ;
2008-01-24 00:15:33 +02:00
}
}
}
}
2010-11-15 17:15:00 +02:00
2012-06-15 20:08:19 +03:00
CDwellingInfoBox : : CDwellingInfoBox ( int centerX , int centerY , const CGTownInstance * Town , int level ) :
CWindowObject ( RCLICK_POPUP | PLAYER_COLORED , " CRTOINFO " , Point ( centerX , centerY ) )
2011-04-07 20:54:08 +03:00
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
const CCreature * creature = CGI - > creh - > creatures [ Town - > creatures [ level ] . second . back ( ) ] ;
2011-12-22 16:05:19 +03:00
title = new CLabel ( 80 , 30 , FONT_SMALL , CENTER , Colors : : Cornsilk , creature - > namePl ) ;
2011-04-07 20:54:08 +03:00
animation = new CCreaturePic ( 30 , 44 , creature , true , true ) ;
std : : string text = boost : : lexical_cast < std : : string > ( Town - > creatures [ level ] . first ) ;
2011-12-22 16:05:19 +03:00
available = new CLabel ( 80 , 190 , FONT_SMALL , CENTER , Colors : : Cornsilk , CGI - > generaltexth - > allTexts [ 217 ] + text ) ;
costPerTroop = new CLabel ( 80 , 227 , FONT_SMALL , CENTER , Colors : : Cornsilk , CGI - > generaltexth - > allTexts [ 346 ] ) ;
2011-04-07 20:54:08 +03:00
2011-12-14 00:23:17 +03:00
for ( int i = 0 ; i < GameConstants : : RESOURCE_QUANTITY ; i + + )
2011-04-07 20:54:08 +03:00
{
if ( creature - > cost [ i ] )
{
2012-05-13 18:04:21 +03:00
resPicture . push_back ( new CAnimImage ( " RESOURCE " , i , 0 , 0 , 0 ) ) ;
2011-12-22 16:05:19 +03:00
resAmount . push_back ( new CLabel ( 0 , 0 , FONT_SMALL , CENTER , Colors : : Cornsilk , boost : : lexical_cast < std : : string > ( creature - > cost [ i ] ) ) ) ;
2011-04-07 20:54:08 +03:00
}
}
int posY = 238 ;
2011-09-23 18:58:18 +03:00
int posX = pos . w / 2 - resAmount . size ( ) * 25 + 5 ;
2011-04-07 20:54:08 +03:00
for ( size_t i = 0 ; i < resAmount . size ( ) ; i + + )
{
2011-12-22 16:05:19 +03:00
resPicture [ i ] - > moveBy ( Point ( posX , posY ) ) ;
resAmount [ i ] - > moveBy ( Point ( posX + 16 , posY + 43 ) ) ;
2011-09-23 18:58:18 +03:00
posX + = 50 ;
2011-04-07 20:54:08 +03:00
}
}
2008-08-16 11:47:41 +03:00
void CHeroGSlot : : hover ( bool on )
{
2010-11-15 17:15:00 +02:00
if ( ! on )
2009-12-23 03:46:15 +02:00
{
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2009-12-23 03:46:15 +02:00
return ;
}
2011-04-30 21:16:58 +03:00
CHeroGSlot * other = upg ? owner - > garrisonedHero : owner - > visitingHero ;
2008-08-16 11:47:41 +03:00
std : : string temp ;
if ( hero )
{
2012-05-13 18:04:21 +03:00
if ( selection ) //view NNN
2008-08-16 11:47:41 +03:00
{
2008-12-22 19:48:41 +02:00
temp = CGI - > generaltexth - > tcommands [ 4 ] ;
2008-08-16 11:47:41 +03:00
boost : : algorithm : : replace_first ( temp , " %s " , hero - > name ) ;
}
2012-05-13 18:04:21 +03:00
else if ( other - > hero & & other - > selection ) //exchange
2008-08-16 11:47:41 +03:00
{
2008-12-22 19:48:41 +02:00
temp = CGI - > generaltexth - > tcommands [ 7 ] ;
2008-08-16 11:47:41 +03:00
boost : : algorithm : : replace_first ( temp , " %s " , hero - > name ) ;
boost : : algorithm : : replace_first ( temp , " %s " , other - > hero - > name ) ;
}
else // select NNN (in ZZZ)
{
if ( upg ) //down - visiting
{
2008-12-22 19:48:41 +02:00
temp = CGI - > generaltexth - > tcommands [ 32 ] ;
2008-08-16 11:47:41 +03:00
boost : : algorithm : : replace_first ( temp , " %s " , hero - > name ) ;
}
else //up - garrison
{
2008-12-22 19:48:41 +02:00
temp = CGI - > generaltexth - > tcommands [ 12 ] ;
2008-08-16 11:47:41 +03:00
boost : : algorithm : : replace_first ( temp , " %s " , hero - > name ) ;
}
}
}
else //we are empty slot
{
2012-05-13 18:04:21 +03:00
if ( other - > selection & & other - > hero ) //move NNNN
2008-08-16 11:47:41 +03:00
{
2008-12-22 19:48:41 +02:00
temp = CGI - > generaltexth - > tcommands [ 6 ] ;
2008-08-16 11:47:41 +03:00
boost : : algorithm : : replace_first ( temp , " %s " , other - > hero - > name ) ;
}
else //empty
{
temp = CGI - > generaltexth - > allTexts [ 507 ] ;
}
}
if ( temp . size ( ) )
2010-02-15 08:54:57 +02:00
GH . statusbar - > print ( temp ) ;
2008-08-16 11:47:41 +03:00
}
2009-04-14 15:47:09 +03:00
2009-08-11 19:05:33 +03:00
void CHeroGSlot : : clickLeft ( tribool down , bool previousState )
2008-08-16 11:47:41 +03:00
{
2011-04-30 21:16:58 +03:00
CHeroGSlot * other = upg ? owner - > garrisonedHero : owner - > visitingHero ;
2008-08-16 11:47:41 +03:00
if ( ! down )
{
2009-05-25 02:21:55 +03:00
owner - > garr - > splitting = false ;
owner - > garr - > highlighted = NULL ;
2009-09-09 09:04:42 +03:00
2012-05-13 18:04:21 +03:00
if ( hero & & selection )
2008-08-16 11:47:41 +03:00
{
2009-09-09 09:04:42 +03:00
setHighlight ( false ) ;
2008-08-16 11:47:41 +03:00
LOCPLINT - > openHeroWindow ( hero ) ;
}
2012-05-13 18:04:21 +03:00
else if ( other - > hero & & other - > selection )
2008-08-25 13:25:16 +03:00
{
2009-04-09 18:05:20 +03:00
bool allow = true ;
2009-10-23 06:07:03 +03:00
if ( upg ) //moving hero out of town - check if it is allowed
2009-04-09 18:05:20 +03:00
{
if ( ! hero & & LOCPLINT - > cb - > howManyHeroes ( false ) > = 8 )
{
std : : string tmp = CGI - > generaltexth - > allTexts [ 18 ] ; //You already have %d adventuring heroes under your command.
boost : : algorithm : : replace_first ( tmp , " %d " , boost : : lexical_cast < std : : string > ( LOCPLINT - > cb - > howManyHeroes ( false ) ) ) ;
2011-12-22 16:05:19 +03:00
LOCPLINT - > showInfoDialog ( tmp , std : : vector < CComponent * > ( ) , soundBase : : sound_todo ) ;
2009-04-09 18:05:20 +03:00
allow = false ;
}
2010-05-02 21:20:26 +03:00
else if ( ! other - > hero - > stacksCount ( ) ) //hero has no creatures - strange, but if we have appropriate error message...
2009-04-09 18:05:20 +03:00
{
2011-12-22 16:05:19 +03:00
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > allTexts [ 19 ] , std : : vector < CComponent * > ( ) , soundBase : : sound_todo ) ; //This hero has no creatures. A hero must have creatures before he can brave the dangers of the countryside.
2009-04-09 18:05:20 +03:00
allow = false ;
}
}
2009-09-09 09:04:42 +03:00
setHighlight ( false ) ;
other - > setHighlight ( false ) ;
2009-04-09 18:05:20 +03:00
if ( allow )
LOCPLINT - > cb - > swapGarrisonHero ( owner - > town ) ;
2008-08-25 13:25:16 +03:00
}
2008-08-16 11:47:41 +03:00
else if ( hero )
{
2009-09-09 09:04:42 +03:00
setHighlight ( true ) ;
2008-08-25 13:25:16 +03:00
owner - > garr - > highlighted = NULL ;
2011-04-30 21:16:58 +03:00
showAll ( screen2 ) ;
2008-08-16 11:47:41 +03:00
}
hover ( false ) ; hover ( true ) ; //refresh statusbar
}
}
2009-04-14 15:47:09 +03:00
2008-08-16 11:47:41 +03:00
void CHeroGSlot : : deactivate ( )
{
2012-06-02 18:16:54 +03:00
vstd : : clear_pointer ( selection ) ;
2010-11-15 17:15:00 +02:00
CIntObject : : deactivate ( ) ;
2008-08-16 11:47:41 +03:00
}
2009-04-14 15:47:09 +03:00
2011-04-30 21:16:58 +03:00
CHeroGSlot : : CHeroGSlot ( int x , int y , int updown , const CGHeroInstance * h , HeroSlots * Owner )
2008-08-16 11:47:41 +03:00
{
owner = Owner ;
2011-04-07 20:54:08 +03:00
pos . x + = x ;
pos . y + = y ;
2008-08-16 11:47:41 +03:00
pos . w = 58 ;
pos . h = 64 ;
upg = updown ;
2012-05-13 18:04:21 +03:00
selection = nullptr ;
image = nullptr ;
set ( h ) ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | HOVER ) ;
2008-08-16 11:47:41 +03:00
}
2009-04-14 15:47:09 +03:00
2008-08-16 11:47:41 +03:00
CHeroGSlot : : ~ CHeroGSlot ( )
{
}
2009-04-14 15:47:09 +03:00
2009-09-09 09:04:42 +03:00
void CHeroGSlot : : setHighlight ( bool on )
{
2012-05-13 18:04:21 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
vstd : : clear_pointer ( selection ) ;
2012-05-13 18:04:21 +03:00
if ( on )
selection = new CAnimImage ( " TWCRPORT " , 1 , 0 ) ;
2011-04-30 21:16:58 +03:00
if ( owner - > garrisonedHero - > hero & & owner - > visitingHero - > hero ) //two heroes in town
2009-09-09 09:04:42 +03:00
{
for ( size_t i = 0 ; i < owner - > garr - > splitButtons . size ( ) ; i + + ) //splitting enabled when slot higlighted
owner - > garr - > splitButtons [ i ] - > block ( ! on ) ;
}
}
2012-05-13 18:04:21 +03:00
void CHeroGSlot : : set ( const CGHeroInstance * newHero )
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
if ( image )
2012-06-02 18:16:54 +03:00
delete image ;
2012-05-13 18:04:21 +03:00
hero = newHero ;
if ( newHero )
image = new CAnimImage ( " PortraitsLarge " , newHero - > portrait , 0 , 0 , 0 ) ;
else if ( ! upg & & owner - > showEmpty ) //up garrison
image = new CAnimImage ( " CREST58 " , LOCPLINT - > castleInt - > town - > getOwner ( ) , 0 , 0 , 0 ) ;
else
image = NULL ;
}
2011-03-22 15:19:07 +02:00
template < class ptr >
2008-01-15 23:38:01 +02:00
class SORTHELP
{
public :
bool operator ( )
2011-03-22 15:19:07 +02:00
( const ptr * a ,
const ptr * b )
2008-01-15 23:38:01 +02:00
{
2008-01-19 13:55:04 +02:00
return ( * a ) < ( * b ) ;
2008-01-15 23:38:01 +02:00
}
2011-03-22 15:19:07 +02:00
} ;
2008-01-09 19:21:31 +02:00
2011-03-22 15:19:07 +02:00
SORTHELP < CBuildingRect > buildSorter ;
SORTHELP < Structure > structSorter ;
2008-04-19 19:15:04 +03:00
2011-03-22 15:19:07 +02:00
CCastleBuildings : : CCastleBuildings ( const CGTownInstance * Town ) :
town ( Town ) ,
selectedBuilding ( NULL )
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2008-04-19 19:15:04 +03:00
2011-03-22 15:19:07 +02:00
background = new CPicture ( graphics - > townBgs [ town - > subID ] ) ;
pos . w = background - > pos . w ;
pos . h = background - > pos . h ;
//Generate buildings list
for ( std : : set < si32 > : : const_iterator building = town - > builtBuildings . begin ( ) ; building ! = town - > builtBuildings . end ( ) ; building + + )
{
std : : map < int , Structure * > : : iterator structure ;
structure = CGI - > townh - > structures [ town - > subID ] . find ( * building ) ;
2008-01-31 23:35:30 +02:00
2012-02-16 20:10:58 +03:00
if ( structure ! = CGI - > townh - > structures [ town - > subID ] . end ( ) & & structure - > second )
2011-03-22 15:19:07 +02:00
{
if ( structure - > second - > group < 0 ) // no group - just add it
2011-04-07 20:54:08 +03:00
buildings . push_back ( new CBuildingRect ( this , town , structure - > second ) ) ;
2011-03-22 15:19:07 +02:00
else // generate list for each group
groups [ structure - > second - > group ] . push_back ( structure - > second ) ;
}
}
2009-07-20 11:18:33 +03:00
2011-03-22 15:19:07 +02:00
Structure * shipyard = CGI - > townh - > structures [ town - > subID ] [ 6 ] ;
//ship in shipyard
if ( shipyard & & vstd : : contains ( groups , shipyard - > group ) )
{
std : : vector < const CGObjectInstance * > vobjs = LOCPLINT - > cb - > getVisitableObjs ( town - > bestLocation ( ) ) ;
2011-12-14 00:23:17 +03:00
if ( ! vobjs . empty ( ) & & ( vobjs . front ( ) - > ID = = 8 | | vobjs . front ( ) - > ID = = GameConstants : : HEROI_TYPE ) ) //there is visitable obj at shipyard output tile and it's a boat or hero (on boat)
2011-03-22 15:19:07 +02:00
{
groups [ shipyard - > group ] . push_back ( CGI - > townh - > structures [ town - > subID ] [ 20 ] ) ;
}
}
//Create building for each group
for ( std : : map < int , std : : vector < const Structure * > > : : iterator group = groups . begin ( ) ; group ! = groups . end ( ) ; group + + )
{
std : : sort ( group - > second . begin ( ) , group - > second . end ( ) , structSorter ) ;
2011-04-07 20:54:08 +03:00
buildings . push_back ( new CBuildingRect ( this , town , group - > second . back ( ) ) ) ;
2011-03-22 15:19:07 +02:00
}
std : : sort ( buildings . begin ( ) , buildings . end ( ) , buildSorter ) ;
checkRules ( ) ;
}
2008-01-31 23:35:30 +02:00
2011-03-22 15:19:07 +02:00
CCastleBuildings : : ~ CCastleBuildings ( )
{
2008-01-09 19:21:31 +02:00
}
2009-04-14 15:47:09 +03:00
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : checkRules ( )
2008-01-09 19:21:31 +02:00
{
2011-11-01 15:58:01 +03:00
//if town tonwID have building toCheck
//then set animation of building buildID to firstA..lastA
//else set to firstB..lastB
struct AnimRule
{
int townID , buildID ;
int toCheck ;
size_t firstA , lastA ;
size_t firstB , lastB ;
} ;
2011-03-22 15:19:07 +02:00
static const AnimRule animRule [ 2 ] =
{
2012-04-08 13:34:23 +03:00
{ 5 , 21 , 4 , 10 , size_t ( - 1 ) , 0 , 10 } , //Mana Vortex, Dungeon
{ 0 , 6 , 8 , 1 , size_t ( - 1 ) , 0 , 1 } //Shipyard, Castle
2011-03-22 15:19:07 +02:00
} ;
for ( size_t i = 0 ; i < 2 ; i + + )
2008-01-15 23:38:01 +02:00
{
2011-03-22 15:19:07 +02:00
if ( town - > subID ! = animRule [ i ] . townID ) //wrong town
continue ;
2011-11-01 15:58:01 +03:00
int buildingID = animRule [ i ] . buildID ;
//check if this building have been upgraded (Ship is upgrade of Shipyard)
2011-03-22 15:19:07 +02:00
int groupID = CGI - > townh - > structures [ town - > subID ] [ animRule [ i ] . buildID ] - > group ;
2011-11-01 15:58:01 +03:00
if ( groupID ! = - 1 )
{
std : : map < int , std : : vector < const Structure * > > : : const_iterator git = groups . find ( groupID ) ;
if ( git = = groups . end ( ) | | git - > second . empty ( ) )
continue ;
buildingID = git - > second . back ( ) - > ID ;
}
2011-03-22 15:19:07 +02:00
2011-11-01 15:58:01 +03:00
BOOST_FOREACH ( CBuildingRect * rect , buildings )
2011-03-22 15:19:07 +02:00
{
2011-11-01 15:58:01 +03:00
if ( rect - > str - > ID = = buildingID )
2011-03-22 15:19:07 +02:00
{
if ( vstd : : contains ( town - > builtBuildings , animRule [ i ] . toCheck ) )
2011-11-01 15:58:01 +03:00
rect - > set ( 0 , animRule [ i ] . firstA , animRule [ i ] . lastA ) ;
2011-03-22 15:19:07 +02:00
else
2011-11-01 15:58:01 +03:00
rect - > set ( 0 , animRule [ i ] . firstB , animRule [ i ] . lastB ) ;
break ;
2011-03-22 15:19:07 +02:00
}
}
2008-01-15 23:38:01 +02:00
}
2011-03-22 15:19:07 +02:00
}
void CCastleBuildings : : addBuilding ( int building )
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
std : : map < int , Structure * > : : const_iterator structure ;
structure = CGI - > townh - > structures [ town - > subID ] . find ( building ) ;
if ( structure ! = CGI - > townh - > structures [ town - > subID ] . end ( ) ) //we have info about that structure
2009-12-23 03:46:15 +02:00
{
2011-03-22 15:19:07 +02:00
if ( structure - > second - > group < 0 ) //no group - just add it
{
2011-04-07 20:54:08 +03:00
buildings . push_back ( new CBuildingRect ( this , town , structure - > second ) ) ;
buildings . back ( ) - > stateCounter = 0 ;
2011-03-22 15:19:07 +02:00
}
else
{
2011-04-07 20:54:08 +03:00
//find last building in this group and replace it with new building if needed
2011-03-22 15:19:07 +02:00
groups [ structure - > second - > group ] . push_back ( structure - > second ) ;
int newBuilding = groups [ structure - > second - > group ] . back ( ) - > ID ;
if ( newBuilding = = building )
{
for ( std : : vector < CBuildingRect * > : : iterator it = buildings . begin ( ) ; it ! = buildings . end ( ) ; it + + )
{
if ( ( * it ) - > str - > ID = = newBuilding )
{
2012-06-02 18:16:54 +03:00
delete * it ;
2011-03-22 15:19:07 +02:00
buildings . erase ( it ) ;
break ;
}
}
2011-04-07 20:54:08 +03:00
buildings . push_back ( new CBuildingRect ( this , town , structure - > second ) ) ;
2011-03-22 15:19:07 +02:00
buildings . back ( ) - > stateCounter = 0 ;
}
}
2009-12-23 03:46:15 +02:00
}
2011-03-22 15:19:07 +02:00
std : : sort ( buildings . begin ( ) , buildings . end ( ) , buildSorter ) ;
checkRules ( ) ;
2008-01-09 19:21:31 +02:00
}
2009-04-14 15:47:09 +03:00
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : removeBuilding ( int building )
2008-01-09 19:21:31 +02:00
{
2011-03-22 15:19:07 +02:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
std : : map < int , Structure * > : : const_iterator structure ;
structure = CGI - > townh - > structures [ town - > subID ] . find ( building ) ;
if ( structure ! = CGI - > townh - > structures [ town - > subID ] . end ( ) ) //we have info about that structure
2010-10-31 21:56:37 +02:00
{
2011-03-22 15:19:07 +02:00
if ( structure - > second - > group < 0 ) //no group - just add it
{
for ( std : : vector < CBuildingRect * > : : iterator it = buildings . begin ( ) ; it ! = buildings . end ( ) ; it + + )
{
if ( ( * it ) - > str - > ID = = building )
{
2012-06-02 18:16:54 +03:00
delete * it ;
2011-03-22 15:19:07 +02:00
buildings . erase ( it ) ;
break ;
}
}
}
2010-10-31 21:56:37 +02:00
else
2011-03-22 15:19:07 +02:00
{
groups [ structure - > second - > group ] . pop_back ( ) ;
2012-06-02 18:16:54 +03:00
delete buildings [ building ] ;
2011-03-22 15:19:07 +02:00
if ( ! groups [ structure - > second - > group ] . empty ( ) )
2011-04-07 20:54:08 +03:00
buildings . push_back ( new CBuildingRect ( this , town , structure - > second ) ) ;
2011-03-22 15:19:07 +02:00
}
2010-10-31 21:56:37 +02:00
}
2011-03-22 15:19:07 +02:00
std : : sort ( buildings . begin ( ) , buildings . end ( ) , buildSorter ) ;
checkRules ( ) ;
}
2011-12-22 16:05:19 +03:00
void CCastleBuildings : : show ( SDL_Surface * to )
2011-03-22 15:19:07 +02:00
{
2011-04-07 20:54:08 +03:00
CIntObject : : show ( to ) ;
2011-03-22 15:19:07 +02:00
for ( std : : vector < CBuildingRect * > : : const_iterator it = buildings . begin ( ) ; it ! = buildings . end ( ) ; it + + )
( * it ) - > show ( to ) ;
}
2011-12-22 16:05:19 +03:00
void CCastleBuildings : : showAll ( SDL_Surface * to )
2011-03-22 15:19:07 +02:00
{
2011-04-07 20:54:08 +03:00
CIntObject : : showAll ( to ) ;
2011-03-22 15:19:07 +02:00
for ( std : : vector < CBuildingRect * > : : const_iterator it = buildings . begin ( ) ; it ! = buildings . end ( ) ; it + + )
( * it ) - > showAll ( to ) ;
2008-01-09 19:21:31 +02:00
}
2009-04-14 15:47:09 +03:00
2011-03-22 15:19:07 +02:00
const CGHeroInstance * CCastleBuildings : : getHero ( )
2008-01-30 00:47:43 +02:00
{
2011-03-22 15:19:07 +02:00
if ( town - > visitingHero )
return town - > visitingHero ;
if ( town - > garrisonHero )
return town - > garrisonHero ;
return NULL ;
2008-01-30 00:47:43 +02:00
}
2009-04-14 15:47:09 +03:00
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : buildingClicked ( int building )
2008-03-10 01:06:35 +02:00
{
2008-09-19 15:09:15 +03:00
tlog5 < < " You've clicked on " < < building < < std : : endl ;
2010-06-30 22:27:35 +03:00
building = hordeToDwellingID ( building ) ;
2010-08-16 12:54:09 +03:00
const CBuilding * b = CGI - > buildh - > buildings [ town - > subID ] . find ( building ) - > second ;
2010-05-26 12:47:53 +03:00
2011-12-14 00:23:17 +03:00
if ( building > = EBuilding : : DWELL_FIRST )
2008-04-04 20:30:53 +03:00
{
2011-12-14 00:23:17 +03:00
enterDwelling ( ( building - EBuilding : : DWELL_FIRST ) % GameConstants : : CREATURES_PER_TOWN ) ;
2008-04-04 20:30:53 +03:00
}
2008-04-20 15:39:33 +03:00
else
2008-03-10 01:06:35 +02:00
{
2008-04-20 15:39:33 +03:00
switch ( building )
{
2011-12-14 00:23:17 +03:00
case EBuilding : : MAGES_GUILD_1 :
case EBuilding : : MAGES_GUILD_2 :
case EBuilding : : MAGES_GUILD_3 :
case EBuilding : : MAGES_GUILD_4 :
case EBuilding : : MAGES_GUILD_5 :
2011-03-22 15:19:07 +02:00
enterMagesGuild ( ) ;
2008-08-20 09:57:53 +03:00
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : TAVERN :
2011-03-22 15:19:07 +02:00
LOCPLINT - > showTavernWindow ( town ) ;
2008-10-26 22:58:34 +02:00
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : SHIPYARD :
2009-07-26 06:33:13 +03:00
LOCPLINT - > showShipyardDialog ( town ) ;
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : FORT :
case EBuilding : : CITADEL :
case EBuilding : : CASTLE :
2011-04-07 20:54:08 +03:00
GH . pushInt ( new CFortScreen ( town ) ) ;
2008-08-17 12:11:16 +03:00
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : VILLAGE_HALL :
case EBuilding : : CITY_HALL :
case EBuilding : : TOWN_HALL :
case EBuilding : : CAPITOL :
2011-03-22 15:19:07 +02:00
enterTownHall ( ) ;
break ;
2011-12-14 00:23:17 +03:00
case EBuilding : : MARKETPLACE :
2011-03-22 15:19:07 +02:00
GH . pushInt ( new CMarketplaceWindow ( town , town - > visitingHero ) ) ;
2008-09-07 06:38:37 +03:00
break ;
2009-12-29 15:40:16 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : BLACKSMITH :
2011-03-22 15:19:07 +02:00
enterBlacksmith ( town - > town - > warMachine ) ;
break ;
2011-12-14 00:23:17 +03:00
case EBuilding : : SPECIAL_1 :
2010-01-25 23:25:14 +02:00
switch ( town - > subID )
2008-08-27 13:19:18 +03:00
{
2011-03-22 15:19:07 +02:00
case 1 : //Mystic Pond
enterFountain ( building ) ;
break ;
case 2 : case 5 : case 8 : //Artifact Merchant
if ( town - > visitingHero )
2011-12-14 00:23:17 +03:00
GH . pushInt ( new CMarketplaceWindow ( town , town - > visitingHero , EMarketMode : : RESOURCE_ARTIFACT ) ) ;
2011-03-22 15:19:07 +02:00
else
LOCPLINT - > showInfoDialog ( boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 273 ] ) % b - > Name ( ) ) ) ; //Only visiting heroes may use the %s.
break ;
2010-10-31 21:17:26 +02:00
2010-01-25 23:25:14 +02:00
default :
2011-03-22 15:19:07 +02:00
enterBuilding ( building ) ;
2010-01-25 23:25:14 +02:00
break ;
2008-08-27 13:19:18 +03:00
}
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : SHIP :
2011-03-22 15:19:07 +02:00
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > allTexts [ 51 ] ) ; //Cannot build another boat
break ;
2011-12-14 00:23:17 +03:00
case EBuilding : : SPECIAL_2 :
2010-01-25 23:25:14 +02:00
switch ( town - > subID )
{
2011-03-22 15:19:07 +02:00
case 1 : //Fountain of Fortune
enterFountain ( building ) ;
break ;
case 6 : //Freelancer's Guild
if ( getHero ( ) )
2011-12-14 00:23:17 +03:00
GH . pushInt ( new CMarketplaceWindow ( town , getHero ( ) , EMarketMode : : CREATURE_RESOURCE ) ) ;
2011-03-22 15:19:07 +02:00
else
LOCPLINT - > showInfoDialog ( boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 273 ] ) % b - > Name ( ) ) ) ; //Only visiting heroes may use the %s.
break ;
case 8 : //Magic University
if ( getHero ( ) )
GH . pushInt ( new CUniversityWindow ( getHero ( ) , town ) ) ;
else
enterBuilding ( building ) ;
break ;
2010-11-15 17:15:00 +02:00
2010-01-25 23:25:14 +02:00
default :
2011-03-22 15:19:07 +02:00
enterBuilding ( building ) ;
break ;
2010-01-25 23:25:14 +02:00
}
break ;
2011-03-22 15:19:07 +02:00
2011-12-14 00:23:17 +03:00
case EBuilding : : SPECIAL_3 :
2009-05-22 02:50:45 +03:00
switch ( town - > subID )
{
2011-03-22 15:19:07 +02:00
case 0 : //Brotherhood of sword
LOCPLINT - > showTavernWindow ( town ) ;
break ;
case 3 : //Castle Gate
enterCastleGate ( ) ;
break ;
2010-11-15 17:15:00 +02:00
2011-03-22 15:19:07 +02:00
case 4 : //Skeleton Transformer
GH . pushInt ( new CTransformerWindow ( getHero ( ) , town ) ) ;
2010-07-03 15:00:53 +03:00
break ;
2010-11-15 17:15:00 +02:00
2011-03-22 15:19:07 +02:00
case 5 : //Portal of Summoning
2011-12-14 00:23:17 +03:00
if ( town - > creatures [ GameConstants : : CREATURES_PER_TOWN ] . second . empty ( ) ) //No creatures
2011-03-22 15:19:07 +02:00
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > tcommands [ 30 ] ) ;
2010-11-15 17:15:00 +02:00
else
2011-12-14 00:23:17 +03:00
enterDwelling ( GameConstants : : CREATURES_PER_TOWN ) ;
2011-03-22 15:19:07 +02:00
break ;
case 6 : //Ballista Yard
enterBlacksmith ( 4 ) ;
break ;
2009-05-22 02:50:45 +03:00
default :
2011-03-22 15:19:07 +02:00
enterBuilding ( building ) ;
break ;
2009-05-22 02:50:45 +03:00
}
break ;
2011-03-22 15:19:07 +02:00
2009-12-30 09:49:25 +02:00
default :
2011-03-22 15:19:07 +02:00
enterBuilding ( building ) ;
2009-12-29 15:40:16 +02:00
break ;
2008-04-20 15:39:33 +03:00
}
2008-03-10 01:06:35 +02:00
}
2009-12-30 09:49:25 +02:00
}
2010-06-26 13:01:26 +03:00
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : enterBlacksmith ( int ArtifactID )
2010-06-26 13:01:26 +03:00
{
2011-03-22 15:19:07 +02:00
const CGHeroInstance * hero = town - > visitingHero ;
if ( ! hero )
{
LOCPLINT - > showInfoDialog ( boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 273 ] ) % CGI - > buildh - > buildings [ town - > subID ] . find ( 16 ) - > second - > Name ( ) ) ) ;
return ;
}
int price = CGI - > arth - > artifacts [ ArtifactID ] - > price ;
bool possible = LOCPLINT - > cb - > getResourceAmount ( Res : : GOLD ) > = price & & ! hero - > hasArt ( ArtifactID + 9 ) ;
GH . pushInt ( new CBlacksmithDialog ( possible , CArtHandler : : convertMachineID ( ArtifactID , false ) , ArtifactID , hero - > id ) ) ;
2010-06-26 13:01:26 +03:00
}
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : enterBuilding ( int building )
2009-12-30 09:49:25 +02:00
{
2012-05-13 18:04:21 +03:00
std : : vector < CComponent * > comps ( 1 , new CComponent ( CComponent : : building , town - > subID , building ) ) ;
2009-12-29 15:40:16 +02:00
2009-12-30 09:49:25 +02:00
LOCPLINT - > showInfoDialog (
2011-03-22 15:19:07 +02:00
CGI - > buildh - > buildings [ town - > subID ] . find ( building ) - > second - > Description ( ) , comps ) ;
}
void CCastleBuildings : : enterCastleGate ( )
{
if ( ! town - > visitingHero )
{
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > allTexts [ 126 ] ) ;
return ; //only visiting hero can use castle gates
}
std : : vector < int > availableTowns ;
std : : vector < const CGTownInstance * > Towns = LOCPLINT - > cb - > getTownsInfo ( false ) ;
for ( size_t i = 0 ; i < Towns . size ( ) ; i + + )
{
const CGTownInstance * t = Towns [ i ] ;
if ( t - > id ! = this - > town - > id & & t - > visitingHero = = NULL & & //another town, empty and this is
t - > subID = = 3 & & vstd : : contains ( t - > builtBuildings , 22 ) ) //inferno with castle gate
{
availableTowns . push_back ( t - > id ) ; //add to the list
}
}
CPicture * titlePic = new CPicture ( LOCPLINT - > castleInt - > bicons - > ourImages [ 22 ] . bitmap , 0 , 0 , false ) ; //will be deleted by selection window
GH . pushInt ( new CObjectListWindow ( availableTowns , titlePic , CGI - > generaltexth - > jktexts [ 40 ] ,
CGI - > generaltexth - > jktexts [ 41 ] , boost : : bind ( & CCastleInterface : : castleTeleport , LOCPLINT - > castleInt , _1 ) ) ) ;
}
void CCastleBuildings : : enterDwelling ( int level )
{
assert ( level > = 0 & & level < town - > creatures . size ( ) ) ;
GH . pushInt ( new CRecruitmentWindow ( town , level , town , boost : : bind ( & CCallback : : recruitCreatures , LOCPLINT - > cb , town , _1 , _2 , level ) , - 87 ) ) ;
2008-03-10 01:06:35 +02:00
}
2009-04-14 15:47:09 +03:00
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : enterFountain ( int building )
2010-01-25 23:25:14 +02:00
{
2012-05-13 18:04:21 +03:00
std : : vector < CComponent * > comps ( 1 , new CComponent ( CComponent : : building , town - > subID , building ) ) ;
2010-01-25 23:25:14 +02:00
2010-08-16 12:54:09 +03:00
std : : string descr = CGI - > buildh - > buildings [ town - > subID ] . find ( building ) - > second - > Description ( ) ;
2010-01-25 23:25:14 +02:00
if ( building = = 21 ) //we need description for mystic pond as well
2011-03-22 15:19:07 +02:00
descr + = " \n \n " + CGI - > buildh - > buildings [ town - > subID ] . find ( 17 ) - > second - > Description ( ) ;
2010-01-28 18:15:46 +02:00
if ( town - > bonusValue . first = = 0 ) //fountain was builded this week
2010-01-25 23:25:14 +02:00
descr + = " \n \n " + CGI - > generaltexth - > allTexts [ 677 ] ;
2010-01-28 18:15:46 +02:00
else //fountain produced something;
2010-01-25 23:25:14 +02:00
{
descr + = " \n \n " + CGI - > generaltexth - > allTexts [ 678 ] ;
2010-01-28 18:15:46 +02:00
boost : : algorithm : : replace_first ( descr , " %s " , CGI - > generaltexth - > restypes [ town - > bonusValue . first ] ) ;
2011-03-22 15:19:07 +02:00
boost : : algorithm : : replace_first ( descr , " %d " , boost : : lexical_cast < std : : string > ( town - > bonusValue . second ) ) ;
2010-01-28 18:15:46 +02:00
}
2011-03-22 15:19:07 +02:00
LOCPLINT - > showInfoDialog ( descr , comps ) ;
2010-01-25 23:25:14 +02:00
}
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : enterMagesGuild ( )
2010-01-25 23:25:14 +02:00
{
2011-03-22 15:19:07 +02:00
const CGHeroInstance * hero = getHero ( ) ;
if ( hero & & ! hero - > hasSpellbook ( ) ) //hero doesn't have spellbok
2010-01-25 23:25:14 +02:00
{
2011-03-22 15:19:07 +02:00
if ( LOCPLINT - > cb - > getResourceAmount ( Res : : GOLD ) < 500 ) //not enough gold to buy spellbook
{
2012-06-02 18:16:54 +03:00
openMagesGuild ( ) ;
2011-03-22 15:19:07 +02:00
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > allTexts [ 213 ] ) ;
}
else
{
2012-06-02 18:16:54 +03:00
CFunctionList < void ( ) > onYes = boost : : bind ( & CCastleBuildings : : openMagesGuild , this ) ;
CFunctionList < void ( ) > onNo = onYes ;
onYes + = boost : : bind ( & CCallback : : buyArtifact , LOCPLINT - > cb , hero , 0 ) ;
2011-12-22 16:05:19 +03:00
std : : vector < CComponent * > components ( 1 , new CComponent ( CComponent : : artifact , 0 , 0 ) ) ;
2011-03-22 15:19:07 +02:00
2012-06-02 18:16:54 +03:00
LOCPLINT - > showYesNoDialog ( CGI - > generaltexth - > allTexts [ 214 ] , onYes , onNo , true , components ) ;
2011-03-22 15:19:07 +02:00
}
2010-01-25 23:25:14 +02:00
}
2011-03-22 15:19:07 +02:00
else
{
openMagesGuild ( ) ;
}
}
void CCastleBuildings : : enterTownHall ( )
{
if ( town - > visitingHero & & town - > visitingHero - > hasArt ( 2 ) & &
2011-12-14 00:23:17 +03:00
! vstd : : contains ( town - > builtBuildings , EBuilding : : GRAIL ) ) //hero has grail, but town does not have it
2011-03-22 15:19:07 +02:00
{
2011-12-14 00:23:17 +03:00
if ( ! vstd : : contains ( town - > forbiddenBuildings , EBuilding : : GRAIL ) )
2011-03-22 15:19:07 +02:00
{
LOCPLINT - > showYesNoDialog ( CGI - > generaltexth - > allTexts [ 597 ] , //Do you wish this to be the permanent home of the Grail?
2011-12-14 00:23:17 +03:00
boost : : bind ( & CCallback : : buildBuilding , LOCPLINT - > cb , town , EBuilding : : GRAIL ) ,
2011-03-22 15:19:07 +02:00
boost : : bind ( & CCastleBuildings : : openTownHall , this ) , true ) ;
}
else
{
LOCPLINT - > showInfoDialog ( CGI - > generaltexth - > allTexts [ 673 ] ) ;
( dynamic_cast < CInfoWindow * > ( GH . topInt ( ) ) ) - > buttons [ 0 ] - > callback + = boost : : bind ( & CCastleBuildings : : openTownHall , this ) ;
}
}
else
{
openTownHall ( ) ;
}
}
void CCastleBuildings : : openMagesGuild ( )
{
GH . pushInt ( new CMageGuildScreen ( LOCPLINT - > castleInt ) ) ;
2010-01-25 23:25:14 +02:00
}
2011-03-22 15:19:07 +02:00
void CCastleBuildings : : openTownHall ( )
2008-03-10 01:06:35 +02:00
{
2011-04-07 20:54:08 +03:00
GH . pushInt ( new CHallInterface ( town ) ) ;
2011-03-22 15:19:07 +02:00
}
2012-06-13 16:04:06 +03:00
CCastleInterface : : CCastleInterface ( const CGTownInstance * Town , const CGTownInstance * from ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( PLAYER_COLORED | BORDERED ) ,
2011-04-07 20:54:08 +03:00
hall ( NULL ) ,
fort ( NULL ) ,
town ( Town )
2011-03-22 15:19:07 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-05-13 18:04:21 +03:00
LOCPLINT - > castleInt = this ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( KEYBOARD ) ;
2011-04-07 20:54:08 +03:00
builds = new CCastleBuildings ( town ) ;
panel = new CPicture ( " TOWNSCRN " , 0 , builds - > pos . h ) ;
panel - > colorize ( LOCPLINT - > playerID ) ;
pos . w = panel - > pos . w ;
pos . h = builds - > pos . h + panel - > pos . h ;
center ( ) ;
2012-06-16 13:41:14 +03:00
updateShadow ( ) ;
2011-04-07 20:54:08 +03:00
2011-12-22 16:05:19 +03:00
garr = new CGarrisonInt ( 305 , 387 , 4 , Point ( 0 , 96 ) , panel - > bg , Point ( 62 , 374 ) , town - > getUpperArmy ( ) , town - > visitingHero ) ;
heroes = new HeroSlots ( town , Point ( 241 , 387 ) , Point ( 241 , 483 ) , garr , true ) ;
title = new CLabel ( 85 , 387 , FONT_MEDIUM , TOPLEFT , Colors : : Cornsilk , town - > name ) ;
2011-04-07 20:54:08 +03:00
income = new CLabel ( 195 , 443 , FONT_SMALL , CENTER ) ;
icon = new CAnimImage ( " ITPT " , 0 , 0 , 15 , 387 ) ;
2011-12-22 16:05:19 +03:00
exit = new CAdventureMapButton ( CGI - > generaltexth - > tcommands [ 8 ] , " " , boost : : bind ( & CCastleInterface : : close , this ) , 744 , 544 , " TSBTNS " , SDLK_RETURN ) ;
2011-03-22 15:19:07 +02:00
exit - > assignedKeys . insert ( SDLK_ESCAPE ) ;
2011-04-07 20:54:08 +03:00
exit - > setOffset ( 4 ) ;
2011-12-22 16:05:19 +03:00
split = new CAdventureMapButton ( CGI - > generaltexth - > tcommands [ 3 ] , " " , boost : : bind ( & CGarrisonInt : : splitClick , garr ) , 744 , 382 , " TSBTNS.DEF " ) ;
2011-04-30 21:16:58 +03:00
split - > callback + = boost : : bind ( & HeroSlots : : splitClicked , heroes ) ;
2011-03-22 15:19:07 +02:00
garr - > addSplitBtn ( split ) ;
2011-12-22 16:05:19 +03:00
Rect barRect ( 9 , 182 , 732 , 18 ) ;
2011-04-07 20:54:08 +03:00
statusbar = new CGStatusBar ( new CPicture ( * panel , barRect , 9 , 555 , false ) ) ;
resdatabar = new CResDataBar ( " ZRESBAR " , 3 , 575 , 32 , 2 , 85 , 85 ) ;
2012-06-13 16:04:06 +03:00
townlist = new CTownList ( 3 , Point ( 744 , 414 ) , " IAM014 " , " IAM015 " ) ;
if ( from )
townlist - > select ( from ) ;
2011-03-22 15:19:07 +02:00
2012-06-13 16:04:06 +03:00
townlist - > select ( town ) ; //this will scroll list to select current town
townlist - > onSelect = boost : : bind ( & CCastleInterface : : townChange , this ) ;
2011-03-22 15:19:07 +02:00
recreateIcons ( ) ;
CCS - > musich - > playMusic ( CCS - > musich - > townMusics [ town - > subID ] , - 1 ) ;
2011-04-07 20:54:08 +03:00
bicons = CDefHandler : : giveDefEss ( graphics - > buildingPics [ town - > subID ] ) ;
2011-03-22 15:19:07 +02:00
}
CCastleInterface : : ~ CCastleInterface ( )
{
2011-04-07 20:54:08 +03:00
LOCPLINT - > castleInt = NULL ;
2011-03-22 15:19:07 +02:00
delete bicons ;
}
void CCastleInterface : : close ( )
{
if ( town - > tempOwner = = LOCPLINT - > playerID ) //we may have opened window for an allied town
{
if ( town - > visitingHero )
adventureInt - > select ( town - > visitingHero ) ;
else
adventureInt - > select ( town ) ;
}
2012-06-15 20:08:19 +03:00
CWindowObject : : close ( ) ;
2011-03-22 15:19:07 +02:00
}
2011-04-07 20:54:08 +03:00
void CCastleInterface : : castleTeleport ( int where )
2009-04-14 15:47:09 +03:00
{
2011-05-03 06:14:18 +03:00
const CGTownInstance * dest = LOCPLINT - > cb - > getTown ( where ) ;
2011-04-07 20:54:08 +03:00
LOCPLINT - > cb - > teleportHero ( town - > visitingHero , dest ) ;
2008-01-19 14:26:55 +02:00
}
2009-04-14 15:47:09 +03:00
2008-01-31 23:35:30 +02:00
void CCastleInterface : : townChange ( )
{
2012-06-13 16:04:06 +03:00
const CGTownInstance * dest = LOCPLINT - > towns [ townlist - > getSelectedIndex ( ) ] ;
const CGTownInstance * town = this - > town ; // "this" is going to be deleted
if ( dest = = town )
2011-01-01 22:26:39 +02:00
return ;
2012-06-15 20:08:19 +03:00
close ( ) ;
2012-06-13 16:04:06 +03:00
GH . pushInt ( new CCastleInterface ( dest , town ) ) ;
2008-01-31 23:35:30 +02:00
}
2009-04-14 15:47:09 +03:00
2008-03-23 03:01:17 +02:00
void CCastleInterface : : addBuilding ( int bid )
{
2008-08-01 21:13:33 +03:00
deactivate ( ) ;
2011-03-22 15:19:07 +02:00
builds - > addBuilding ( bid ) ;
2009-12-23 03:46:15 +02:00
recreateIcons ( ) ;
2008-08-01 21:13:33 +03:00
activate ( ) ;
2008-03-23 03:01:17 +02:00
}
void CCastleInterface : : removeBuilding ( int bid )
{
2011-04-07 20:54:08 +03:00
deactivate ( ) ;
2011-03-22 15:19:07 +02:00
builds - > removeBuilding ( bid ) ;
2009-12-23 03:46:15 +02:00
recreateIcons ( ) ;
2011-04-07 20:54:08 +03:00
activate ( ) ;
2008-03-23 03:01:17 +02:00
}
2009-12-23 03:46:15 +02:00
void CCastleInterface : : recreateIcons ( )
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
delete fort ;
delete hall ;
2011-04-07 20:54:08 +03:00
size_t iconIndex = town - > subID * 2 ;
if ( ! town - > hasFort ( ) )
2011-12-14 00:23:17 +03:00
iconIndex + = GameConstants : : F_NUMBER * 2 ;
2009-12-23 03:46:15 +02:00
2011-12-14 00:23:17 +03:00
if ( town - > builded > = GameConstants : : MAX_BUILDING_PER_TURN )
2011-04-07 20:54:08 +03:00
iconIndex + + ;
2009-12-23 03:46:15 +02:00
2011-04-07 20:54:08 +03:00
icon - > setFrame ( iconIndex ) ;
income - > setTxt ( boost : : lexical_cast < std : : string > ( town - > dailyIncome ( ) ) ) ;
hall = new CTownInfo ( 80 , 413 , town , true ) ;
fort = new CTownInfo ( 122 , 413 , town , false ) ;
for ( size_t i = 0 ; i < creainfo . size ( ) ; i + + )
2012-06-02 18:16:54 +03:00
delete creainfo [ i ] ;
2009-12-23 03:46:15 +02:00
creainfo . clear ( ) ;
2011-04-07 20:54:08 +03:00
for ( size_t i = 0 ; i < 4 ; i + + )
2011-12-22 16:05:19 +03:00
creainfo . push_back ( new CCreaInfo ( Point ( 14 + 55 * i , 459 ) , town , i ) ) ;
2011-04-07 20:54:08 +03:00
for ( size_t i = 0 ; i < 4 ; i + + )
2011-12-22 16:05:19 +03:00
creainfo . push_back ( new CCreaInfo ( Point ( 14 + 55 * i , 507 ) , town , i + 4 ) ) ;
2009-12-23 03:46:15 +02:00
}
2011-04-07 20:54:08 +03:00
2011-12-22 16:05:19 +03:00
CCreaInfo : : CCreaInfo ( Point position , const CGTownInstance * Town , int Level , bool compact , bool ShowAvailable ) :
2011-04-07 20:54:08 +03:00
town ( Town ) ,
2011-07-18 18:21:16 +03:00
level ( Level ) ,
showAvailable ( ShowAvailable )
2009-12-23 03:46:15 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2011-07-18 18:21:16 +03:00
pos + = position ;
2011-04-07 20:54:08 +03:00
if ( town - > creatures . size ( ) < = level | | town - > creatures [ level ] . second . empty ( ) )
{
level = - 1 ;
2011-07-18 18:21:16 +03:00
label = NULL ;
picture = NULL ;
2011-04-07 20:54:08 +03:00
return ; //No creature
}
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | RCLICK | HOVER ) ;
2011-04-07 20:54:08 +03:00
2011-12-14 00:23:17 +03:00
ui32 creatureID = town - > creatures [ level ] . second . back ( ) ;
2011-04-07 20:54:08 +03:00
creature = CGI - > creh - > creatures [ creatureID ] ;
picture = new CAnimImage ( " CPRSMALL " , creatureID + 2 , 0 , 8 , 0 ) ;
2011-07-18 18:21:16 +03:00
std : : string value ;
if ( showAvailable )
value = boost : : lexical_cast < std : : string > ( town - > creatures [ level ] . first ) ;
else
value = boost : : lexical_cast < std : : string > ( town - > creatureGrowth ( level ) ) ;
if ( compact )
{
2011-12-22 16:05:19 +03:00
label = new CLabel ( 40 , 32 , FONT_TINY , BOTTOMRIGHT , Colors : : Cornsilk , value ) ;
2011-07-18 18:21:16 +03:00
pos . x + = 8 ;
pos . w = 32 ;
pos . h = 32 ;
}
else
{
2011-12-22 16:05:19 +03:00
label = new CLabel ( 24 , 40 , FONT_SMALL , CENTER , Colors : : Cornsilk , value ) ;
2011-07-18 18:21:16 +03:00
pos . w = 48 ;
pos . h = 48 ;
}
}
void CCreaInfo : : update ( )
{
if ( label )
{
std : : string value ;
if ( showAvailable )
value = boost : : lexical_cast < std : : string > ( town - > creatures [ level ] . first ) ;
else
value = boost : : lexical_cast < std : : string > ( town - > creatureGrowth ( level ) ) ;
if ( value ! = label - > text )
label - > setTxt ( value ) ;
}
2009-12-23 03:46:15 +02:00
}
2011-04-07 20:54:08 +03:00
void CCreaInfo : : hover ( bool on )
2009-12-23 03:46:15 +02:00
{
2011-04-30 21:16:58 +03:00
std : : string message = CGI - > generaltexth - > allTexts [ 588 ] ;
boost : : algorithm : : replace_first ( message , " %s " , creature - > namePl ) ;
2009-12-23 03:46:15 +02:00
if ( on )
{
2011-04-30 21:16:58 +03:00
GH . statusbar - > print ( message ) ;
2009-12-23 03:46:15 +02:00
}
2011-04-30 21:16:58 +03:00
else if ( message = = GH . statusbar - > getCurrent ( ) )
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2009-12-23 03:46:15 +02:00
}
2010-07-10 19:50:23 +03:00
2011-04-07 20:54:08 +03:00
void CCreaInfo : : clickLeft ( tribool down , bool previousState )
2011-07-18 18:21:16 +03:00
{
if ( previousState & & ( ! down ) )
{
int offset = LOCPLINT - > castleInt ? ( - 87 ) : 0 ;
GH . pushInt ( new CRecruitmentWindow ( town , level , town ,
boost : : bind ( & CCallback : : recruitCreatures , LOCPLINT - > cb , town , _1 , _2 , level ) , offset ) ) ;
}
2010-07-10 19:50:23 +03:00
}
2009-12-23 03:46:15 +02:00
2011-04-07 20:54:08 +03:00
int CCreaInfo : : AddToString ( std : : string from , std : : string & to , int numb )
2009-12-23 03:46:15 +02:00
{
2011-04-07 20:54:08 +03:00
if ( numb = = 0 )
return 0 ;
2010-10-02 10:10:38 +03:00
boost : : algorithm : : replace_first ( from , " %+d " , ( numb > 0 ? " + " : " " ) + boost : : lexical_cast < std : : string > ( numb ) ) ; //negative values don't need "+"
2009-12-23 03:46:15 +02:00
to + = " \n " + from ;
return numb ;
2010-07-10 19:50:23 +03:00
}
2009-12-23 03:46:15 +02:00
2011-07-18 18:21:16 +03:00
std : : string CCreaInfo : : genGrowthText ( )
2009-12-23 03:46:15 +02:00
{
2011-08-26 23:32:05 +03:00
GrowthInfo gi = town - > getGrowthInfo ( level ) ;
std : : string descr = boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 589 ] ) % creature - > nameSing % gi . totalGrowth ( ) ) ;
2009-12-23 03:46:15 +02:00
2011-08-26 23:32:05 +03:00
BOOST_FOREACH ( const GrowthInfo : : Entry & entry , gi . entries )
2011-07-18 18:21:16 +03:00
{
2011-08-26 23:32:05 +03:00
descr + = " \n " + entry . description ;
2011-07-18 18:21:16 +03:00
}
2011-08-26 23:32:05 +03:00
2011-07-18 18:21:16 +03:00
return descr ;
}
2009-12-23 03:46:15 +02:00
2011-07-18 18:21:16 +03:00
void CCreaInfo : : clickRight ( tribool down , bool previousState )
{
if ( down )
{
if ( showAvailable )
GH . pushInt ( new CDwellingInfoBox ( screen - > w / 2 , screen - > h / 2 , town , level ) ) ;
else
{
std : : string descr = genGrowthText ( ) ;
CInfoPopup * mess = new CInfoPopup ( ) ; //creating popup
mess - > free = true ;
mess - > bitmap = CMessage : : drawBoxTextBitmapSub
( LOCPLINT - > playerID , descr , graphics - > bigImgs [ creature - > idNumber ] , " " ) ;
mess - > pos . x = screen - > w / 2 - mess - > bitmap - > w / 2 ;
mess - > pos . y = screen - > h / 2 - mess - > bitmap - > h / 2 ;
GH . pushInt ( mess ) ;
}
2009-12-23 03:46:15 +02:00
}
}
2010-06-30 22:27:35 +03:00
2011-04-07 20:54:08 +03:00
CTownInfo : : CTownInfo ( int posX , int posY , const CGTownInstance * Town , bool townHall ) :
town ( Town ) ,
building ( NULL )
2009-12-23 03:46:15 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( RCLICK | HOVER ) ;
2011-04-07 20:54:08 +03:00
pos . x + = posX ;
pos . y + = posY ;
int buildID ;
2010-06-30 22:27:35 +03:00
2011-04-07 20:54:08 +03:00
if ( townHall )
{
buildID = 10 + town - > hallLevel ( ) ;
picture = new CAnimImage ( " ITMTL.DEF " , town - > hallLevel ( ) ) ;
}
else
2009-12-23 03:46:15 +02:00
{
2011-04-07 20:54:08 +03:00
buildID = 6 + town - > fortLevel ( ) ;
if ( buildID = = 6 )
return ;
picture = new CAnimImage ( " ITMCL.DEF " , town - > fortLevel ( ) - 1 ) ;
2009-12-23 03:46:15 +02:00
}
2011-04-07 20:54:08 +03:00
building = CGI - > buildh - > buildings [ town - > subID ] [ buildID ] ;
pos = picture - > pos ;
2009-12-23 03:46:15 +02:00
}
2011-04-07 20:54:08 +03:00
void CTownInfo : : hover ( bool on )
2009-12-23 03:46:15 +02:00
{
if ( on )
{
2011-04-07 20:54:08 +03:00
if ( building )
GH . statusbar - > print ( building - > Name ( ) ) ;
2009-12-23 03:46:15 +02:00
}
else
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2009-12-23 03:46:15 +02:00
}
2010-06-30 22:27:35 +03:00
2011-04-07 20:54:08 +03:00
void CTownInfo : : clickRight ( tribool down , bool previousState )
{ //FIXME: castleInt may be NULL
2011-04-30 21:16:58 +03:00
if ( down & & building & & LOCPLINT - > castleInt )
2010-11-15 17:15:00 +02:00
{
2009-12-23 03:46:15 +02:00
CInfoPopup * mess = new CInfoPopup ( ) ;
mess - > free = true ;
2011-04-07 20:54:08 +03:00
2009-12-23 03:46:15 +02:00
mess - > bitmap = CMessage : : drawBoxTextBitmapSub
2011-04-07 20:54:08 +03:00
( LOCPLINT - > playerID ,
building - > Description ( ) ,
LOCPLINT - > castleInt - > bicons - > ourImages [ building - > bid ] . bitmap ,
building - > Name ( ) ) ;
2009-12-23 03:46:15 +02:00
mess - > pos . x = screen - > w / 2 - mess - > bitmap - > w / 2 ;
mess - > pos . y = screen - > h / 2 - mess - > bitmap - > h / 2 ;
GH . pushInt ( mess ) ;
}
}
2010-06-30 22:27:35 +03:00
2009-07-20 11:18:33 +03:00
void CCastleInterface : : keyPressed ( const SDL_KeyboardEvent & key )
{
2009-09-07 05:29:44 +03:00
if ( key . state ! = SDL_PRESSED ) return ;
2009-07-20 11:18:33 +03:00
switch ( key . keysym . sym )
{
case SDLK_UP :
2012-06-13 16:04:06 +03:00
townlist - > selectPrev ( ) ;
2009-07-20 11:18:33 +03:00
break ;
case SDLK_DOWN :
2012-06-13 16:04:06 +03:00
townlist - > selectNext ( ) ;
2009-07-20 11:18:33 +03:00
break ;
case SDLK_SPACE :
2011-02-04 16:58:14 +02:00
if ( ! ! town - > visitingHero & & town - > garrisonHero )
2009-07-20 11:18:33 +03:00
{
LOCPLINT - > cb - > swapGarrisonHero ( town ) ;
}
break ;
2012-04-08 04:15:18 +03:00
case SDLK_t :
if ( town - > hasBuilt ( EBuilding : : TAVERN ) )
LOCPLINT - > showTavernWindow ( town ) ;
break ;
2009-10-13 07:07:26 +03:00
default :
break ;
2009-07-20 11:18:33 +03:00
}
}
2011-12-22 16:05:19 +03:00
HeroSlots : : HeroSlots ( const CGTownInstance * Town , Point garrPos , Point visitPos , CGarrisonInt * Garrison , bool ShowEmpty ) :
2011-04-30 21:16:58 +03:00
showEmpty ( ShowEmpty ) ,
town ( Town ) ,
garr ( Garrison )
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
garrisonedHero = new CHeroGSlot ( garrPos . x , garrPos . y , 0 , town - > garrisonHero , this ) ;
visitingHero = new CHeroGSlot ( visitPos . x , visitPos . y , 1 , town - > visitingHero , this ) ;
}
void HeroSlots : : update ( )
{
2012-05-13 18:04:21 +03:00
garrisonedHero - > set ( town - > garrisonHero ) ;
visitingHero - > set ( town - > visitingHero ) ;
2011-04-30 21:16:58 +03:00
}
void HeroSlots : : splitClicked ( )
2009-09-09 09:04:42 +03:00
{
2012-05-13 18:04:21 +03:00
if ( ! ! town - > visitingHero & & town - > garrisonHero & & ( visitingHero - > selection | | garrisonedHero - > selection ) )
2009-09-09 09:04:42 +03:00
{
LOCPLINT - > heroExchangeStarted ( town - > visitingHero - > id , town - > garrisonHero - > id ) ;
}
}
2008-03-10 01:06:35 +02:00
void CHallInterface : : CBuildingBox : : hover ( bool on )
{
2008-03-16 02:09:43 +02:00
if ( on )
{
2008-06-03 21:16:54 +03:00
std : : string toPrint ;
2011-12-14 00:23:17 +03:00
if ( state = = EBuildingState : : PREREQUIRES )
2008-12-22 19:48:41 +02:00
toPrint = CGI - > generaltexth - > hcommands [ 5 ] ;
2011-12-14 00:23:17 +03:00
else if ( state = = EBuildingState : : CANT_BUILD_TODAY )
2009-12-23 03:46:15 +02:00
toPrint = CGI - > generaltexth - > allTexts [ 223 ] ;
2008-06-03 21:16:54 +03:00
else
2008-12-22 19:48:41 +02:00
toPrint = CGI - > generaltexth - > hcommands [ state ] ;
2011-04-07 20:54:08 +03:00
boost : : algorithm : : replace_first ( toPrint , " %s " , building - > Name ( ) ) ;
GH . statusbar - > print ( toPrint ) ;
2008-03-16 02:09:43 +02:00
}
else
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2008-03-10 01:06:35 +02:00
}
2011-04-07 20:54:08 +03:00
2009-08-11 19:05:33 +03:00
void CHallInterface : : CBuildingBox : : clickLeft ( tribool down , bool previousState )
2008-03-10 01:06:35 +02:00
{
2009-08-11 19:05:33 +03:00
if ( previousState & & ( ! down ) )
2011-04-07 20:54:08 +03:00
GH . pushInt ( new CBuildWindow ( town , building , state , 0 ) ) ;
2008-03-10 01:06:35 +02:00
}
2011-04-07 20:54:08 +03:00
2009-08-11 19:05:33 +03:00
void CHallInterface : : CBuildingBox : : clickRight ( tribool down , bool previousState )
2008-03-10 01:06:35 +02:00
{
2008-03-21 02:03:31 +02:00
if ( down )
2011-04-07 20:54:08 +03:00
GH . pushInt ( new CBuildWindow ( town , building , state , 1 ) ) ;
2008-03-11 23:36:59 +02:00
}
2011-04-07 20:54:08 +03:00
CHallInterface : : CBuildingBox : : CBuildingBox ( int x , int y , const CGTownInstance * Town , const CBuilding * Building ) :
town ( Town ) ,
building ( Building )
2008-03-11 23:36:59 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | RCLICK | HOVER ) ;
2011-04-07 20:54:08 +03:00
pos . x + = x ;
pos . y + = y ;
pos . w = 154 ;
pos . h = 92 ;
state = LOCPLINT - > cb - > canBuildStructure ( town , building - > bid ) ;
2011-12-14 00:23:17 +03:00
assert ( state < EBuildingState : : BUILDING_ERROR ) ;
2011-04-07 20:54:08 +03:00
static int panelIndex [ 9 ] = { 3 , 3 , 3 , 0 , 0 , 2 , 2 , 1 , 2 } ;
static int iconIndex [ 9 ] = { - 1 , - 1 , - 1 , 0 , 0 , 1 , 2 , - 1 , 1 } ;
2008-03-10 01:06:35 +02:00
2011-04-07 20:54:08 +03:00
picture = new CAnimImage ( graphics - > buildingPics [ town - > subID ] , building - > bid , 0 , 2 , 2 ) ;
panel = new CAnimImage ( " TPTHBAR " , panelIndex [ state ] , 0 , 1 , 73 ) ;
if ( iconIndex [ state ] > = 0 )
icon = new CAnimImage ( " TPTHCHK " , iconIndex [ state ] , 0 , 136 , 56 ) ;
2011-12-22 16:05:19 +03:00
label = new CLabel ( 75 , 81 , FONT_SMALL , CENTER , Colors : : Cornsilk , building - > Name ( ) ) ;
2011-04-07 20:54:08 +03:00
}
2008-03-10 01:06:35 +02:00
2011-04-07 20:54:08 +03:00
CHallInterface : : CHallInterface ( const CGTownInstance * Town ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( PLAYER_COLORED | BORDERED , CGI - > buildh - > hall [ Town - > subID ] . first ) ,
2011-04-07 20:54:08 +03:00
town ( Town )
2008-03-10 01:06:35 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2009-05-20 12:02:50 +03:00
resdatabar = new CMinorResDataBar ;
resdatabar - > pos . x + = pos . x ;
resdatabar - > pos . y + = pos . y ;
2011-12-22 16:05:19 +03:00
Rect barRect ( 5 , 556 , 740 , 18 ) ;
2011-04-07 20:54:08 +03:00
statusBar = new CGStatusBar ( new CPicture ( * background , barRect , 5 , 556 , false ) ) ;
2011-12-22 16:05:19 +03:00
title = new CLabel ( 399 , 12 , FONT_MEDIUM , CENTER , Colors : : Cornsilk , CGI - > buildh - > buildings [ town - > subID ] [ town - > hallLevel ( ) + EBuilding : : VILLAGE_HALL ] - > Name ( ) ) ;
exit = new CAdventureMapButton ( CGI - > generaltexth - > hcommands [ 8 ] , " " ,
2011-04-07 20:54:08 +03:00
boost : : bind ( & CHallInterface : : close , this ) , 748 , 556 , " TPMAGE1.DEF " , SDLK_RETURN ) ;
2008-11-28 03:36:34 +02:00
exit - > assignedKeys . insert ( SDLK_ESCAPE ) ;
2008-03-21 02:03:31 +02:00
2011-04-07 20:54:08 +03:00
const std : : vector < std : : vector < std : : vector < int > > > & boxList = CGI - > buildh - > hall [ town - > subID ] . second ;
boxes . resize ( boxList . size ( ) ) ;
for ( size_t row = 0 ; row < boxList . size ( ) ; row + + ) //for each row
2008-03-11 23:36:59 +02:00
{
2011-04-07 20:54:08 +03:00
for ( size_t col = 0 ; col < boxList [ row ] . size ( ) ; col + + ) //for each box
2008-03-11 23:36:59 +02:00
{
2011-04-07 20:54:08 +03:00
const CBuilding * building = NULL ;
for ( size_t item = 0 ; item < boxList [ row ] [ col ] . size ( ) ; item + + ) //we are looking for the first not build structure
2008-03-11 23:36:59 +02:00
{
2011-04-07 20:54:08 +03:00
int buildingID = boxList [ row ] [ col ] [ item ] ;
building = CGI - > buildh - > buildings [ town - > subID ] [ buildingID ] ;
2011-11-27 16:14:20 +03:00
if ( buildingID = = 18 | | buildingID = = 24 )
{
if ( ( buildingID = = 18 & & ! vstd : : contains ( town - > builtBuildings , town - > town - > hordeLvl [ 0 ] + 37 ) )
| | ( buildingID = = 24 & & ! vstd : : contains ( town - > builtBuildings , town - > town - > hordeLvl [ 1 ] + 37 ) ) )
break ; // horde present, no upgraded dwelling -> select 18 or 24
else
continue ; //upgraded dwelling, no horde -> select 19 or 25
}
2011-08-19 22:50:24 +03:00
2011-04-07 20:54:08 +03:00
if ( vstd : : contains ( town - > builtBuildings , buildingID ) )
continue ;
break ;
2008-03-11 23:36:59 +02:00
}
2011-04-07 20:54:08 +03:00
int posX = pos . w / 2 - boxList [ row ] . size ( ) * 154 / 2 - ( boxList [ row ] . size ( ) - 1 ) * 20 + 194 * col ,
posY = 35 + 104 * row ;
if ( building )
boxes [ row ] . push_back ( new CBuildingBox ( posX , posY , town , building ) ) ;
2008-03-11 23:36:59 +02:00
}
}
2008-03-10 01:06:35 +02:00
}
2009-04-14 15:47:09 +03:00
2011-04-07 20:54:08 +03:00
void CBuildWindow : : buyFunc ( )
2008-03-21 02:03:31 +02:00
{
2011-04-07 20:54:08 +03:00
LOCPLINT - > cb - > buildBuilding ( town , building - > bid ) ;
GH . popInts ( 2 ) ; //we - build window and hall screen
2008-03-21 02:03:31 +02:00
}
2009-04-14 15:47:09 +03:00
2011-04-07 20:54:08 +03:00
std : : string CBuildWindow : : getTextForState ( int state )
2008-03-21 02:03:31 +02:00
{
2008-03-23 03:01:17 +02:00
std : : string ret ;
2008-03-21 02:03:31 +02:00
if ( state < 7 )
2008-12-22 19:48:41 +02:00
ret = CGI - > generaltexth - > hcommands [ state ] ;
2008-03-21 02:03:31 +02:00
switch ( state )
{
2008-06-03 21:16:54 +03:00
case 4 : case 5 : case 6 :
2011-04-07 20:54:08 +03:00
ret . replace ( ret . find_first_of ( " %s " ) , 2 , building - > Name ( ) ) ;
2008-03-23 03:01:17 +02:00
break ;
2008-03-21 02:03:31 +02:00
case 7 :
return CGI - > generaltexth - > allTexts [ 219 ] ; //all prereq. are met
2008-03-23 03:01:17 +02:00
case 8 :
{
ret = CGI - > generaltexth - > allTexts [ 52 ] ;
2011-04-07 20:54:08 +03:00
std : : set < int > reqs = LOCPLINT - > cb - > getBuildingRequiments ( town , building - > bid ) ;
2009-12-30 09:49:25 +02:00
2008-03-23 03:01:17 +02:00
for ( std : : set < int > : : iterator i = reqs . begin ( ) ; i ! = reqs . end ( ) ; i + + )
2009-12-30 09:49:25 +02:00
{
2011-04-07 20:54:08 +03:00
if ( vstd : : contains ( town - > builtBuildings , * i ) )
2009-12-29 15:40:16 +02:00
continue ; //skipping constructed buildings
2011-04-07 20:54:08 +03:00
ret + = CGI - > buildh - > buildings [ town - > subID ] [ * i ] - > Name ( ) + " , " ;
2008-03-23 03:01:17 +02:00
}
2011-04-07 20:54:08 +03:00
ret . erase ( ret . size ( ) - 2 ) ;
2008-03-23 03:01:17 +02:00
}
2008-03-21 02:03:31 +02:00
}
2008-03-23 03:01:17 +02:00
return ret ;
2008-03-16 02:09:43 +02:00
}
2009-04-14 15:47:09 +03:00
2012-06-13 16:04:06 +03:00
CBuildWindow : : CBuildWindow ( const CGTownInstance * Town , const CBuilding * Building , int State , bool rightClick ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( PLAYER_COLORED | ( rightClick ? RCLICK_POPUP : 0 ) , " TPUBUILD " ) ,
2012-06-13 16:04:06 +03:00
town ( Town ) ,
building ( Building ) ,
state ( State )
2011-04-07 20:54:08 +03:00
{
OBJ_CONSTRUCTION_CAPTURING_ALL ;
buildingPic = new CAnimImage ( graphics - > buildingPics [ town - > subID ] , building - > bid , 0 , 125 , 50 ) ;
2011-12-22 16:05:19 +03:00
Rect barRect ( 9 , 494 , 380 , 18 ) ;
2011-04-07 20:54:08 +03:00
statusBar = new CGStatusBar ( new CPicture ( * background , barRect , 9 , 494 , false ) ) ;
2011-12-22 16:05:19 +03:00
title = new CLabel ( 197 , 30 , FONT_MEDIUM , CENTER , Colors : : Cornsilk ,
2011-04-07 20:54:08 +03:00
boost : : str ( boost : : format ( CGI - > generaltexth - > hcommands [ 7 ] ) % building - > Name ( ) ) ) ;
2011-12-22 16:05:19 +03:00
buildingDescr = new CTextBox ( building - > Description ( ) , Rect ( 33 , 135 , 329 , 67 ) , 0 , FONT_MEDIUM , CENTER ) ;
buildingState = new CTextBox ( getTextForState ( state ) , Rect ( 33 , 216 , 329 , 67 ) , 0 , FONT_SMALL , CENTER ) ;
2011-04-07 20:54:08 +03:00
//Create objects for all required resources
2011-12-14 00:23:17 +03:00
for ( int i = 0 ; i < GameConstants : : RESOURCE_QUANTITY ; i + + )
2008-12-23 15:59:03 +02:00
{
2011-04-07 20:54:08 +03:00
if ( building - > resources [ i ] )
2008-12-23 15:59:03 +02:00
{
2012-05-13 18:04:21 +03:00
resPicture . push_back ( new CAnimImage ( " RESOURCE " , i ) ) ;
2011-12-22 16:05:19 +03:00
resAmount . push_back ( new CLabel ( 0 , 0 , FONT_SMALL , CENTER , Colors : : Cornsilk ,
2011-04-07 20:54:08 +03:00
boost : : lexical_cast < std : : string > ( building - > resources [ i ] ) ) ) ;
2008-12-23 15:59:03 +02:00
}
}
2011-04-07 20:54:08 +03:00
2011-12-14 00:23:17 +03:00
ui32 rowSize [ 2 ] ;
2011-04-07 20:54:08 +03:00
int posY ;
if ( resAmount . size ( ) > 4 )
{ //Resources will be placed in multiple rows
rowSize [ 0 ] = ( resAmount . size ( ) + 1 ) / 2 ;
posY = 303 ;
}
else
{ //one row
rowSize [ 0 ] = resAmount . size ( ) ;
posY = 340 ;
}
rowSize [ 1 ] = resAmount . size ( ) - rowSize [ 0 ] ;
2011-12-14 00:23:17 +03:00
ui32 index = 0 ;
2011-04-07 20:54:08 +03:00
for ( size_t row = 0 ; row < 2 ; row + + )
{
int posX = pos . w / 2 - rowSize [ row ] * 40 + 24 ;
for ( size_t i = 0 ; i < rowSize [ row ] ; i + + )
{ //Move current resource to correct position
2011-12-22 16:05:19 +03:00
resPicture [ index ] - > moveBy ( Point ( posX , posY ) ) ;
resAmount [ index ] - > moveBy ( Point ( posX + 16 , posY + 48 ) ) ;
2011-04-07 20:54:08 +03:00
posX + = 80 ;
index + + ;
2008-03-21 02:03:31 +02:00
}
2011-04-07 20:54:08 +03:00
posY + = 75 ;
2008-03-21 02:03:31 +02:00
}
2011-04-07 20:54:08 +03:00
2012-06-13 16:04:06 +03:00
if ( ! rightClick )
2012-02-21 17:08:42 +03:00
{ //normal window
2011-12-22 16:05:19 +03:00
buy = new CAdventureMapButton ( boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 595 ] ) % building - > Name ( ) ) ,
2011-04-07 20:54:08 +03:00
" " , boost : : bind ( & CBuildWindow : : buyFunc , this ) , 45 , 446 , " IBUY30 " , SDLK_RETURN ) ;
2011-04-30 22:52:35 +03:00
buy - > borderColor = Colors : : MetallicGold ;
2011-04-26 16:30:29 +03:00
buy - > borderEnabled = true ;
2011-12-22 16:05:19 +03:00
cancel = new CAdventureMapButton ( boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 596 ] ) % building - > Name ( ) ) ,
2011-04-07 20:54:08 +03:00
" " , boost : : bind ( & CBuildWindow : : close , this ) , 290 , 445 , " ICANCEL " , SDLK_ESCAPE ) ;
2011-04-30 22:52:35 +03:00
cancel - > borderColor = Colors : : MetallicGold ;
2011-04-26 16:30:29 +03:00
cancel - > borderEnabled = true ;
2012-02-21 17:08:42 +03:00
buy - > block ( state ! = 7 | | LOCPLINT - > playerID ! = town - > tempOwner ) ;
2008-03-23 03:01:17 +02:00
}
2008-03-16 02:09:43 +02:00
}
2009-04-14 15:47:09 +03:00
2011-04-07 20:54:08 +03:00
2012-06-02 18:16:54 +03:00
std : : string CFortScreen : : getBgName ( const CGTownInstance * town )
2011-04-07 20:54:08 +03:00
{
2012-06-02 18:16:54 +03:00
ui32 fortSize = town - > creatures . size ( ) ;
if ( fortSize > GameConstants : : CREATURES_PER_TOWN & & town - > creatures . back ( ) . second . empty ( ) )
fortSize - - ;
if ( fortSize = = GameConstants : : CREATURES_PER_TOWN )
return " TPCASTL7 " ;
else
return " TPCASTL8 " ;
2011-04-07 20:54:08 +03:00
}
2012-06-02 18:16:54 +03:00
CFortScreen : : CFortScreen ( const CGTownInstance * town ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( PLAYER_COLORED | BORDERED , getBgName ( town ) )
2008-03-16 02:09:43 +02:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2011-12-14 00:23:17 +03:00
ui32 fortSize = town - > creatures . size ( ) ;
if ( fortSize > GameConstants : : CREATURES_PER_TOWN & & town - > creatures . back ( ) . second . empty ( ) )
2011-04-07 20:54:08 +03:00
fortSize - - ;
const CBuilding * fortBuilding = CGI - > buildh - > buildings [ town - > subID ] [ town - > fortLevel ( ) + 6 ] ;
2011-12-22 16:05:19 +03:00
title = new CLabel ( 400 , 12 , FONT_BIG , CENTER , Colors : : Cornsilk , fortBuilding - > Name ( ) ) ;
2011-04-07 20:54:08 +03:00
std : : string text = boost : : str ( boost : : format ( CGI - > generaltexth - > fcommands [ 6 ] ) % fortBuilding - > Name ( ) ) ;
2011-12-22 16:05:19 +03:00
exit = new CAdventureMapButton ( text , " " , boost : : bind ( & CFortScreen : : close , this ) , 748 , 556 , " TPMAGE1 " , SDLK_RETURN ) ;
2011-04-07 20:54:08 +03:00
2011-12-22 16:05:19 +03:00
std : : vector < Point > positions ;
positions + = Point ( 10 , 22 ) , Point ( 404 , 22 ) ,
Point ( 10 , 155 ) , Point ( 404 , 155 ) ,
Point ( 10 , 288 ) , Point ( 404 , 288 ) ;
2011-04-07 20:54:08 +03:00
2011-12-14 00:23:17 +03:00
if ( fortSize = = GameConstants : : CREATURES_PER_TOWN )
2011-12-22 16:05:19 +03:00
positions + = Point ( 206 , 421 ) ;
2011-04-07 20:54:08 +03:00
else
2011-12-22 16:05:19 +03:00
positions + = Point ( 10 , 421 ) , Point ( 404 , 421 ) ;
2011-04-07 20:54:08 +03:00
2011-12-14 00:23:17 +03:00
for ( ui32 i = 0 ; i < fortSize ; i + + )
2008-03-23 03:01:17 +02:00
{
2011-04-07 20:54:08 +03:00
int buildingID ;
2011-12-14 00:23:17 +03:00
if ( fortSize = = GameConstants : : CREATURES_PER_TOWN )
2011-04-07 20:54:08 +03:00
{
2011-12-14 00:23:17 +03:00
if ( vstd : : contains ( town - > builtBuildings , EBuilding : : DWELL_UP_FIRST + i ) )
buildingID = EBuilding : : DWELL_UP_FIRST + i ;
2011-04-07 20:54:08 +03:00
else
2011-12-14 00:23:17 +03:00
buildingID = EBuilding : : DWELL_FIRST + i ;
2011-04-07 20:54:08 +03:00
}
else
buildingID = 22 ;
recAreas . push_back ( new RecruitArea ( positions [ i ] . x , positions [ i ] . y , town , buildingID , i ) ) ;
2008-03-23 03:01:17 +02:00
}
2011-04-07 20:54:08 +03:00
resdatabar = new CMinorResDataBar ;
resdatabar - > pos . x + = pos . x ;
resdatabar - > pos . y + = pos . y ;
2011-12-22 16:05:19 +03:00
Rect barRect ( 4 , 554 , 740 , 18 ) ;
2011-04-07 20:54:08 +03:00
statusBar = new CGStatusBar ( new CPicture ( * background , barRect , 4 , 554 , false ) ) ;
2008-08-02 18:08:03 +03:00
}
2008-08-17 12:11:16 +03:00
2011-04-07 20:54:08 +03:00
void CFortScreen : : creaturesChanged ( )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
for ( size_t i = 0 ; i < recAreas . size ( ) ; i + + )
recAreas [ i ] - > creaturesChanged ( ) ;
2008-08-17 12:11:16 +03:00
}
2011-12-22 16:05:19 +03:00
LabeledValue : : LabeledValue ( Rect size , std : : string name , std : : string descr , int min , int max )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
pos . x + = size . x ;
pos . y + = size . y ;
pos . w = size . w ;
pos . h = size . h ;
init ( name , descr , min , max ) ;
2011-02-06 19:26:27 +02:00
}
2011-12-22 16:05:19 +03:00
LabeledValue : : LabeledValue ( Rect size , std : : string name , std : : string descr , int val )
2011-02-06 19:26:27 +02:00
{
2011-04-07 20:54:08 +03:00
pos . x + = size . x ;
pos . y + = size . y ;
pos . w = size . w ;
pos . h = size . h ;
init ( name , descr , val , val ) ;
2008-08-17 12:11:16 +03:00
}
2011-04-07 20:54:08 +03:00
void LabeledValue : : init ( std : : string nameText , std : : string descr , int min , int max )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( HOVER ) ;
2011-04-07 20:54:08 +03:00
hoverText = descr ;
std : : string valueText ;
if ( min & & max )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
valueText = boost : : lexical_cast < std : : string > ( min ) ;
if ( min ! = max )
valueText + = ' - ' + boost : : lexical_cast < std : : string > ( max ) ;
2008-08-17 12:11:16 +03:00
}
2011-12-22 16:05:19 +03:00
name = new CLabel ( 3 , 0 , FONT_SMALL , TOPLEFT , Colors : : Cornsilk , nameText ) ;
value = new CLabel ( pos . w - 3 , pos . h - 2 , FONT_SMALL , BOTTOMRIGHT , Colors : : Cornsilk , valueText ) ;
2008-08-17 12:11:16 +03:00
}
2011-04-07 20:54:08 +03:00
void LabeledValue : : hover ( bool on )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
if ( on )
GH . statusbar - > print ( hoverText ) ;
else
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
GH . statusbar - > clear ( ) ;
parent - > hovered = false ;
2008-08-17 12:11:16 +03:00
}
}
2011-04-07 20:54:08 +03:00
CFortScreen : : RecruitArea : : RecruitArea ( int posX , int posY , const CGTownInstance * Town , int buildingID , int Level ) :
town ( Town ) ,
level ( Level ) ,
availableCount ( NULL )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
pos . x + = posX ;
pos . y + = posY ;
pos . w = 386 ;
pos . h = 126 ;
if ( ! town - > creatures [ level ] . second . empty ( ) )
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | RCLICK | HOVER ) ; //Activate only if dwelling is present
2011-04-07 20:54:08 +03:00
icons = new CPicture ( " ZPCAINFO " , 261 , 3 ) ;
buildingPic = new CAnimImage ( graphics - > buildingPics [ town - > subID ] , buildingID , 0 , 4 , 21 ) ;
const CCreature * creature = NULL ;
if ( ! town - > creatures [ level ] . second . empty ( ) )
creature = CGI - > creh - > creatures [ town - > creatures [ level ] . second . back ( ) ] ;
else
creature = CGI - > creh - > creatures [ town - > town - > basicCreatures [ level ] ] ;
hoverText = boost : : str ( boost : : format ( CGI - > generaltexth - > tcommands [ 21 ] ) % creature - > namePl ) ;
creatureAnim = new CCreaturePic ( 159 , 4 , creature , false ) ;
2011-12-22 16:05:19 +03:00
Rect sizes ( 287 , 4 , 96 , 18 ) ;
2011-04-07 20:54:08 +03:00
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 190 ] , CGI - > generaltexth - > fcommands [ 0 ] , creature - > attack ) ) ;
sizes . y + = 20 ;
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 191 ] , CGI - > generaltexth - > fcommands [ 1 ] , creature - > defence ) ) ;
sizes . y + = 21 ;
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 199 ] , CGI - > generaltexth - > fcommands [ 2 ] , creature - > damageMin , creature - > damageMax ) ) ;
sizes . y + = 20 ;
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 388 ] , CGI - > generaltexth - > fcommands [ 3 ] , creature - > hitPoints ) ) ;
sizes . y + = 21 ;
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 193 ] , CGI - > generaltexth - > fcommands [ 4 ] , creature - > speed ) ) ;
sizes . y + = 20 ;
values . push_back ( new LabeledValue ( sizes , CGI - > generaltexth - > allTexts [ 194 ] , CGI - > generaltexth - > fcommands [ 5 ] , town - > creatureGrowth ( level ) ) ) ;
2011-12-22 16:05:19 +03:00
creatureName = new CLabel ( 78 , 11 , FONT_SMALL , CENTER , Colors : : Cornsilk , creature - > namePl ) ;
dwellingName = new CLabel ( 78 , 101 , FONT_SMALL , CENTER , Colors : : Cornsilk , CGI - > buildh - > buildings [ town - > subID ] [ buildingID ] - > Name ( ) ) ;
2011-04-07 20:54:08 +03:00
if ( vstd : : contains ( town - > builtBuildings , buildingID ) )
{
2011-12-14 00:23:17 +03:00
ui32 available = town - > creatures [ level ] . first ;
2011-04-07 20:54:08 +03:00
std : : string availableText = CGI - > generaltexth - > allTexts [ 217 ] + boost : : lexical_cast < std : : string > ( available ) ;
2011-12-22 16:05:19 +03:00
availableCount = new CLabel ( 78 , 119 , FONT_SMALL , CENTER , Colors : : Cornsilk , availableText ) ;
2011-04-07 20:54:08 +03:00
}
2008-08-17 12:11:16 +03:00
}
2009-04-14 15:47:09 +03:00
2011-04-07 20:54:08 +03:00
void CFortScreen : : RecruitArea : : hover ( bool on )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
if ( on )
GH . statusbar - > print ( hoverText ) ;
2010-07-26 01:47:59 +03:00
else
2011-04-07 20:54:08 +03:00
GH . statusbar - > clear ( ) ;
2008-08-17 12:11:16 +03:00
}
2011-04-07 20:54:08 +03:00
void CFortScreen : : RecruitArea : : creaturesChanged ( )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
if ( availableCount )
2008-08-17 12:11:16 +03:00
{
2011-04-07 20:54:08 +03:00
std : : string availableText = CGI - > generaltexth - > allTexts [ 217 ] +
boost : : lexical_cast < std : : string > ( town - > creatures [ level ] . first ) ;
availableCount - > setTxt ( availableText ) ;
2008-08-17 12:11:16 +03:00
}
}
2011-04-07 20:54:08 +03:00
void CFortScreen : : RecruitArea : : clickLeft ( tribool down , bool previousState )
2008-08-17 12:11:16 +03:00
{
2009-08-11 19:05:33 +03:00
if ( ! down & & previousState )
2011-03-22 15:19:07 +02:00
LOCPLINT - > castleInt - > builds - > enterDwelling ( level ) ;
2008-08-17 12:11:16 +03:00
}
2008-08-20 09:57:53 +03:00
2011-04-07 20:54:08 +03:00
void CFortScreen : : RecruitArea : : clickRight ( tribool down , bool previousState )
2009-01-22 19:30:15 +02:00
{
2009-08-11 19:05:33 +03:00
clickLeft ( down , false ) ; //r-click does same as l-click - opens recr. window
2009-01-22 19:30:15 +02:00
}
2011-04-07 20:54:08 +03:00
2012-06-02 18:16:54 +03:00
CMageGuildScreen : : CMageGuildScreen ( CCastleInterface * owner ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( BORDERED , " TPMAGE " )
2008-08-20 09:57:53 +03:00
{
2010-11-15 17:15:00 +02:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2011-04-07 20:54:08 +03:00
window = new CPicture ( graphics - > guildBgs [ owner - > town - > subID ] , 332 , 76 ) ;
2009-05-20 12:02:50 +03:00
resdatabar = new CMinorResDataBar ;
resdatabar - > pos . x + = pos . x ;
resdatabar - > pos . y + = pos . y ;
2011-12-22 16:05:19 +03:00
Rect barRect ( 7 , 556 , 737 , 18 ) ;
2011-04-07 20:54:08 +03:00
statusBar = new CGStatusBar ( new CPicture ( * background , barRect , 7 , 556 , false ) ) ;
2010-11-15 17:15:00 +02:00
2011-12-22 16:05:19 +03:00
exit = new CAdventureMapButton ( CGI - > generaltexth - > allTexts [ 593 ] , " " , boost : : bind ( & CMageGuildScreen : : close , this ) , 748 , 556 , " TPMAGE1.DEF " , SDLK_RETURN ) ;
2008-11-28 03:36:34 +02:00
exit - > assignedKeys . insert ( SDLK_ESCAPE ) ;
2010-11-15 17:15:00 +02:00
2011-12-22 16:05:19 +03:00
std : : vector < std : : vector < Point > > positions ;
2011-04-07 20:54:08 +03:00
2008-08-20 09:57:53 +03:00
positions . resize ( 5 ) ;
2011-12-22 16:05:19 +03:00
positions [ 0 ] + = Point ( 222 , 445 ) , Point ( 312 , 445 ) , Point ( 402 , 445 ) , Point ( 520 , 445 ) , Point ( 610 , 445 ) , Point ( 700 , 445 ) ;
positions [ 1 ] + = Point ( 48 , 53 ) , Point ( 48 , 147 ) , Point ( 48 , 241 ) , Point ( 48 , 335 ) , Point ( 48 , 429 ) ;
positions [ 2 ] + = Point ( 570 , 82 ) , Point ( 672 , 82 ) , Point ( 570 , 157 ) , Point ( 672 , 157 ) ;
positions [ 3 ] + = Point ( 183 , 42 ) , Point ( 183 , 148 ) , Point ( 183 , 253 ) ;
positions [ 4 ] + = Point ( 491 , 325 ) , Point ( 591 , 325 ) ;
2010-11-15 17:15:00 +02:00
2008-12-21 21:17:35 +02:00
for ( size_t i = 0 ; i < owner - > town - > town - > mageLevel ; i + + )
2008-08-20 09:57:53 +03:00
{
2011-04-07 20:54:08 +03:00
size_t spellCount = owner - > town - > spellsAtLevel ( i + 1 , false ) ; //spell at level with -1 hmmm?
for ( size_t j = 0 ; j < spellCount ; j + + )
2008-08-20 09:57:53 +03:00
{
2008-09-23 13:58:54 +03:00
if ( i < owner - > town - > mageGuildLevel ( ) & & owner - > town - > spells [ i ] . size ( ) > j )
2011-04-07 20:54:08 +03:00
spells . push_back ( new Scroll ( positions [ i ] [ j ] , CGI - > spellh - > spells [ owner - > town - > spells [ i ] [ j ] ] ) ) ;
2008-08-20 09:57:53 +03:00
else
2011-04-07 20:54:08 +03:00
new CAnimImage ( " TPMAGES.DEF " , 1 , 0 , positions [ i ] [ j ] . x , positions [ i ] [ j ] . y ) ; //closed scroll
2008-08-20 09:57:53 +03:00
}
}
}
2009-04-14 15:47:09 +03:00
2011-12-22 16:05:19 +03:00
CMageGuildScreen : : Scroll : : Scroll ( Point position , const CSpell * Spell )
2010-11-15 17:15:00 +02:00
: spell ( Spell )
2008-08-20 09:57:53 +03:00
{
2011-04-07 20:54:08 +03:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2012-06-02 18:16:54 +03:00
addUsedEvents ( LCLICK | RCLICK | HOVER ) ;
2011-04-07 20:54:08 +03:00
pos + = position ;
image = new CAnimImage ( " SPELLSCR " , spell - > id ) ;
pos = image - > pos ;
2008-08-20 09:57:53 +03:00
}
2009-04-14 15:47:09 +03:00
2009-08-11 19:05:33 +03:00
void CMageGuildScreen : : Scroll : : clickLeft ( tribool down , bool previousState )
2008-08-20 09:57:53 +03:00
{
2008-08-27 13:19:18 +03:00
if ( down )
{
2011-12-22 16:05:19 +03:00
std : : vector < CComponent * > comps ( 1 ,
new CComponent ( CComponent : : spell , spell - > id , 0 )
2008-08-27 13:19:18 +03:00
) ;
2009-04-22 21:48:56 +03:00
LOCPLINT - > showInfoDialog ( spell - > descriptions [ 0 ] , comps , soundBase : : sound_todo ) ;
2008-08-27 13:19:18 +03:00
}
2008-08-20 09:57:53 +03:00
}
2009-04-14 15:47:09 +03:00
2009-08-11 19:05:33 +03:00
void CMageGuildScreen : : Scroll : : clickRight ( tribool down , bool previousState )
2008-08-20 09:57:53 +03:00
{
if ( down )
{
CInfoPopup * vinya = new CInfoPopup ( ) ;
vinya - > free = true ;
vinya - > bitmap = CMessage : : drawBoxTextBitmapSub
( LOCPLINT - > playerID ,
2009-04-14 15:47:09 +03:00
spell - > descriptions [ 0 ] , graphics - > spellscr - > ourImages [ spell - > id ] . bitmap ,
2008-08-20 22:02:48 +03:00
spell - > name , 30 , 30 ) ;
2008-08-20 09:57:53 +03:00
vinya - > pos . x = screen - > w / 2 - vinya - > bitmap - > w / 2 ;
vinya - > pos . y = screen - > h / 2 - vinya - > bitmap - > h / 2 ;
2009-08-07 01:36:51 +03:00
GH . pushInt ( vinya ) ;
2008-08-20 09:57:53 +03:00
}
}
2009-04-14 15:47:09 +03:00
2008-08-20 09:57:53 +03:00
void CMageGuildScreen : : Scroll : : hover ( bool on )
{
2008-08-27 13:19:18 +03:00
if ( on )
2010-02-15 08:54:57 +02:00
GH . statusbar - > print ( spell - > name ) ;
2008-08-27 13:19:18 +03:00
else
2010-02-15 08:54:57 +02:00
GH . statusbar - > clear ( ) ;
2008-08-20 09:57:53 +03:00
}
2009-04-14 15:47:09 +03:00
2012-06-02 18:16:54 +03:00
CBlacksmithDialog : : CBlacksmithDialog ( bool possible , int creMachineID , int aid , int hid ) :
2012-06-15 20:08:19 +03:00
CWindowObject ( PLAYER_COLORED , " TPSMITH " )
2008-08-27 13:19:18 +03:00
{
2010-11-15 17:15:00 +02:00
OBJ_CONSTRUCTION_CAPTURING_ALL ;
2011-04-07 20:54:08 +03:00
2012-06-16 13:41:14 +03:00
statusBar = new CGStatusBar ( new CPicture ( * background , Rect ( 8 , pos . h - 26 , pos . w - 16 , 19 ) , 8 , pos . h - 26 ) ) ;
2010-11-15 17:15:00 +02:00
2011-02-06 19:26:27 +02:00
animBG = new CPicture ( " TPSMITBK " , 64 , 50 ) ;
animBG - > needRefresh = true ;
2009-05-07 20:20:41 +03:00
2011-04-07 20:54:08 +03:00
const CCreature * creature = CGI - > creh - > creatures [ creMachineID ] ;
2011-12-22 16:05:19 +03:00
anim = new CCreatureAnim ( 64 , 50 , creature - > animDefName , Rect ( ) ) ;
2011-02-06 19:26:27 +02:00
anim - > clipRect ( 113 , 125 , 200 , 150 ) ;
2011-04-07 20:54:08 +03:00
2011-12-22 16:05:19 +03:00
title = new CLabel ( 165 , 28 , FONT_BIG , CENTER , Colors : : Jasmine ,
2011-04-07 20:54:08 +03:00
boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 274 ] ) % creature - > nameSing ) ) ;
2011-12-22 16:05:19 +03:00
costText = new CLabel ( 165 , 218 , FONT_MEDIUM , CENTER , Colors : : Cornsilk , CGI - > generaltexth - > jktexts [ 43 ] ) ;
costValue = new CLabel ( 165 , 290 , FONT_MEDIUM , CENTER , Colors : : Cornsilk ,
2011-04-07 20:54:08 +03:00
boost : : lexical_cast < std : : string > ( CGI - > arth - > artifacts [ aid ] - > price ) ) ;
std : : string text = boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 595 ] ) % creature - > nameSing ) ;
2011-12-22 16:05:19 +03:00
buy = new CAdventureMapButton ( text , " " , boost : : bind ( & CBlacksmithDialog : : close , this ) , 42 , 312 , " IBUY30.DEF " , SDLK_RETURN ) ;
2011-04-07 20:54:08 +03:00
text = boost : : str ( boost : : format ( CGI - > generaltexth - > allTexts [ 596 ] ) % creature - > nameSing ) ;
2011-12-22 16:05:19 +03:00
cancel = new CAdventureMapButton ( text , " " , boost : : bind ( & CBlacksmithDialog : : close , this ) , 224 , 312 , " ICANCEL.DEF " , SDLK_ESCAPE ) ;
2009-05-07 20:20:41 +03:00
2008-08-27 13:19:18 +03:00
if ( possible )
2011-05-03 06:14:18 +03:00
buy - > callback + = boost : : bind ( & CCallback : : buyArtifact , LOCPLINT - > cb , LOCPLINT - > cb - > getHero ( hid ) , aid ) ;
2008-08-27 13:19:18 +03:00
else
2011-04-07 20:54:08 +03:00
buy - > block ( true ) ;
2008-08-27 13:19:18 +03:00
2012-05-13 18:04:21 +03:00
new CAnimImage ( " RESOURCE " , 6 , 0 , 148 , 244 ) ;
2008-08-27 13:19:18 +03:00
}