1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-01-26 03:52:01 +02:00

- implemented scholar skill

- fixed some remaining building issues (#361)
- Portal of Summoning will now be present in fort window
- some fixes for Thieves Guild window (partial #386)
This commit is contained in:
Ivan Savenko 2010-07-25 22:47:59 +00:00
parent e507f8300b
commit a00e5cc177
7 changed files with 147 additions and 120 deletions

View File

@ -580,7 +580,7 @@ void CCastleInterface::buildingClicked(int building)
if(building >= 30)
{
showRecruitmentWindow(building);
showRecruitmentWindow((building-30)%CREATURES_PER_TOWN);
}
else
{
@ -761,14 +761,10 @@ void CCastleInterface::buildingClicked(int building)
/*Dungeon*/ case 5: //Portal of Summoning
if (town->creatures[CREATURES_PER_TOWN].second.empty())
{//extra dwelling has no creatures in it. no external dwellinngs
//extra dwelling has no creatures in it
LOCPLINT->showInfoDialog(CGI->generaltexth->tcommands[30], std::vector<SComponent*>(), soundBase::sound_todo);
}
else
{
GH.pushInt(new CRecruitmentWindow(town, CREATURES_PER_TOWN, town,
boost::bind(&CCallback::recruitCreatures,LOCPLINT->cb,town,_1,_2,CREATURES_PER_TOWN), -87));
}
this->showRecruitmentWindow(CREATURES_PER_TOWN);
break;
/*Stronghold*/ case 6: //Ballista Yard
enterBlacksmith(4);
@ -1198,9 +1194,7 @@ void CCastleInterface::CCreaInfo::hover(bool on)
void CCastleInterface::CCreaInfo::clickLeft(tribool down, bool previousState)
{
if(previousState && (!down))
{
LOCPLINT->castleInt->showRecruitmentWindow(level+37);
}
LOCPLINT->castleInt->showRecruitmentWindow(level);
}
int CCastleInterface::CCreaInfo::AddToString(std::string from, std::string & to, int numb)
@ -1379,26 +1373,12 @@ void CCastleInterface::CTownInfo::show(SDL_Surface * to)
blitAt(pic->ourImages[bid-10].bitmap,pos.x,pos.y,to);
}
CRecruitmentWindow * CCastleInterface::showRecruitmentWindow( int building )
void CCastleInterface::showRecruitmentWindow( int level )
{
if(building>36) //upg dwelling
building-=7;
int level = building-30;
assert(level >= 0 && level < town->creatures.size());
//std::vector<std::pair<int,int > > crs;
//int amount = town->creatures[level].first;
//const std::vector<ui32> &cres = town->creatures[level].second;
//for(size_t i = 0; i < cres.size(); i++)
// crs.push_back(std::make_pair((int)cres[i],amount));
//CRecruitmentWindow *rw = new CRecruitmentWindow(crs,boost::bind(&CCallback::recruitCreatures,LOCPLINT->cb,town,_1,_2));
CRecruitmentWindow *rw = new CRecruitmentWindow(town, level, town, boost::bind(&CCallback::recruitCreatures,LOCPLINT->cb,town,_1,_2,level), -87);
GH.pushInt(rw);
return rw;
}
void CCastleInterface::enterMageGuild()
@ -1817,7 +1797,7 @@ void CFortScreen::show( SDL_Surface * to)
{
blitAt(bg,pos,to);
static unsigned char anim = 1;
for (int i=0; i<CREATURES_PER_TOWN; i++)
for (int i=0; i<crePics.size(); i++)
{
crePics[i]->blitPic(to,pos.x+positions[i].x+159,pos.y+positions[i].y+4,!(anim%4));
}
@ -1853,6 +1833,11 @@ void CFortScreen::close()
CFortScreen::CFortScreen( CCastleInterface * owner )
{
if (owner->town->creatures.size() > CREATURES_PER_TOWN
&& owner->town->creatures[CREATURES_PER_TOWN].second.size() )//dungeon with active portal
fortSize = CREATURES_PER_TOWN+1;
else
fortSize = CREATURES_PER_TOWN;
resdatabar = new CMinorResDataBar;
pos = owner->pos;
bg = NULL;
@ -1862,8 +1847,11 @@ CFortScreen::CFortScreen( CCastleInterface * owner )
exit = new AdventureMapButton(temp,"",boost::bind(&CFortScreen::close,this),pos.x+748,pos.y+556,"TPMAGE1.DEF",SDLK_RETURN);
positions += genRect(126,386,10,22),genRect(126,386,404,22),
genRect(126,386,10,155),genRect(126,386,404,155),
genRect(126,386,10,288),genRect(126,386,404,288),
genRect(126,386,206,421);
genRect(126,386,10,288),genRect(126,386,404,288);
if (fortSize == CREATURES_PER_TOWN)
positions += genRect(126,386,206,421);
else
positions += genRect(126,386,10,421),genRect(126,386,404,421);
draw(owner,true);
resdatabar->pos += pos;
}
@ -1874,22 +1862,40 @@ void CFortScreen::draw( CCastleInterface * owner, bool first)
SDL_FreeSurface(bg);
char buf[20];
memset(buf,0,20);
SDL_Surface *bg2 = BitmapHandler::loadBitmap("TPCASTL7.bmp"),
*icons = BitmapHandler::loadBitmap("ZPCAINFO.bmp");
SDL_Surface *bg2;
if (fortSize == CREATURES_PER_TOWN)
bg2 = BitmapHandler::loadBitmap("TPCASTL7.bmp");
else
bg2 = BitmapHandler::loadBitmap("TPCASTL8.bmp");
SDL_Surface *icons = BitmapHandler::loadBitmap("ZPCAINFO.bmp");
SDL_SetColorKey(icons,SDL_SRCCOLORKEY,SDL_MapRGB(icons->format,0,255,255));
graphics->blueToPlayersAdv(bg2,LOCPLINT->playerID);
bg = SDL_ConvertSurface(bg2,screen->format,0);
SDL_FreeSurface(bg2);
printAtMiddle(CGI->buildh->buildings[owner->town->subID][owner->town->fortLevel()+6]->Name(),400,13,FONT_MEDIUM,zwykly,bg);
for(int i=0;i<CREATURES_PER_TOWN; i++)
for(int i=0;i<fortSize; i++)
{
bool upgraded = owner->town->creatureDwelling(i,true);
bool present = owner->town->creatureDwelling(i,false);
CCreature *c = CGI->creh->creatures[upgraded ? owner->town->town->upgradedCreatures[i] : owner->town->town->basicCreatures[i]];
int dwelling;// ID of buiding with this creature
CCreature *c;
bool present = true;
if ( i < CREATURES_PER_TOWN )
{
bool upgraded = owner->town->creatureDwelling(i,true);
present = owner->town->creatureDwelling(i,false);
c = CGI->creh->creatures[upgraded ? owner->town->town->upgradedCreatures[i] : owner->town->town->basicCreatures[i]];
dwelling = 30+i+upgraded*7;
}
else
{
c = CGI->creh->creatures[owner->town->creatures[i].second[0]];
dwelling = 22;//Portal of summon
}
printAtMiddle(c->namePl,positions[i].x+79,positions[i].y+10,FONT_SMALL,zwykly,bg); //cr. name
blitAt(owner->bicons->ourImages[30+i+upgraded*7].bitmap,positions[i].x+4,positions[i].y+21,bg); //dwelling pic
printAtMiddle(CGI->buildh->buildings[owner->town->subID][30+i+upgraded*7]->Name(),positions[i].x+79,positions[i].y+100,FONT_SMALL,zwykly,bg); //dwelling name
if(present) //if creature is present print avail able quantity
blitAt(owner->bicons->ourImages[dwelling].bitmap,positions[i].x+4,positions[i].y+21,bg); //dwelling pic
printAtMiddle(CGI->buildh->buildings[owner->town->subID][dwelling]->Name(),positions[i].x+79,positions[i].y+100,FONT_SMALL,zwykly,bg); //dwelling name
if(present) //if creature is present print available quantity
{
SDL_itoa(owner->town->creatures[i].first,buf,10);
printAtMiddle(CGI->generaltexth->allTexts[217] + buf,positions[i].x+79,positions[i].y+118,FONT_SMALL,zwykly,bg);
@ -1939,7 +1945,7 @@ void CFortScreen::draw( CCastleInterface * owner, bool first)
crePics.push_back(new CCreaturePic(c,false));
if(present)
{
recAreas.push_back(new RecArea(30+i+upgraded*7));
recAreas.push_back(new RecArea(i));
recAreas.back()->pos = positions[i] + pos;
}
}
@ -1949,10 +1955,7 @@ void CFortScreen::draw( CCastleInterface * owner, bool first)
void CFortScreen::RecArea::clickLeft(tribool down, bool previousState)
{
if(!down && previousState)
{
LOCPLINT->castleInt->showRecruitmentWindow(bid);
}
//ClickableL::clickLeft(down);
LOCPLINT->castleInt->showRecruitmentWindow(level);
}
void CFortScreen::RecArea::clickRight(tribool down, bool previousState)

View File

@ -138,7 +138,7 @@ public:
void enterTavern();
void enterMageGuild();
void splitClicked(); //for hero meeting (splitting stacks is handled by garrison int)
CRecruitmentWindow * showRecruitmentWindow(int building);
void showRecruitmentWindow( int level );
void enterHall();
void close();
void splitF();
@ -209,13 +209,14 @@ class CFortScreen : public CIntObject
class RecArea : public CIntObject
{
public:
int bid;
RecArea(int BID):bid(BID){used = LCLICK | RCLICK;}; //c-tor
int level;
RecArea(int LEVEL):level(LEVEL){used = LCLICK | RCLICK;}; //c-tor
void clickLeft(tribool down, bool previousState);
void clickRight(tribool down, bool previousState);
};
public:
CMinorResDataBar * resdatabar;
int fortSize;
AdventureMapButton *exit;
SDL_Surface * bg;
std::vector<Rect> positions;

View File

@ -3781,6 +3781,7 @@ void CAltarWindow::calcTotalExp()
val += valOfArt * arts->artifactsOnAltar.count(*i);
}
}
val *=(100+hero->getSecSkillLevel(21)*5)/100.0f;
expOnAltar->setTxt(boost::lexical_cast<std::string>(val));
}
@ -6235,15 +6236,16 @@ CThievesGuildWindow::CThievesGuildWindow(const CGObjectInstance * _owner)
//loading backround and converting to more bpp form
SDL_Surface * bg = background = BitmapHandler::loadBitmap("TpRank.bmp", false);
graphics->blueToPlayersAdv(bg,LOCPLINT->playerID);
background = newSurface(bg->w, bg->h);
blitAt(bg, 0, 0, background);
SDL_FreeSurface(bg);
exitb = new AdventureMapButton (std::string(), std::string(), boost::bind(&CThievesGuildWindow::bexitf,this), 748, 556, "HSBTNS.def", SDLK_RETURN);
exitb = new AdventureMapButton (std::string(), std::string(), boost::bind(&CThievesGuildWindow::bexitf,this), 748, 556, "TPMAGE1.def", SDLK_RETURN);
statusBar = new CGStatusBar(3, 555, "TStatBar.bmp", 742);
resdatabar = new CMinorResDataBar();
resdatabar->pos.x += pos.x - 3;
resdatabar->pos.x += pos.x;
resdatabar->pos.y += pos.y;
static std::vector< std::list< ui8 > > SThievesGuildInfo::* fields[] = { &SThievesGuildInfo::numOfTowns, &SThievesGuildInfo::numOfHeroes, &SThievesGuildInfo::gold,
@ -6271,7 +6273,9 @@ CThievesGuildWindow::CThievesGuildWindow(const CGObjectInstance * _owner)
{
y = 52 + 32*g;
}
printAtMiddle(CGI->generaltexth->jktexts[24+g], 135, y, FONT_MEDIUM, tytulowy, background);
std::string text = CGI->generaltexth->jktexts[24+g];
boost::algorithm::trim_if(text,boost::algorithm::is_any_of("\""));
printAtMiddle(text, 135, y, FONT_MEDIUM, tytulowy, background);
}
CDefHandler * strips = CDefHandler::giveDef("PRSTRIPS.DEF");
@ -6284,7 +6288,7 @@ CThievesGuildWindow::CThievesGuildWindow(const CGObjectInstance * _owner)
{
blitAt(strips->ourImages[g-1].bitmap, 250 + 66*g, 7, background);
}
printAtMiddle(CGI->generaltexth->jktexts[16+g], 283 + 66*g, 20, FONT_MEDIUM, tytulowy, background);
printAtMiddle(CGI->generaltexth->jktexts[16+g], 283 + 66*g, 24, FONT_BIG, tytulowy, background);
SDL_Surface * box = BitmapHandler::loadBitmap(colorToBox[tgi.playerColors[g]]);
blitAt(box, 253 + 66*g, 334, background);
SDL_FreeSurface(box);
@ -6327,12 +6331,12 @@ CThievesGuildWindow::CThievesGuildWindow(const CGObjectInstance * _owner)
//printing stats
if(it->second.details)
{
printAtWB(CGI->generaltexth->allTexts[184], 191 + 66*counter, 396, FONT_TINY, 10, zwykly, background);
for (int i=0; i<it->second.details->primskills.size(); ++i)
{
printAt(CGI->generaltexth->allTexts[380+i], 191 + 66*counter, 394 + 11*i, FONT_SMALL, zwykly, background);
std::ostringstream skill;
skill << it->second.details->primskills[i];
printTo(skill.str(), 244 + 66 * counter, 410 + 11*i, FONT_SMALL, zwykly, background);
printTo(skill.str(), 244 + 66 * counter, 407 + 11*i, FONT_TINY, zwykly, background);
}
}

View File

@ -1,41 +1,56 @@
0 11
1 12
2 13
3 7
4 8
5 9
6 5
7 16
8 14
9 15
10 23
11 0
12 1
13 2
14 3
15 4
16 6
17 26
18 17
19 22
20 21
21 23
22 30
23 37
24 -1
25 31
26 38
27 -2
28 32
29 39
30 -3
31 33
32 40
33 -4
34 34
35 41
36 -5
37 35
38 42
39 36
40 43
-1 0 11
-1 1 12
-1 2 13
-1 3 7
-1 4 8
-1 5 9
-1 6 5
-1 7 16
-1 8 14
-1 9 15
-1 10 17
-1 11 0
-1 12 1
-1 13 2
-1 14 3
-1 15 4
-1 16 6
-1 17 26
-1 18 17
-1 19 22
-1 20 22
-1 21 23
-1 22 30
-1 23 37
-1 24 -1
-1 25 31
-1 26 38
-1 27 -2
-1 28 32
-1 29 39
-1 30 -3
-1 31 33
-1 32 40
-1 33 -4
-1 34 34
-1 35 41
-1 36 -5
-1 37 35
-1 38 42
-1 39 36
-1 40 43
0 20 21
1 19 21
2 18 22
2 19 23
2 20 21
3 20 23
3 18 21
4 19 21
5 20 23
5 18 21
6 19 21
7 20 17
7 18 22
7 19 21
8 18 21

View File

@ -1862,7 +1862,9 @@ int CGTownInstance::mageGuildLevel() const
}
bool CGTownInstance::creatureDwelling(const int & level, bool upgraded) const
{
return builtBuildings.find(30+level+upgraded*7)!=builtBuildings.end();
if ( level<0 || level >= CREATURES_PER_TOWN )
return false;
return vstd::contains(builtBuildings, 30+level+upgraded*CREATURES_PER_TOWN);
}
int CGTownInstance::getHordeLevel(const int & HID) const//HID - 0 or 1; returns creature level or -1 if that horde structure is not present
{
@ -2437,6 +2439,8 @@ void CGVisitableOPH::onNAHeroVisit(int heroID, bool alreadyVisited) const
}
case 100: //give exp
{
const CGHeroInstance *h = cb->getHero(heroID);
val = val*(100+h->getSecSkillLevel(21)*5)/100.0f;
InfoWindow iw;
iw.soundID = sound;
iw.components.push_back(Component(id,subid,val,0));
@ -2731,9 +2735,9 @@ void CTownBonus::onHeroVisit (const CGHeroInstance * h) const
break;
case 5://academy of battle scholars
what = 4;
val = 1000;
val = 1000*(100+h->getSecSkillLevel(21)*5)/100.0f;
mid = 583;
iw.components.push_back (Component(Component::EXPERIENCE, 0, 1000, 0));
iw.components.push_back (Component(Component::EXPERIENCE, 0, val, 0));
break;
}
break;
@ -3686,7 +3690,8 @@ void CGPickable::onHeroVisit( const CGHeroInstance * h ) const
sd.player = h->tempOwner;
sd.text << std::pair<ui8,ui32>(11,146);
sd.components.push_back(Component(2,6,val1,0));
sd.components.push_back(Component(5,0,val2,0));
int expVal = val2*(100+h->getSecSkillLevel(21)*5)/100.0f;
sd.components.push_back(Component(5,0,expVal, 0));
sd.soundID = soundBase::chest;
boost::function<void(ui32)> fun = boost::bind(&CGPickable::chosen,this,_1,h->id);
cb->showBlockingDialog(&sd,fun);
@ -3699,13 +3704,14 @@ void CGPickable::onHeroVisit( const CGHeroInstance * h ) const
void CGPickable::chosen( int which, int heroID ) const
{
const CGHeroInstance *h = cb->getHero(heroID);
switch(which)
{
case 1: //player pick gold
cb->giveResource(cb->getOwner(heroID),6,val1);
break;
case 2: //player pick exp
cb->changePrimSkill(heroID, 4, val2);
cb->changePrimSkill(heroID, 4, val2*(100+h->getSecSkillLevel(21)*5)/100.0f);
break;
default:
throw std::string("Unhandled treasure choice");
@ -4220,13 +4226,18 @@ void CGSeerHut::completeQuest (const CGHeroInstance * h) const //reward
switch (rewardType)
{
case 1: //experience
cb->changePrimSkill(h->id, 4, rVal, false);
iw.components.push_back (Component (Component::EXPERIENCE, 0, rVal, 0));
{
int expVal = rVal*(100+h->getSecSkillLevel(21)*5)/100.0f;
cb->changePrimSkill(h->id, 4, expVal, false);
iw.components.push_back (Component (Component::EXPERIENCE, 0, expVal, 0));
break;
}
case 2: //mana points
{
cb->setManaPoints(h->id, h->mana+rVal);
iw.components.push_back (Component (Component::PRIM_SKILL, 5, rVal, 0));
break;
}
case 3: case 4: //morale /luck
{
Bonus hb(Bonus::ONE_WEEK, (rewardType == 3 ? Bonus::MORALE : Bonus::LUCK),
@ -4682,10 +4693,11 @@ void CGPandoraBox::giveContents( const CGHeroInstance *h, bool afterBattle ) con
if(gainedExp || changesPrimSkill || abilities.size())
{
int expVal = gainedExp*(100+h->getSecSkillLevel(21)*5)/100.0f;
getText(iw,afterBattle,175,h);
if(gainedExp)
iw.components.push_back(Component(Component::EXPERIENCE,0,gainedExp,0));
if(expVal)
iw.components.push_back(Component(Component::EXPERIENCE,0,expVal,0));
for(int i=0; i<primskills.size(); i++)
if(primskills[i])
iw.components.push_back(Component(Component::PRIM_SKILL,i,primskills[i],0));
@ -4696,8 +4708,8 @@ void CGPandoraBox::giveContents( const CGHeroInstance *h, bool afterBattle ) con
cb->showInfoDialog(&iw);
//give exp
if(gainedExp)
cb->changePrimSkill(h->id,4,gainedExp,false);
if(expVal)
cb->changePrimSkill(h->id,4,expVal,false);
//give prim skills
for(int i=0; i<primskills.size(); i++)
if(primskills[i])

View File

@ -29,23 +29,11 @@ static std::set<si32> convertBuildings(const std::set<si32> h3m, int castleID)
std::ifstream b5(DATA_DIR "/config/buildings5.txt");
while(!b5.eof())
{
int a, b;
b5 >> a >> b;
if(castleID==8 && b==17) //magic university ID 17 (h3m) => 21 (vcmi)
b=21;
if(castleID==4 && a==20) //necropolis, skeleton transformer
b=22;
if(castleID==4 && a==19) //necropolis, necromancy aplifier
b=21;
if(castleID==3 && a==18) //inferno, brimstone clouds
b=21;
if(castleID==3 && a==20) //inferno, order of fire
b=23;
if(castleID==8 && a==10) //conflux, artifact merchant
b=17;
mapa[a]=b;
int h3, VCMI, town;
b5 >> town >> h3 >> VCMI;
if ( town == castleID || town == -1 )
mapa[h3]=VCMI;
}
for(std::set<si32>::const_iterator i=h3m.begin();i!=h3m.end();i++)
{
if(mapa[*i]>=0)

View File

@ -571,6 +571,10 @@ void CGameHandler::endBattle(int3 tile, const CGHeroInstance *hero1, const CGHer
//end battle, remove all info, free memory
giveExp(*battleResult.data);
if (hero1)
battleResult.data->exp[0] *= (100+hero1->getSecSkillLevel(21)*5)/100.0f;//sholar skill
if (hero2)
battleResult.data->exp[1] *= (100+hero2->getSecSkillLevel(21)*5)/100.0f;
sendAndApply(battleResult.data);
//if one hero has lost we will erase him
@ -4936,7 +4940,7 @@ bool CGameHandler::sacrificeCreatures(const IMarket *market, const CGHeroInstanc
int dump, exp;
market->getOffer(crid, 0, dump, exp, CREATURE_EXP);
exp *= count;
changePrimSkill (hero->id, 4, exp);
changePrimSkill (hero->id, 4, exp*(100+hero->getSecSkillLevel(21)*5)/100.0f);
return true;
}