1
0
mirror of https://github.com/vcmi/vcmi.git synced 2024-12-24 22:14:36 +02:00

Fixed all the issues with Quests, #828 and #1223.

Upgrade cost will never be negative.
This commit is contained in:
DjWarmonger 2013-07-23 15:03:01 +00:00
parent b1a569910b
commit 66d6aebe32
7 changed files with 37 additions and 18 deletions

View File

@ -993,7 +993,17 @@ std::string CComponent::getSubtitleInternal()
case resource: return boost::lexical_cast<std::string>(val);
case creature: return (val? boost::lexical_cast<std::string>(val) + " " : "") + CGI->creh->creatures[subtype]->*(val != 1 ? &CCreature::namePl : &CCreature::nameSing);
case artifact: return CGI->arth->artifacts[subtype]->Name();
case experience: return (subtype && val==1) ? CGI->generaltexth->allTexts[442] : boost::lexical_cast<std::string>(val);
case experience:
{
if (subtype == 1) //+1 level - tree of knowledge
{
std::string level = CGI->generaltexth->allTexts[442];
boost::replace_first(level, "1", boost::lexical_cast<std::string>(val));
return level;
}
else
return boost::lexical_cast<std::string>(val); //amount of experience OR level required for seer hut;
}
case spell: return CGI->spellh->spells[subtype]->name;
case morale: return "";
case luck: return "";

View File

@ -1728,6 +1728,9 @@ UpgradeInfo CGameState::getUpgradeInfo(const CStackInstance &stack)
if(ret.newID.size())
ret.oldID = base->idNumber;
for (Res::ResourceSet &cost : ret.cost)
cost.positive(); //upgrade cost can't be negative, ignore missing resources
return ret;
}

View File

@ -241,10 +241,10 @@ CGeneralTextHandler::CGeneralTextHandler()
//skip header
parser.endLine();
parser.endLine();
for (int i = 0; i < 6; ++i)
seerEmpty.push_back(parser.readString());
parser.endLine();
quests.resize(10);
for (int i = 0; i < 9; ++i) //9 types of quests

View File

@ -4390,17 +4390,17 @@ void CQuest::getVisitText (MetaString &iwText, std::vector<Component> &component
if (firstVisit)
{
isCustom = isCustomFirst;
iwText << firstVisitText;
iwText << (text = firstVisitText);
}
else if (failRequirements)
{
isCustom = isCustomNext;
iwText << nextVisitText;
iwText << (text = nextVisitText);
}
switch (missionType)
{
case MISSION_LEVEL:
components.push_back(Component (Component::EXPERIENCE, 1, m13489val, 0));
components.push_back(Component (Component::EXPERIENCE, 0, m13489val, 0));
if (!isCustom)
iwText.addReplacement(m13489val);
break;
@ -4435,7 +4435,9 @@ void CQuest::getVisitText (MetaString &iwText, std::vector<Component> &component
{
components.push_back(Component(stackToKill));
if (!isCustom)
{
addReplacements(iwText, text);
}
}
break;
case MISSION_ART:
@ -4687,7 +4689,10 @@ void CGSeerHut::initObj()
quest->completedText = VLC->generaltexth->quests[quest->missionType-1][2][quest->textOption];
}
else
{
quest->progress = CQuest::COMPLETE;
quest->firstVisitText = VLC->generaltexth->seerEmpty[quest->textOption];
}
}
@ -4788,17 +4793,13 @@ void CGSeerHut::setPropertyDer (ui8 what, ui32 val)
case 10:
quest->progress = static_cast<CQuest::Eprogress>(val);
break;
case 11:
quest->missionType = CQuest::MISSION_NONE;
break;
}
}
void CGSeerHut::newTurn() const
{
if (quest->lastDay >= 0 && quest->lastDay < cb->getDate()) //time is up
if (quest->lastDay >= 0 && quest->lastDay < cb->getDate()-1) //time is up
{
cb->setObjProperty (id, 11, 0);
cb->setObjProperty (id, 10, 0);
cb->setObjProperty (id, 10, CQuest::COMPLETE);
}
}
@ -4806,7 +4807,7 @@ void CGSeerHut::onHeroVisit( const CGHeroInstance * h ) const
{
InfoWindow iw;
iw.player = h->getOwner();
if (quest->missionType)
if (quest->progress < CQuest::COMPLETE)
{
bool firstVisit = !quest->progress;
bool failRequirements = !checkQuest(h);
@ -4908,9 +4909,8 @@ void CGSeerHut::finishQuest(const CGHeroInstance * h, ui32 accept) const
default:
break;
}
cb->setObjProperty (id, 10, CQuest::COMPLETE); //mission complete - for AI
cb->setObjProperty (id, 11, 0); //no more mission available - redundant?
completeQuest(h); //make sure to remove QuestQuard at the very end
cb->setObjProperty (id, 10, CQuest::COMPLETE); //mission complete
completeQuest(h); //make sure to remove QuestGuard at the very end
}
}
void CGSeerHut::completeQuest (const CGHeroInstance * h) const //reward

View File

@ -335,10 +335,10 @@ DLL_LINKAGE void RemoveObject::applyGs( CGameState *gs )
return;
}
auto quest = dynamic_cast<const CQuest *>(obj);
auto quest = dynamic_cast<const IQuestObject *>(obj);
if (quest)
{
gs->map->quests[quest->qid] = nullptr;
gs->map->quests[quest->quest->qid] = nullptr;
for (auto &player : gs->players)
{
for (auto &q : player.second.quests)
@ -349,7 +349,6 @@ DLL_LINKAGE void RemoveObject::applyGs( CGameState *gs )
}
}
}
//gs->map->quests[quest->qid].dellNull();
}
gs->map->objects[id.getNum()].dellNull();

View File

@ -40,6 +40,12 @@ void Res::ResourceSet::amax(const TResourceCap &val)
::vstd::amax(elem, val);
}
void Res::ResourceSet::positive()
{
for(auto & elem : *this)
::vstd::amax(elem, 0);
}
bool Res::ResourceSet::canBeAfforded(const ResourceSet &res) const
{
return Res::canAfford(res, *this);

View File

@ -125,6 +125,7 @@ namespace Res
}
DLL_LINKAGE void amax(const TResourceCap &val); //performs vstd::amax on each element
DLL_LINKAGE void positive(); //values below 0 are set to 0 - upgrade cost can't be negative, for example
DLL_LINKAGE bool nonZero() const; //returns true if at least one value is non-zero;
DLL_LINKAGE bool canAfford(const ResourceSet &price) const;
DLL_LINKAGE bool canBeAfforded(const ResourceSet &res) const;