diff --git a/client/CAdvmapInterface.cpp b/client/CAdvmapInterface.cpp index 0edbbfbe3..2847974a5 100644 --- a/client/CAdvmapInterface.cpp +++ b/client/CAdvmapInterface.cpp @@ -1188,7 +1188,7 @@ townList(ADVOPT.tlistSize,ADVOPT.tlistX,ADVOPT.tlistY,ADVOPT.tlistAU,ADVOPT.tlis //townList.init(); //townList.genList(); - heroWindow = new CHeroWindow(LOCPLINT->playerID); + heroWindow = NULL; for (int g=0; gblueToPlayersAdv(resdatabar.bg,player); - heroWindow->setPlayer(player); //heroList.updateHList(); //townList.genList(); diff --git a/client/CHeroWindow.cpp b/client/CHeroWindow.cpp index b91679dd4..e0b404630 100644 --- a/client/CHeroWindow.cpp +++ b/client/CHeroWindow.cpp @@ -25,6 +25,8 @@ #include #include #include +#include +#include #undef min @@ -45,202 +47,148 @@ void CHeroSwitcher::clickLeft(tribool down, bool previousState) { if(!down) { - owner->deactivate(); + getOwner()->deactivate(); const CGHeroInstance * buf = LOCPLINT->getWHero(id); - owner->setHero(buf); - owner->redrawCurBack(); - owner->activate(); + getOwner()->setHero(buf); + getOwner()->activate(); } } -CHeroSwitcher::CHeroSwitcher() +CHeroWindow * CHeroSwitcher::getOwner() { + return dynamic_cast(parent); +} + +CHeroSwitcher::CHeroSwitcher(int serial) +{ + pos = Rect(677, 95 + serial * 54, 48, 32) + pos; + id = serial; used = LCLICK; } -CHeroWindow::CHeroWindow(int playerColor): - player(playerColor) +CHeroWindow::CHeroWindow(const CGHeroInstance *hero) { - background = BitmapHandler::loadBitmap("HeroScr4"); - graphics->blueToPlayersAdv(background, playerColor); - pos.x = screen->w/2 - background->w/2 - 65; - pos.y = screen->h/2 - background->h/2 - 8; - pos.h = background->h; - pos.w = background->w; + OBJ_CONSTRUCTION_CAPTURING_ALL; + garr = NULL; curBack = NULL; curHero = NULL; - char bufor[400]; + player = hero->tempOwner; - artifs = new CArtifactsOfHero(pos.topLeft()); - artifs->commonInfo = new CArtifactsOfHero::SCommonPart; - artifs->commonInfo->participants.insert(artifs); + background = new CPicture("HeroScr4.BMP"); + background->colorizeAndConvert(player); + pos = background->center(); - garr = NULL; - ourBar = new CStatusBar(pos.x+72, pos.y+567, "ADROLLVR.bmp", 660); - quitButton = new AdventureMapButton(CGI->generaltexth->heroscrn[17], std::string(), boost::function(), pos.x+674, pos.y+524, "hsbtns.def", SDLK_RETURN); - dismissButton = new AdventureMapButton(std::string(), CGI->generaltexth->heroscrn[28], boost::bind(&CHeroWindow::dismissCurrent,this), pos.x+519, pos.y+437, "hsbtns2.def", SDLK_d); - questlogButton = new AdventureMapButton(CGI->generaltexth->heroscrn[0], std::string(), boost::bind(&CHeroWindow::questlog,this), pos.x+379, pos.y+437, "hsbtns4.def", SDLK_q); + //artifs = new CArtifactsOfHero(pos.topLeft(), true); + ourBar = new CGStatusBar(7, 559, "ADROLLVR.bmp", 660); // new CStatusBar(pos.x+72, pos.y+567, "ADROLLVR.bmp", 660); + + quitButton = new AdventureMapButton(CGI->generaltexth->heroscrn[17], std::string(),boost::bind(&CHeroWindow::quit,this), 609, 516, "hsbtns.def", SDLK_RETURN); + dismissButton = new AdventureMapButton(std::string(), CGI->generaltexth->heroscrn[28], boost::bind(&CHeroWindow::dismissCurrent,this), 454, 429, "hsbtns2.def", SDLK_d); + questlogButton = new AdventureMapButton(CGI->generaltexth->heroscrn[0], std::string(), boost::bind(&CHeroWindow::questlog,this), 314, 429, "hsbtns4.def", SDLK_q); formations = new CHighlightableButtonsGroup(0); - formations->addButton(map_list_of(0,CGI->generaltexth->heroscrn[23]),CGI->generaltexth->heroscrn[29], "hsbtns6.def", pos.x+546, pos.y+491, 0, 0, SDLK_t); - formations->addButton(map_list_of(0,CGI->generaltexth->heroscrn[24]),CGI->generaltexth->heroscrn[30], "hsbtns7.def", pos.x+546, pos.y+527, 1, 0, SDLK_l); + { + BLOCK_CAPTURING; + formations->addButton(map_list_of(0,CGI->generaltexth->heroscrn[23]),CGI->generaltexth->heroscrn[29], "hsbtns6.def", pos.x+481, pos.y+483, 0, 0, SDLK_t); + formations->addButton(map_list_of(0,CGI->generaltexth->heroscrn[24]),CGI->generaltexth->heroscrn[30], "hsbtns7.def", pos.x+481, pos.y+519, 1, 0, SDLK_l); + } - - gar2button = new CHighlightableButton(0, 0, map_list_of(0,CGI->generaltexth->heroscrn[26])(3,CGI->generaltexth->heroscrn[25]), CGI->generaltexth->heroscrn[31], false, "hsbtns8.def", NULL, pos.x+604, pos.y+491, SDLK_b); + tacticsButton = new CHighlightableButton(0, 0, map_list_of(0,CGI->generaltexth->heroscrn[26])(3,CGI->generaltexth->heroscrn[25]), CGI->generaltexth->heroscrn[31], false, "hsbtns8.def", NULL, 539, 483, SDLK_b); //right list of heroes for(int g=0; g<8; ++g) - { - //heroList.push_back(new AdventureMapButton(std::string(), std::string(), &CHeroWindow::switchHero, 677, 95+g*54, "hsbtns5.def", this)); - heroListMi.push_back(new CHeroSwitcher()); - heroListMi[g]->pos = genRect(32, 48, pos.x+677, pos.y + 95+g*54); - heroListMi[g]->owner = this; - heroListMi[g]->id = g; - } + heroListMi.push_back(new CHeroSwitcher(g)); + flags = CDefHandler::giveDefEss("CREST58.DEF"); + //areas - portraitArea = new LRClickableAreaWText(); - portraitArea->pos = genRect(64, 58, pos.x+83, pos.y + 26); + portraitArea = new LRClickableAreaWText(Rect(18, 18, 58, 64)); for(int v=0; vpos = genRect(64, 42, pos.x+95 + 70*v, pos.y + 117); - primSkillAreas[v]->text = CGI->generaltexth->arraytxt[2+v]; - primSkillAreas[v]->type = v; - primSkillAreas[v]->bonusValue = -1; // to be initilized when hero is being set - primSkillAreas[v]->baseType = 0; - sprintf(bufor, CGI->generaltexth->heroscrn[1].c_str(), CGI->generaltexth->primarySkillNames[v].c_str()); - primSkillAreas[v]->hoverText = std::string(bufor); - + LRClickableAreaWTextComp *area = new LRClickableAreaWTextComp(Rect(30 + 70*v, 109, 42, 64), SComponent::primskill); + area->text = CGI->generaltexth->arraytxt[2+v]; + area->type = v; + area->hoverText = boost::str(boost::format(CGI->generaltexth->heroscrn[1]) % CGI->generaltexth->primarySkillNames[v]); + primSkillAreas.push_back(area); } - specArea = new LRClickableAreaWText(); - specArea->pos = genRect(42, 136, pos.x+83, pos.y + 188); - specArea->hoverText = CGI->generaltexth->heroscrn[27]; - - expArea = new LRClickableAreaWText(); - expArea->pos = genRect(42, 136, pos.x+83, pos.y + 236); - expArea->hoverText = CGI->generaltexth->heroscrn[9]; - - morale = new MoraleLuckBox(true); - morale->pos = genRect(45,53,pos.x+240,pos.y+187); - - luck = new MoraleLuckBox(false); - luck->pos = genRect(45,53,pos.x+298,pos.y+187); - - spellPointsArea = new LRClickableAreaWText(); - spellPointsArea->pos = genRect(42, 136, pos.x+227, pos.y + 236); - spellPointsArea->hoverText = CGI->generaltexth->heroscrn[22]; + specArea = new LRClickableAreaWText(Rect(18, 180, 136, 42), CGI->generaltexth->heroscrn[27]); + expArea = new LRClickableAreaWText(Rect(18, 228, 136, 42), CGI->generaltexth->heroscrn[9]); + + morale = new MoraleLuckBox(true, Rect(175,179,53,45)); + luck = new MoraleLuckBox(false, Rect(233,179,53,45)); + spellPointsArea = new LRClickableAreaWText(Rect(162,228, 136, 42), CGI->generaltexth->heroscrn[22]); for(int i=0; ipos = genRect(42, 136, pos.x + ((i%2==0) ? (83) : (227)), pos.y + (284 + 48 * (i/2))); - secSkillAreas[i]->baseType = 1; + Rect r = Rect(i%2 == 0 ? 18 : 162, 276 + 48 * (i/2), 136, 42); + secSkillAreas.push_back(new LRClickableAreaWTextComp(r, SComponent::secskill)); } - pos.x += 65; - pos.y += 8; + + //////////////////////////////////////////////////////////////////////////??????????????? +// pos.x += 65; +// pos.y += 8; +// + //primary skills & exp and mana + new CPicture(graphics->pskillsm->ourImages[0].bitmap, 32, 111, false); + new CPicture(graphics->pskillsm->ourImages[1].bitmap, 102, 111, false); + new CPicture(graphics->pskillsm->ourImages[2].bitmap, 172, 111, false); + new CPicture(graphics->pskillsm->ourImages[5].bitmap, 242, 111, false); + new CPicture(graphics->pskillsm->ourImages[4].bitmap, 20, 230, false); + new CPicture(graphics->pskillsm->ourImages[3].bitmap, 162, 230, false); + + setHero(hero); } CHeroWindow::~CHeroWindow() { - SDL_FreeSurface(background); - delete quitButton; - delete dismissButton; - delete questlogButton; - delete formations; - delete gar2button; - //delete gar4button; + delete flags; + //SDL_FreeSurface(curBack); + //curBack = NULL; + curHero = NULL; - for(size_t g=0; gshow(to); - dismissButton->show(to); - questlogButton->show(to); - formations->show(to); - gar2button->show(to); - //gar4button->show(to); - - garr->show(to); - ourBar->show(to); - - artifs->showAll(to); + //artifs->dispose(); } void CHeroWindow::setHero(const CGHeroInstance *hero) -{ - char bufor[400]; - //CGHeroInstance *hero = const_cast(Hero); //but don't modify hero! - it's only for easy map reading +{ if(!hero) //something strange... no hero? it shouldn't happen + { + tlog1 << "Set NULL hero? no way...\n"; + return; + } + if(hero == curHero) { return; } + + assert(hero->tempOwner == LOCPLINT->playerID); //for now we won't show hero windows for non-our heroes curHero = hero; - artifs->updateState = true; - artifs->setHero(hero); - artifs->updateState = false; - - //pos temporarily switched, restored later - pos.x -= 65; - pos.y -= 8; - specArea->text = CGI->generaltexth->hTxts[hero->subID].longBonus; - gar2button->callback.clear(); - gar2button->callback2.clear(); - - sprintf(bufor, CGI->generaltexth->heroscrn[16].c_str(), curHero->name.c_str(), curHero->type->heroClass->name.c_str()); - dismissButton->hoverTexts[0] = std::string(bufor); - - sprintf(bufor, CGI->generaltexth->allTexts[15].c_str(), curHero->name.c_str(), curHero->type->heroClass->name.c_str()); - portraitArea->hoverText = std::string(bufor); + tacticsButton->callback.clear(); + tacticsButton->callback2.clear(); + dismissButton->hoverTexts[0] = boost::str(boost::format(CGI->generaltexth->heroscrn[16]) % curHero->name % curHero->type->heroClass->name); + portraitArea->hoverText = boost::str(boost::format(CGI->generaltexth->allTexts[15]) % curHero->name % curHero->type->heroClass->name); portraitArea->text = hero->getBiography(); - delete garr; - garr = new CGarrisonInt(pos.x+80, pos.y+493, 8, Point(), curBack, Point(16,486), curHero); + { + delete garr; + OBJ_CONSTRUCTION_CAPTURING_ALL; + garr = new CGarrisonInt(80, 493, 8, Point(), curBack->bg, Point(16,486), curHero); + } - AdventureMapButton * split = new AdventureMapButton(CGI->generaltexth->allTexts[256], CGI->generaltexth->heroscrn[32], boost::bind(&CGarrisonInt::splitClick,garr), pos.x+604, pos.y+527, "hsbtns9.def", false, NULL, false); //deleted by garrison destructor + AdventureMapButton * split = NULL; + { + BLOCK_CAPTURING; + split = new AdventureMapButton(CGI->generaltexth->allTexts[256], CGI->generaltexth->heroscrn[32], boost::bind(&CGarrisonInt::splitClick,garr), pos.x+604, pos.y+527, "hsbtns9.def", false, NULL, false); //deleted by garrison destructor + } boost::algorithm::replace_first(split->hoverTexts[0],"%s",CGI->generaltexth->allTexts[43]); garr->addSplitBtn(split); @@ -253,49 +201,45 @@ void CHeroWindow::setHero(const CGHeroInstance *hero) //secondary skills support for(size_t g=0; gsecSkills.size()); ++g) { - int skill = hero->secSkills[g].first, + int skill = hero->secSkills[g].first, level = hero->getSecSkillLevel(hero->secSkills[g].first); - secSkillAreas[g]->type = skill; secSkillAreas[g]->bonusValue = level; secSkillAreas[g]->text = CGI->generaltexth->skillInfoTexts[skill][level-1]; - - sprintf(bufor, CGI->generaltexth->heroscrn[21].c_str(), CGI->generaltexth->levels[level-1].c_str(), CGI->generaltexth->skillName[skill].c_str()); - secSkillAreas[g]->hoverText = std::string(bufor); + secSkillAreas[g]->hoverText = boost::str(boost::format(CGI->generaltexth->heroscrn[21]) % CGI->generaltexth->levels[level-1] % CGI->generaltexth->skillName[skill]); } + //printing experience - original format does not support ui64 - expArea->text = CGI->generaltexth->allTexts[2].c_str(); + expArea->text = CGI->generaltexth->allTexts[2]; boost::replace_first(expArea->text, "%d", boost::lexical_cast(hero->level)); boost::replace_first(expArea->text, "%d", boost::lexical_cast(CGI->heroh->reqExp(hero->level+1))); boost::replace_first(expArea->text, "%d", boost::lexical_cast(hero->exp)); //printing spell points - sprintf(bufor, CGI->generaltexth->allTexts[205].c_str(), hero->name.c_str(), hero->mana, hero->manaLimit()); - spellPointsArea->text = std::string(bufor); - + spellPointsArea->text = boost::str(boost::format(CGI->generaltexth->allTexts[205]) % hero->name % hero->mana % hero->manaLimit()); //if we have exchange window with this hero open bool noDismiss=false; - for(std::list::iterator it=GH.listInt.begin() ; it != GH.listInt.end(); it++) + BOOST_FOREACH(IShowActivable *isa, GH.listInt) { - CExchangeWindow * cew = dynamic_cast((*it)); - if(cew) - for(int g=0; gheroInst); ++g) - if(cew->heroInst[g] == hero) - noDismiss = true; - CKingdomInterface * cki = dynamic_cast((*it)); - if (cki) - noDismiss = true; + if(CExchangeWindow * cew = dynamic_cast(isa)) + for(int g=0; g < ARRAY_COUNT(cew->heroInst); ++g) + if(cew->heroInst[g] == hero) + noDismiss = true; + + if (CKingdomInterface * cki = dynamic_cast(isa)) + noDismiss = true; } dismissButton->block(!!hero->visitedTown || noDismiss); - if(hero->getSecSkillLevel(19)==0) - gar2button->block(true); + + if(hero->getSecSkillLevel(19) == 0) + tacticsButton->block(true); else { - gar2button->block(false); - gar2button->callback = vstd::assigno(hero->tacticFormationEnabled,true); - gar2button->callback2 = vstd::assigno(hero->tacticFormationEnabled,false); + tacticsButton->block(false); + tacticsButton->callback = vstd::assigno(hero->tacticFormationEnabled,true); + tacticsButton->callback2 = vstd::assigno(hero->tacticFormationEnabled,false); } //setting formations @@ -305,88 +249,12 @@ void CHeroWindow::setHero(const CGHeroInstance *hero) morale->set(hero); luck->set(hero); - - //restoring pos - pos.x += 65; - pos.y += 8; - - redrawCurBack(); } void CHeroWindow::quit() { - GH.popInt(this); - dispose(); -} - -void CHeroWindow::activate() -{ - quitButton->activate(); - dismissButton->activate(); - questlogButton->activate(); - gar2button->activate(); - formations->activate(); - //gar4button->activate(); - portraitArea->activate(); - specArea->activate(); - expArea->activate(); - spellPointsArea->activate(); - morale->activate(); - luck->activate(); - - garr->activate(); - GH.statusbar = ourBar; - - for(size_t v=0; vactivate(); - } - for(size_t v=0; vsecSkills.size()); ++v) - { - secSkillAreas[v]->activate(); - } - redrawCurBack(); - - artifs->activate(); - - for(size_t e=0; eactivate(); - } -} - -void CHeroWindow::deactivate() -{ - quitButton->deactivate(); - dismissButton->deactivate(); - questlogButton->deactivate(); - gar2button->deactivate(); - formations->deactivate(); - specArea->deactivate(); - //gar4button->deactivate(); - portraitArea->deactivate(); - expArea->deactivate(); - spellPointsArea->deactivate(); - morale->deactivate(); - luck->deactivate(); - - garr->deactivate(); - - for(size_t v=0; vdeactivate(); - } - for(size_t v=0; vsecSkills.size()); ++v) - { - secSkillAreas[v]->deactivate(); - } - - artifs->deactivate(); - - for(size_t e=0; edeactivate(); - } + adventureInt->heroWindow = NULL; + GH.popIntTotally(this); } void CHeroWindow::dismissCurrent() @@ -399,138 +267,110 @@ void CHeroWindow::dismissCurrent() void CHeroWindow::questlog() { } - -void CHeroWindow::redrawCurBack() +void CHeroWindow::showAll(SDL_Surface * to) { - if(curBack) - SDL_FreeSurface(curBack); - curBack = SDL_DisplayFormat(background); - - //primary skills & exp and mana - blitAt(graphics->pskillsm->ourImages[0].bitmap, 32, 111, curBack); - blitAt(graphics->pskillsm->ourImages[1].bitmap, 102, 111, curBack); - blitAt(graphics->pskillsm->ourImages[2].bitmap, 172, 111, curBack); - blitAt(graphics->pskillsm->ourImages[5].bitmap, 242, 111, curBack); - blitAt(graphics->pskillsm->ourImages[4].bitmap, 20, 230, curBack); - blitAt(graphics->pskillsm->ourImages[3].bitmap, 162, 230, curBack); - + CIntObject::showAll(to); //blitting portrait - blitAt(graphics->portraitLarge[curHero->portrait], 19, 19, curBack); - + blitAtLoc(graphics->portraitLarge[curHero->portrait], 19, 19, to); + //printing hero's name - CSDL_Ext::printAtMiddle(curHero->name, 190, 38, FONT_BIG, tytulowy, curBack); - + printAtMiddleLoc(curHero->name, 190, 38, FONT_BIG, tytulowy, to); + //printing hero's level std::string secondLine= CGI->generaltexth->allTexts[342]; boost::algorithm::replace_first(secondLine,"%d",boost::lexical_cast(curHero->level)); boost::algorithm::replace_first(secondLine,"%s",curHero->type->heroClass->name); - CSDL_Ext::printAtMiddle(secondLine, 190, 65, FONT_MEDIUM, zwykly, curBack); - + printAtMiddleLoc(secondLine, 190, 65, FONT_MEDIUM, zwykly, to); + //primary skills names - CSDL_Ext::printAtMiddle(CGI->generaltexth->jktexts[1], 52, 99, FONT_SMALL, tytulowy, curBack); - CSDL_Ext::printAtMiddle(CGI->generaltexth->jktexts[2], 123, 99, FONT_SMALL, tytulowy, curBack); - CSDL_Ext::printAtMiddle(CGI->generaltexth->jktexts[3], 193, 99, FONT_SMALL, tytulowy, curBack); - CSDL_Ext::printAtMiddle(CGI->generaltexth->jktexts[4], 262, 99, FONT_SMALL, tytulowy, curBack); - + printAtMiddleLoc(CGI->generaltexth->jktexts[1], 52, 99, FONT_SMALL, tytulowy, to); + printAtMiddleLoc(CGI->generaltexth->jktexts[2], 123, 99, FONT_SMALL, tytulowy, to); + printAtMiddleLoc(CGI->generaltexth->jktexts[3], 193, 99, FONT_SMALL, tytulowy, to); + printAtMiddleLoc(CGI->generaltexth->jktexts[4], 262, 99, FONT_SMALL, tytulowy, to); + //dismiss / quest log std::vector toPrin = CMessage::breakText(CGI->generaltexth->jktexts[8].substr(1, CGI->generaltexth->jktexts[8].size()-2)); if(toPrin.size()==1) { - CSDL_Ext::printAt(toPrin[0], 372, 439, FONT_SMALL, zwykly, curBack); + printAtLoc(toPrin[0], 372, 439, FONT_SMALL, zwykly, to); } else { - CSDL_Ext::printAt(toPrin[0], 372, 430, FONT_SMALL, zwykly, curBack); - CSDL_Ext::printAt(toPrin[1], 372, 446, FONT_SMALL, zwykly, curBack); + printAtLoc(toPrin[0], 372, 430, FONT_SMALL, zwykly, to); + printAtLoc(toPrin[1], 372, 446, FONT_SMALL, zwykly, to); } - + toPrin = CMessage::breakText(CGI->generaltexth->jktexts[9].substr(1, CGI->generaltexth->jktexts[9].size()-2)); if(toPrin.size()==1) { - CSDL_Ext::printAt(toPrin[0], 512, 439, FONT_SMALL, zwykly, curBack); + printAtLoc(toPrin[0], 512, 439, FONT_SMALL, zwykly, to); } else { - CSDL_Ext::printAt(toPrin[0], 512, 430, FONT_SMALL, zwykly, curBack); - CSDL_Ext::printAt(toPrin[1], 512, 446, FONT_SMALL, zwykly, curBack); + printAtLoc(toPrin[0], 512, 430, FONT_SMALL, zwykly, to); + printAtLoc(toPrin[1], 512, 446, FONT_SMALL, zwykly, to); } - + //printing primary skills' amounts for(int m=0; m<4; ++m) { - std::ostringstream primarySkill; - primarySkill<getPrimSkillLevel(m); - CSDL_Ext::printAtMiddle(primarySkill.str(), 53 + 70 * m, 166, FONT_SMALL, zwykly, curBack); + std::ostringstream primarySkill; + primarySkill<getPrimSkillLevel(m); + printAtMiddleLoc(primarySkill.str(), 53 + 70 * m, 166, FONT_SMALL, zwykly, to); } - + //morale and luck printing - blitAt(graphics->luck42->ourImages[curHero->LuckVal()+3].bitmap, 239, 182, curBack); - blitAt(graphics->morale42->ourImages[curHero->MoraleVal()+3].bitmap, 181, 182, curBack); - - blitAt(flags->ourImages[player].bitmap, 606, 8, curBack); - + blitAt(graphics->luck42->ourImages[curHero->LuckVal()+3].bitmap, 239, 182, to); + blitAt(graphics->morale42->ourImages[curHero->MoraleVal()+3].bitmap, 181, 182, to); + + blitAt(flags->ourImages[player].bitmap, 606, 8, to); + //hero list blitting - + for(int pos=0, g=0; gwanderingHeroes.size(); ++g) { - const CGHeroInstance * cur = LOCPLINT->wanderingHeroes[g]; - if (cur->inTownGarrison) - // Only display heroes that are not in garrison - continue; - - blitAt(graphics->portraitSmall[cur->portrait], 611, 87+pos*54, curBack); - //printing yellow border - if(cur->name == curHero->name) - { - for(int f=0; fportraitSmall[cur->portrait]->w; ++f) - { - for(int h=0; hportraitSmall[cur->portrait]->h; ++h) - if(f==0 || h==0 || f==graphics->portraitSmall[cur->portrait]->w-1 || h==graphics->portraitSmall[cur->portrait]->h-1) - { - CSDL_Ext::SDL_PutPixelWithoutRefresh(curBack, 611+f, 87+pos*54+h, 240, 220, 120); - } - } - } - - pos ++; + const CGHeroInstance * cur = LOCPLINT->wanderingHeroes[g]; + if (cur->inTownGarrison) + // Only display heroes that are not in garrison + continue; + + blitAt(graphics->portraitSmall[cur->portrait], 611, 87+pos*54, to); + //printing yellow border + if(cur->name == curHero->name) + { + for(int f=0; fportraitSmall[cur->portrait]->w; ++f) + { + for(int h=0; hportraitSmall[cur->portrait]->h; ++h) + if(f==0 || h==0 || f==graphics->portraitSmall[cur->portrait]->w-1 || h==graphics->portraitSmall[cur->portrait]->h-1) + { + CSDL_Ext::SDL_PutPixelWithoutRefresh(to, 611+f, 87+pos*54+h, 240, 220, 120); + } + } + } + + pos ++; } - + //secondary skills for(size_t v=0; vsecSkills.size()); ++v) { - blitAt(graphics->abils44->ourImages[curHero->secSkills[v].first*3+3+curHero->secSkills[v].second-1].bitmap, v%2 ? 161 : 18, 276 + 48 * (v/2), curBack); - CSDL_Ext::printAt(CGI->generaltexth->levels[curHero->secSkills[v].second-1], v%2 ? 212 : 68, 280 + 48 * (v/2), FONT_SMALL, zwykly, curBack); - CSDL_Ext::printAt(CGI->generaltexth->skillName[curHero->secSkills[v].first], v%2 ? 212 : 68, 300 + 48 * (v/2), FONT_SMALL, zwykly, curBack); + blitAt(graphics->abils44->ourImages[curHero->secSkills[v].first*3+3+curHero->secSkills[v].second-1].bitmap, v%2 ? 161 : 18, 276 + 48 * (v/2), to); + printAtLoc(CGI->generaltexth->levels[curHero->secSkills[v].second-1], v%2 ? 212 : 68, 280 + 48 * (v/2), FONT_SMALL, zwykly, to); + printAtLoc(CGI->generaltexth->skillName[curHero->secSkills[v].first], v%2 ? 212 : 68, 300 + 48 * (v/2), FONT_SMALL, zwykly, to); } - + //printing special ability - blitAt(graphics->un44->ourImages[curHero->subID].bitmap, 18, 180, curBack); - CSDL_Ext::printAt(CGI->generaltexth->jktexts[5].substr(1, CGI->generaltexth->jktexts[5].size()-2), 69, 183, FONT_SMALL, tytulowy, curBack); - CSDL_Ext::printAt(CGI->generaltexth->hTxts[curHero->subID].bonusName, 69, 205, FONT_SMALL, zwykly, curBack); - + blitAt(graphics->un44->ourImages[curHero->subID].bitmap, 18, 180, to); + printAtLoc(CGI->generaltexth->jktexts[5].substr(1, CGI->generaltexth->jktexts[5].size()-2), 69, 183, FONT_SMALL, tytulowy, to); + printAtLoc(CGI->generaltexth->hTxts[curHero->subID].bonusName, 69, 205, FONT_SMALL, zwykly, to); + //printing necessery texts - CSDL_Ext::printAt(CGI->generaltexth->jktexts[6].substr(1, CGI->generaltexth->jktexts[6].size()-2), 69, 232, FONT_SMALL, tytulowy, curBack); + printAtLoc(CGI->generaltexth->jktexts[6].substr(1, CGI->generaltexth->jktexts[6].size()-2), 69, 232, FONT_SMALL, tytulowy, to); std::ostringstream expstr; expstr<exp; - CSDL_Ext::printAt(expstr.str(), 68, 252, FONT_SMALL, zwykly, curBack); - CSDL_Ext::printAt(CGI->generaltexth->jktexts[7].substr(1, CGI->generaltexth->jktexts[7].size()-2), 213, 232, FONT_SMALL, tytulowy, curBack); + printAtLoc(expstr.str(), 68, 252, FONT_SMALL, zwykly, to); + printAtLoc(CGI->generaltexth->jktexts[7].substr(1, CGI->generaltexth->jktexts[7].size()-2), 213, 232, FONT_SMALL, tytulowy, to); std::ostringstream manastr; manastr << curHero->mana << '/' << curHero->manaLimit(); - CSDL_Ext::printAt(manastr.str(), 211, 252, FONT_SMALL, zwykly, curBack); -} - -void CHeroWindow::dispose() -{ - SDL_FreeSurface(curBack); - curBack = NULL; - curHero = NULL; - - artifs->dispose(); -} - -void CHeroWindow::setPlayer(int Player) -{ - player = Player; - - graphics->blueToPlayersAdv(background,player); -} + printAtLoc(manastr.str(), 211, 252, FONT_SMALL, zwykly, to); +} \ No newline at end of file diff --git a/client/CHeroWindow.h b/client/CHeroWindow.h index f31bc88b9..f1eae3bd9 100644 --- a/client/CHeroWindow.h +++ b/client/CHeroWindow.h @@ -29,16 +29,21 @@ class CHeroSwitcher : public CIntObject { public: int id; - CHeroWindow * owner; + + CHeroWindow * getOwner(); virtual void clickLeft(tribool down, bool previousState); - CHeroSwitcher(); + CHeroSwitcher(int serial); }; + + class CHeroWindow: public CWindowWithGarrison { - SDL_Surface * background, * curBack; - CStatusBar * ourBar; //heroWindow's statusBar + enum ELabel {}; + std::map labels; + CPicture *background, *curBack; + CGStatusBar * ourBar; //heroWindow's statusBar //general graphics CDefEssential *flags; @@ -61,23 +66,18 @@ public: const CGHeroInstance * curHero; AdventureMapButton * quitButton, * dismissButton, * questlogButton; //general - CHighlightableButton *gar2button; //garrison / formation handling; + CHighlightableButton *tacticsButton; //garrison / formation handling; CHighlightableButtonsGroup *formations; int player; - CHeroWindow(int playerColor); //c-tor + CHeroWindow(const CGHeroInstance *hero); //c-tor ~CHeroWindow(); //d-tor void setHero(const CGHeroInstance * hero); //sets main displayed hero - void activate(); //activates hero window; - void deactivate(); //activates hero window; - virtual void show(SDL_Surface * to); //shows hero window - void showAll(SDL_Surface * to){show(to);}; - void redrawCurBack(); //redraws curBAck from scratch - void dispose(); //free resources not needed after closing windows and reset state - void quit(); //stops displaying hero window and disposes + void showAll(SDL_Surface * to); //shows and activates adv. map interface +// void redrawCurBack(); //redraws curBAck from scratch + void quit(); //stops displaying hero window and disposes void dismissCurrent(); //dissmissed currently displayed hero (curHero) void questlog(); //show quest log in hero window - void switchHero(); //changes displayed hero - void setPlayer(int Player); + void switchHero(); //changes displayed hero //friends friend void CArtPlace::clickLeft(tribool down, bool previousState); diff --git a/client/CKingdomInterface.cpp b/client/CKingdomInterface.cpp index cf73e64ad..28a4e9c79 100644 --- a/client/CKingdomInterface.cpp +++ b/client/CKingdomInterface.cpp @@ -708,11 +708,9 @@ CKingdomInterface::CHeroItem::CHeroItem(int num, CKingdomInterface * Owner) char bufor[400]; for(int i=0; ipos = genRect(45, 32, pos.x+77 + 36*i, pos.y+26); + primarySkills.push_back(new LRClickableAreaWTextComp(genRect(45, 32, pos.x+77 + 36*i, pos.y+26), SComponent::primskill)); primarySkills[i]->text = CGI->generaltexth->arraytxt[2+i]; primarySkills[i]->type = i; - primarySkills[i]->baseType = 0; sprintf(bufor, CGI->generaltexth->heroscrn[1].c_str(), CGI->generaltexth->primarySkillNames[i].c_str()); primarySkills[i]->hoverText = std::string(bufor); }; @@ -720,11 +718,8 @@ CKingdomInterface::CHeroItem::CHeroItem(int num, CKingdomInterface * Owner) experience->pos = genRect(33, 49, pos.x+322, pos.y+5); experience->hoverText = CGI->generaltexth->heroscrn[9]; - morale = new MoraleLuckBox(true); - morale->pos = genRect(20,32,pos.x+221,pos.y+52); - - luck = new MoraleLuckBox(false); - luck->pos = genRect(20,32,pos.x+221,pos.y+28); + morale = new MoraleLuckBox(true, genRect(20,32,pos.x+221,pos.y+52)); + luck = new MoraleLuckBox(false, genRect(20,32,pos.x+221,pos.y+28)); spellPoints = new LRClickableAreaWText(); spellPoints->pos = genRect(33, 49, pos.x+270, pos.y+5); @@ -736,25 +731,18 @@ CKingdomInterface::CHeroItem::CHeroItem(int num, CKingdomInterface * Owner) for(int i=0; ipos = genRect(32, 32, pos.x+410+i*37, pos.y+5); - secondarySkills[i]->baseType = 1; - }; + secondarySkills.push_back(new LRClickableAreaWTextComp(genRect(32, 32, pos.x+410+i*37, pos.y+5), SComponent::secskill)); + } for (int i=0; i<18;i++) { - artifacts.push_back(new CArtPlace(this)); - artifacts[i]->pos = genRect(44, 44, pos.x+268+(i%9)*48, pos.y+66); - artifacts[i]->baseType = SComponent::artifact; - }; + artifacts.push_back(new CArtPlace(this, genRect(44, 44, pos.x+268+(i%9)*48, pos.y+66))); + } for (int i=0; i<8;i++) { - backpack.push_back(new CArtPlace(this)); - backpack[i]->pos = genRect(44, 44, pos.x+293+(i%9)*48, pos.y+66); - backpack[i]->baseType = SComponent::artifact; - }; - + backpack.push_back(new CArtPlace(this, genRect(44, 44, pos.x+293+(i%9)*48, pos.y+66))); + } } CKingdomInterface::CHeroItem::~CHeroItem() @@ -1005,7 +993,8 @@ void CKingdomInterface::CHeroItem::deactivate() secondarySkills[i]->deactivate(); } -CKingdomInterface::CHeroItem::CArtPlace::CArtPlace(CHeroItem * owner) +CKingdomInterface::CHeroItem::CArtPlace::CArtPlace(CHeroItem * owner, const Rect &r) + : LRClickableAreaWTextComp(r, SComponent::artifact) { parent = owner; used = LCLICK | RCLICK | HOVER; @@ -1043,6 +1032,7 @@ void CKingdomInterface::CHeroItem::CArtPlace::deactivate() CKingdomInterface::CTownItem::CCreaPlace::CCreaPlace() + : LRClickableAreaWTextComp(Rect(0,0,0,0), -1) { town = NULL; used = LCLICK | RCLICK | HOVER; diff --git a/client/CKingdomInterface.h b/client/CKingdomInterface.h index 675ff4610..a4ffe5a68 100644 --- a/client/CKingdomInterface.h +++ b/client/CKingdomInterface.h @@ -61,7 +61,7 @@ class CKingdomInterface : public CGarrisonHolder { public: CHeroItem * parent; - CArtPlace(CHeroItem * owner); //c-tor + CArtPlace(CHeroItem * owner, const Rect &r = Rect(0, 0, 44, 44)); //c-tor void clickLeft(tribool down, bool previousState); void clickRight(tribool down, bool previousState); void activate(); diff --git a/client/CPlayerInterface.cpp b/client/CPlayerInterface.cpp index 9dfee3a45..65e715dc2 100644 --- a/client/CPlayerInterface.cpp +++ b/client/CPlayerInterface.cpp @@ -941,8 +941,8 @@ void CPlayerInterface::tileHidden(const std::set &pos) void CPlayerInterface::openHeroWindow(const CGHeroInstance *hero) { boost::unique_lock un(*pim); + adventureInt->heroWindow = new CHeroWindow(hero); adventureInt->heroWindow->setHero(hero); - adventureInt->heroWindow->quitButton->callback = boost::bind(&CHeroWindow::quit,adventureInt->heroWindow); GH.pushInt(adventureInt->heroWindow); } diff --git a/client/GUIClasses.cpp b/client/GUIClasses.cpp index dbdead36c..eec4a5a28 100644 --- a/client/GUIClasses.cpp +++ b/client/GUIClasses.cpp @@ -2199,12 +2199,10 @@ void CCreInfoWindow::init(const CCreature *cre, const CBonusSystemNode *stackNod printLine(6, CGI->generaltexth->zelp[441].first, cre->valOfBonuses(Bonus::STACKS_SPEED), stackNode->valOfBonuses(Bonus::STACKS_SPEED)); //setting morale - morale = new MoraleLuckBox(true); - morale->pos = genRect(42, 42, pos.x + 24, pos.y + 189); + morale = new MoraleLuckBox(true, genRect(42, 42, pos.x + 24, pos.y + 189)); morale->set(stackNode); //setting luck - luck = new MoraleLuckBox(false); - luck->pos = genRect(42, 42, pos.x + 77, pos.y + 189); + luck = new MoraleLuckBox(false, genRect(42, 42, pos.x + 77, pos.y + 189)); luck->set(stackNode); //luck and morale @@ -4482,10 +4480,10 @@ CRClickPopupInt::CRClickPopupInt( IShowActivable *our, bool deleteInt ) CRClickPopupInt::~CRClickPopupInt() { - //workaround for hero window issue - if it's our interface, call dispose to properly reset it's state - //TODO? it might be better to rewrite hero window so it will bee newed/deleted on opening / closing (not effort-worthy now, but on some day...?) - if(LOCPLINT && inner == adventureInt->heroWindow) - adventureInt->heroWindow->dispose(); +// //workaround for hero window issue - if it's our interface, call dispose to properly reset it's state +// //TODO? it might be better to rewrite hero window so it will bee newed/deleted on opening / closing (not effort-worthy now, but on some day...?) +// if(LOCPLINT && inner == adventureInt->heroWindow) +// adventureInt->heroWindow->dispose(); if(delInner) delete inner; @@ -4792,13 +4790,26 @@ void LRClickableAreaWText::clickRight(tribool down, bool previousState) LRClickableAreaWText::LRClickableAreaWText() { - used = LCLICK | RCLICK | HOVER; + init(); +} + +LRClickableAreaWText::LRClickableAreaWText(const Rect &Pos, const std::string &HoverText /*= ""*/, const std::string &ClickText /*= ""*/) +{ + init(); + pos = Pos + pos; + hoverText = HoverText; + text = ClickText; } LRClickableAreaWText::~LRClickableAreaWText() { } +void LRClickableAreaWText::init() +{ + used = LCLICK | RCLICK | HOVER; +} + void LRClickableAreaWTextComp::clickLeft(tribool down, bool previousState) { if((!down) && previousState) @@ -4808,6 +4819,11 @@ void LRClickableAreaWTextComp::clickLeft(tribool down, bool previousState) } } +LRClickableAreaWTextComp::LRClickableAreaWTextComp(const Rect &Pos, int BaseType) + : LRClickableAreaWText(Pos), baseType(BaseType), bonusValue(-1) +{ +} + CHeroArea::CHeroArea(int x, int y, const CGHeroInstance * _hero):hero(_hero) { used = LCLICK | RCLICK | HOVER; @@ -4860,6 +4876,11 @@ void LRClickableAreaOpenTown::clickRight(tribool down, bool previousState) LOCPLINT->openTownWindow(town);//TODO: popup? } +LRClickableAreaOpenTown::LRClickableAreaOpenTown() + : LRClickableAreaWTextComp(Rect(0,0,0,0), -1) +{ +} + void CArtifactsOfHero::SCommonPart::reset() { destAOH = srcAOH = NULL; @@ -4942,7 +4963,7 @@ void CArtifactsOfHero::setHero(const CGHeroInstance * hero) void CArtifactsOfHero::dispose() { - delNull(curHero); + //delNull(curHero); unmarkSlots(false); CGI->curh->dragAndDropCursor(NULL); } @@ -5078,9 +5099,15 @@ void CArtifactsOfHero::eraseSlotData (CArtPlace* artPlace, int slotID) artPlace->hoverText = CGI->generaltexth->allTexts[507]; } -CArtifactsOfHero::CArtifactsOfHero(const Point &position) : - curHero(NULL), backpackPos(0), commonInfo(NULL), updateState(false), allowedAssembling(true) +CArtifactsOfHero::CArtifactsOfHero(const Point& position, bool createCommonPart /*= false*/) + : curHero(NULL), backpackPos(0), commonInfo(NULL), updateState(false), allowedAssembling(true) { + if(createCommonPart) + { + commonInfo = new CArtifactsOfHero::SCommonPart; + commonInfo->participants.insert(this); + } + OBJ_CONSTRUCTION_CAPTURING_ALL; pos += position; artWorn.resize(19); @@ -5442,12 +5469,10 @@ CExchangeWindow::CExchangeWindow(si32 hero1, si32 hero2) : bg(NULL) spellPoints[b]->text = std::string(bufor); //setting morale - morale[b] = new MoraleLuckBox(true); - morale[b]->pos = genRect(32, 32, pos.x + 177 + 490*b, pos.y + 45); + morale[b] = new MoraleLuckBox(true, genRect(32, 32, pos.x + 177 + 490*b, pos.y + 45)); morale[b]->set(heroInst[b]); //setting luck - luck[b] = new MoraleLuckBox(false); - luck[b]->pos = genRect(32, 32, pos.x + 213 + 490*b, pos.y + 45); + luck[b] = new MoraleLuckBox(false, genRect(32, 32, pos.x + 213 + 490*b, pos.y + 45)); luck[b]->set(heroInst[b]); } @@ -6416,10 +6441,11 @@ void MoraleLuckBox::showAll(SDL_Surface * to) blitAt(def->ourImages[bonusValue].bitmap, pos, to); } -MoraleLuckBox::MoraleLuckBox(bool Morale) +MoraleLuckBox::MoraleLuckBox(bool Morale, const Rect &r) :morale(Morale) { bonusValue = 0; + pos = r + pos; } MoraleLuckBox::~MoraleLuckBox() diff --git a/client/GUIClasses.h b/client/GUIClasses.h index 94976a5f4..df96ea538 100644 --- a/client/GUIClasses.h +++ b/client/GUIClasses.h @@ -815,7 +815,9 @@ public: std::string text; LRClickableAreaWText(); + LRClickableAreaWText(const Rect &Pos, const std::string &HoverText = "", const std::string &ClickText = ""); virtual ~LRClickableAreaWText(); + void init(); virtual void clickLeft(tribool down, bool previousState); virtual void clickRight(tribool down, bool previousState); @@ -827,6 +829,8 @@ public: int baseType; int bonusValue, type; virtual void clickLeft(tribool down, bool previousState); + + LRClickableAreaWTextComp(const Rect &Pos = Rect(0,0,0,0), int BaseType = -1); }; class MoraleLuckBox : public LRClickableAreaWTextComp @@ -837,7 +841,7 @@ public: void set(const CBonusSystemNode *node); void showAll(SDL_Surface * to); - MoraleLuckBox(bool Morale); + MoraleLuckBox(bool Morale, const Rect &r); ~MoraleLuckBox(); }; @@ -861,6 +865,7 @@ public: const CGTownInstance * town; void clickLeft(tribool down, bool previousState); void clickRight(tribool down, bool previousState); + LRClickableAreaOpenTown(); }; class CCreInfoWindow : public CIntObject @@ -967,7 +972,7 @@ public: void setSlotData (CArtPlace* artPlace, int slotID); void eraseSlotData (CArtPlace* artPlace, int slotID); - CArtifactsOfHero(const Point& position); //c-tor + CArtifactsOfHero(const Point& position, bool createCommonPart = false); //c-tor ~CArtifactsOfHero(); //d-tor void updateParentWindow(); friend class CArtPlace; diff --git a/lib/ConstTransitivePtr.h b/lib/ConstTransitivePtr.h index 28231d67d..e05909b23 100644 --- a/lib/ConstTransitivePtr.h +++ b/lib/ConstTransitivePtr.h @@ -5,10 +5,7 @@ class ConstTransitivePtr { T *ptr; public: - ConstTransitivePtr() - : ptr(NULL) - {} - ConstTransitivePtr(T *Ptr) + ConstTransitivePtr(T *Ptr = NULL) : ptr(Ptr) {} diff --git a/lib/NetPacks.h b/lib/NetPacks.h index 2c1260125..c822e0b06 100644 --- a/lib/NetPacks.h +++ b/lib/NetPacks.h @@ -601,6 +601,7 @@ struct SetHeroesInTown : public CPackForClient //508 h & tid & visiting & garrison; } }; + struct SetHeroArtifacts : public CPackForClient //509 { SetHeroArtifacts(){type = 509;}; @@ -701,7 +702,7 @@ struct SetAvailableArtifacts : public CPackForClient //519 } }; -struct NewArtifact : public CPackForClient +struct NewArtifact : public CPackForClient //520 { NewArtifact(){type = 520;}; //void applyCl(CClient *cl); @@ -826,6 +827,71 @@ struct RebalanceStacks : CGarrisonOperationPack //526 } }; +typedef CArtifact TTempArtInstance; +typedef si32 TArtPos; + +struct ArtifactLocation +{ + ConstTransitivePtr hero; + TArtPos slot; + + ArtifactLocation() + { + hero = NULL; + slot = -1; + } + ArtifactLocation(const CGHeroInstance *Hero, TArtPos Slot) + { + hero = const_cast(Hero); //we are allowed here to const cast -> change will go through one of our packages... do not abuse! + slot = Slot; + } + DLL_EXPORT const TTempArtInstance *getArt(); + template void serialize(Handler &h, const int version) + { + h & hero & slot; + } +}; + +struct PutArtifact : CGarrisonOperationPack //526 +{ + ArtifactLocation al; + TTempArtInstance *art; + + void applyCl(CClient *cl); + DLL_EXPORT void applyGs(CGameState *gs); + + template void serialize(Handler &h, const int version) + { + h & src & dst & count; + } +}; + +struct EraseArtifact : CGarrisonOperationPack //527 +{ + ArtifactLocation al; + + void applyCl(CClient *cl); + DLL_EXPORT void applyGs(CGameState *gs); + + template void serialize(Handler &h, const int version) + { + h & al; + } +}; + +struct MoveArtifact : CGarrisonOperationPack //528 +{ + ArtifactLocation src, dst; + + void applyCl(CClient *cl); + DLL_EXPORT void applyGs(CGameState *gs); + + template void serialize(Handler &h, const int version) + { + h & src & dst; + } +}; + struct NewTurn : public CPackForClient //101 { enum weekType {NORMAL, DOUBLE_GROWTH, BONUS_GROWTH, DEITYOFFIRE, PLAGUE, CUSTOM, NO_ACTION, NONE};