Merge branch 'MikeHoffert-feature-attack-boost' into develop

This commit is contained in:
titiger 2014-08-10 00:20:19 +02:00
commit c43320ba2e
6 changed files with 139 additions and 2 deletions

View File

@ -2630,7 +2630,15 @@ bool Unit::update() {
int64 heightFactor = getHeightFactor(ANIMATION_SPEED_MULTIPLIER);
int64 speedDenominator = speedDivider *
game->getWorld()->getUpdateFps(this->getFactionIndex());
int64 progressIncrease = (currSkill->getAnimSpeed() * heightFactor) / speedDenominator;
// Override the animation speed for attacks that have upgraded the attack speed
int animSpeed = currSkill->getAnimSpeed();
if(currSkill->getClass() == scAttack) {
int animSpeedBoost = ((AttackSkillType *) currSkill)->getAnimSpeedBoost(&totalUpgrade);
animSpeed += animSpeedBoost;
}
int64 progressIncrease = (animSpeed * heightFactor) / speedDenominator;
// Ensure we increment at least a value of 1 of the action will be stuck infinitely
if(currSkill->getAnimSpeed() > 0 && heightFactor > 0 && progressIncrease == 0) {
progressIncrease = 1;

View File

@ -288,7 +288,13 @@ string AttackCommandType::getDesc(const TotalUpgrade *totalUpgrade, bool transla
}
str+="\n";
//attack speed
str+= lang.getString("AttackSpeed",(translatedValue == true ? "" : "english"))+": "+ intToStr(attackSkillType->getSpeed()) +"\n";
if(totalUpgrade->getAttackSpeed(attackSkillType) != 0) {
str+= "+"+intToStr(totalUpgrade->getAttackSpeed(attackSkillType));
}
str+="\n";
str+=attackSkillType->getBoostDesc(translatedValue);
return str;
}

View File

@ -1013,6 +1013,24 @@ void AttackSkillType::load(const XmlNode *sn, const XmlNode *attackBoostsNode,
}
}
int AttackSkillType::getTotalSpeed(const TotalUpgrade *totalUpgrade) const{
int result = speed + totalUpgrade->getAttackSpeed(this);
result = max(0,result);
return result;
}
// Get the amount to boost the attack animation speed by (based on attack-speed upgrades)
int AttackSkillType::getAnimSpeedBoost(const TotalUpgrade *totalUpgrade) const{
// Same calculation as in TotalUpgrade::sum, but bypassing the use of the value
// list (which is for the attack speed, not animation speed)
if(totalUpgrade->getAttackRangeIsMultiplier()) {
return animSpeed * (totalUpgrade->getAttackSpeed(NULL) / (double)100);
}
else {
return totalUpgrade->getAttackSpeed(NULL);
}
}
string AttackSkillType::toString(bool translatedValue) const{
if(translatedValue == false) {
return "Attack";

View File

@ -334,6 +334,8 @@ public:
//misc
int getTotalAttackStrength(const TotalUpgrade *totalUpgrade) const;
int getTotalAttackRange(const TotalUpgrade *totalUpgrade) const;
virtual int getTotalSpeed(const TotalUpgrade *totalUpgrade) const;
virtual int getAnimSpeedBoost(const TotalUpgrade *totalUpgrade) const;
virtual void saveGame(XmlNode *rootNode);
};

View File

@ -169,6 +169,19 @@ void UpgradeTypeBase::load(const XmlNode *upgradeNode, string upgradename) {
else {
prodSpeed = 0;
}
attackSpeedIsMultiplier = false;
if(upgradeNode->hasChild("attack-speed") == true) {
attackSpeed= upgradeNode->getChild("attack-speed")->getAttribute("value")->getIntValue();
if(upgradeNode->getChild("attack-speed")->getAttribute(VALUE_PERCENT_MULTIPLIER_KEY_NAME,false) != NULL) {
attackSpeedIsMultiplier = upgradeNode->getChild("attack-speed")->getAttribute(VALUE_PERCENT_MULTIPLIER_KEY_NAME)->getBoolValue();
//printf("Found prodSpeedIsMultiplier = %d\n",prodSpeedIsMultiplier);
}
}
else {
attackSpeed = 0;
}
}
int UpgradeTypeBase::getAttackStrength(const AttackSkillType *st) const {
@ -212,6 +225,20 @@ int UpgradeTypeBase::getMoveSpeed(const MoveSkillType *st) const {
}
}
int UpgradeTypeBase::getAttackSpeed(const AttackSkillType *st) const {
if(attackSpeedIsMultiplier == false || st == NULL) {
return attackSpeed;
}
else {
int result = 0;
if(attackSpeedIsMultiplierValueList.find(st->getName()) != attackSpeedIsMultiplierValueList.end()) {
result = attackSpeedIsMultiplierValueList.find(st->getName())->second;
}
return result;
}
}
int UpgradeTypeBase::getProdSpeed(const SkillType *st) const {
if(prodSpeedIsMultiplier == false || st == NULL) {
return prodSpeed;
@ -347,6 +374,18 @@ string UpgradeTypeBase::getDesc(bool translatedValue) const{
str+= indent+lang.getString("ProductionSpeed",(translatedValue == true ? "" : "english")) + " +" + intToStr(prodSpeed);
}
}
if(attackSpeed != 0) {
if(str != "") {
str += "\n";
}
if(attackSpeedIsMultiplier) {
str+= indent+lang.getString("AttackSpeed",(translatedValue == true ? "" : "english")) + " *" + intToStr(moveSpeed);
}
else {
str+= indent+lang.getString("AttackSpeed",(translatedValue == true ? "" : "english")) + " +" + intToStr(moveSpeed);
}
}
if(str != "") {
str += "\n";
}
@ -821,6 +860,9 @@ void TotalUpgrade::reset() {
prodSpeed=0;
prodSpeedIsMultiplier=false;
attackSpeed=0;
attackSpeedIsMultiplier=false;
}
void TotalUpgrade::sum(const UpgradeTypeBase *ut, const Unit *unit) {
@ -832,6 +874,7 @@ void TotalUpgrade::sum(const UpgradeTypeBase *ut, const Unit *unit) {
attackRangeIsMultiplier = ut->getAttackRangeIsMultiplier();
moveSpeedIsMultiplier = ut->getMoveSpeedIsMultiplier();
prodSpeedIsMultiplier = ut->getProdSpeedIsMultiplier();
attackSpeedIsMultiplier = ut->getAttackSpeedIsMultiplier();
if(ut->getMaxHpIsMultiplier() == true) {
//printf("#1 Maxhp maxHp = %d, unit->getHp() = %d ut->getMaxHp() = %d\n",maxHp,unit->getHp(),ut->getMaxHp());
@ -941,6 +984,19 @@ void TotalUpgrade::sum(const UpgradeTypeBase *ut, const Unit *unit) {
else {
prodSpeed += ut->getProdSpeed(NULL);
}
if(ut->getAttackSpeedIsMultiplier() == true) {
for(unsigned int i = 0; i < (unsigned int)unit->getType()->getSkillTypeCount(); ++i) {
const SkillType *skillType = unit->getType()->getSkillType(i);
const AttackSkillType *ast = dynamic_cast<const AttackSkillType *>(skillType);
if(ast != NULL) {
attackSpeedIsMultiplierValueList[ast->getName()] += ((double)ast->getSpeed() * ((double)ut->getAttackSpeed(NULL) / (double)100));
}
}
}
else {
attackSpeed += ut->getAttackSpeed(NULL);
}
}
void TotalUpgrade::apply(const UpgradeTypeBase *ut, const Unit *unit) {
@ -1080,6 +1136,23 @@ void TotalUpgrade::deapply(const UpgradeTypeBase *ut,const Unit *unit) {
prodSpeed -= ut->getProdSpeed(NULL);
enforceMinimumValue(0,prodSpeed);
}
if(ut->getAttackSpeedIsMultiplier() == true) {
for(unsigned int i = 0; i < (unsigned int)unit->getType()->getSkillTypeCount(); ++i) {
const SkillType *skillType = unit->getType()->getSkillType(i);
const AttackSkillType *ast = dynamic_cast<const AttackSkillType *>(skillType);
if(ast != NULL) {
attackSpeedIsMultiplierValueList[ast->getName()] -= ((double)ast->getSpeed() * ((double)ut->getAttackSpeed(NULL) / (double)100));
enforceMinimumValue(0, attackSpeedIsMultiplierValueList[ast->getName()]);
}
}
//printf("AFTER Applying moveSpeedIsMultiplier, moveSpeed = %d\n",moveSpeed);
}
else {
attackSpeed -= ut->getAttackSpeed(NULL);
enforceMinimumValue(0, attackSpeed);
}
}
void TotalUpgrade::incLevel(const UnitType *ut) {
@ -1184,6 +1257,16 @@ void TotalUpgrade::saveGame(XmlNode *rootNode) const {
prodSpeedMorphIsMultiplierValueListNode->addAttribute("key",iterMap->first, mapTagReplacements);
prodSpeedMorphIsMultiplierValueListNode->addAttribute("value",intToStr(iterMap->second), mapTagReplacements);
}
upgradeTypeBaseNode->addAttribute("attackSpeed",intToStr(attackSpeed), mapTagReplacements);
upgradeTypeBaseNode->addAttribute("attackSpeedIsMultiplier",intToStr(attackSpeedIsMultiplier), mapTagReplacements);
for(std::map<string,int>::const_iterator iterMap = attackSpeedIsMultiplierValueList.begin();
iterMap != attackSpeedIsMultiplierValueList.end(); ++iterMap) {
XmlNode *attackSpeedIsMultiplierValueListNode = upgradeTypeBaseNode->addChild("attackSpeedIsMultiplierValueList");
attackSpeedIsMultiplierValueListNode->addAttribute("key",iterMap->first, mapTagReplacements);
attackSpeedIsMultiplierValueListNode->addAttribute("value",intToStr(iterMap->second), mapTagReplacements);
}
}
void TotalUpgrade::loadGame(const XmlNode *rootNode) {
@ -1282,6 +1365,16 @@ void TotalUpgrade::loadGame(const XmlNode *rootNode) {
prodSpeedMorphIsMultiplierValueList[node->getAttribute("key")->getValue()] =
node->getAttribute("value")->getIntValue();
}
attackSpeed = upgradeTypeBaseNode->getAttribute("attackSpeed")->getIntValue();
attackSpeedIsMultiplier = upgradeTypeBaseNode->getAttribute("attackSpeedIsMultiplier")->getIntValue() != 0;
vector<XmlNode *> attackSpeedIsMultiplierValueNodeList = upgradeTypeBaseNode->getChildList("attackSpeedIsMultiplierValueList");
for(unsigned int i = 0; i < attackSpeedIsMultiplierValueNodeList.size(); ++i) {
XmlNode *node = attackSpeedIsMultiplierValueNodeList[i];
attackSpeedIsMultiplierValueList[node->getAttribute("key")->getValue()] =
node->getAttribute("value")->getIntValue();
}
}

View File

@ -92,6 +92,10 @@ protected:
std::map<string,int> prodSpeedUpgradeIsMultiplierValueList; /**< @see #attackStrengthMultiplierValueList */
std::map<string,int> prodSpeedMorphIsMultiplierValueList; /**< @see #attackStrengthMultiplierValueList */
int attackSpeed;
bool attackSpeedIsMultiplier;
std::map<string,int> attackSpeedIsMultiplierValueList;
public:
/**
* Creates an UpgradeTypeBase with values such that there are no stat changes.
@ -142,13 +146,16 @@ public:
bool getMoveSpeedIsMultiplier() const {return moveSpeedIsMultiplier;}
int getProdSpeed(const SkillType *st) const;
bool getProdSpeedIsMultiplier() const {return prodSpeedIsMultiplier;}
int getAttackSpeed(const AttackSkillType *st) const;
bool getAttackSpeedIsMultiplier() const {return attackSpeedIsMultiplier;}
/**
* Loads the upgrade values (stat boosts and whether or not the boosts use a multiplier) from an
* XML node.
* @param upgradeNode Node containing the stat boost elements (`max-hp`, `attack-strength`, etc).
* @param upgradename Unique identifier for the upgrade.
*/
void load(const XmlNode *upgradeNode, string upgradename);
/**
@ -243,6 +250,9 @@ public:
crcForUpgradeType.addInt64((int64)prodSpeedUpgradeIsMultiplierValueList.size());
//std::map<string,int> prodSpeedMorphIsMultiplierValueList;
crcForUpgradeType.addInt64((int64)prodSpeedMorphIsMultiplierValueList.size());
crcForUpgradeType.addInt(attackSpeed);
crcForUpgradeType.addInt(attackSpeedIsMultiplier);
return crcForUpgradeType;
}