From f22c96e5034f08d49cdb7fe1d719a46565f9a0a8 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 09:15:53 -0600 Subject: [PATCH 01/14] Start ep now an argument of max-ep Syntax is `` --- source/glest_game/types/unit_type.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 5eac779e..47f4d903 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -249,10 +249,9 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, addItemToVault(&(this->epRegeneration),this->epRegeneration); //startEp - - if(parametersNode->hasChild("start-ep")) { + if(parametersNode->getChild("max-ep")->hasAttribute("start-value")) { //checkItemInVault(&(this->startEp),this->startEp); - startEp= parametersNode->getChild("start-ep")->getAttribute("value")->getIntValue(); + startEp= parametersNode->getChild("max-ep")->getAttribute("start-value")->getIntValue(); } addItemToVault(&(this->startEp),this->startEp); From a65898571d6902e3176cab6331483f0cdeeadcbe Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 09:53:38 -0600 Subject: [PATCH 02/14] Implemented start percentage for EP Note that start-value and start-percentage (both are attributes of the max-ep tag) are mutually exclusive. If they both exist, then start-percentage is used. --- source/glest_game/type_instances/unit.cpp | 9 +++++++-- source/glest_game/types/unit_type.cpp | 21 ++++++++++++++++----- source/glest_game/types/unit_type.h | 13 +++++++++++-- 3 files changed, 34 insertions(+), 9 deletions(-) diff --git a/source/glest_game/type_instances/unit.cpp b/source/glest_game/type_instances/unit.cpp index 7042c4ee..70258b7c 100644 --- a/source/glest_game/type_instances/unit.cpp +++ b/source/glest_game/type_instances/unit.cpp @@ -1959,9 +1959,14 @@ void Unit::born(const CommandType *ct) { } addItemToVault(&this->hp,this->hp); - //set ep from start-ep tag + //set ep from start ep checkItemInVault(&this->ep,this->ep); - this->ep= type->getStartEp(); + if(type->getStartEpType() == UnitType::stValue) { + this->ep= type->getStartEpValue(); + } + else { + this->ep= type->getStartEpPercentage() * type->getTotalMaxEp(&totalUpgrade); + } } void Unit::kill() { diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 47f4d903..a9b264d0 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -126,7 +126,9 @@ UnitType::UnitType() : ProducibleType() { maxUnitCount= 0; maxHp=0; maxEp=0; - startEp=0; + startEpValue=0; + startEpPercentage=0; + startEpType=stValue; armor=0; sight=0; size=0; @@ -248,12 +250,20 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } addItemToVault(&(this->epRegeneration),this->epRegeneration); - //startEp + //startEpValue -- the *absolute* value to use for starting EP if(parametersNode->getChild("max-ep")->hasAttribute("start-value")) { //checkItemInVault(&(this->startEp),this->startEp); - startEp= parametersNode->getChild("max-ep")->getAttribute("start-value")->getIntValue(); + startEpValue= parametersNode->getChild("max-ep")->getAttribute("start-value")->getIntValue(); + startEpType= stValue; } - addItemToVault(&(this->startEp),this->startEp); + addItemToVault(&(this->startEpValue),this->startEpValue); + + //startEpPercentage -- the *relative* value to use for starting EP + if(parametersNode->getChild("max-ep")->hasAttribute("start-percentage")) { + startEpPercentage= parametersNode->getChild("max-ep")->getAttribute("start-percentage")->getFloatValue(); + startEpType= stPercentage; + } + addItemToVault(&(this->startEpPercentage),this->startEpPercentage); //maxUnitCount if(parametersNode->hasChild("max-unit-count")) { @@ -1108,7 +1118,8 @@ std::string UnitType::toString() const { result += " maxHp = " + intToStr(maxHp); result += " hpRegeneration = " + intToStr(hpRegeneration); result += " maxEp = " + intToStr(maxEp); - result += " startEp = " + intToStr(startEp); + result += " startEpValue = " + intToStr(startEpValue); + result += " startEpPercentage = " + intToStr(startEpPercentage); result += " epRegeneration = " + intToStr(epRegeneration); result += " maxUnitCount = " + intToStr(getMaxUnitCount()); diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index ee23d111..5f2a4cd9 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -92,6 +92,11 @@ public: pCount }; + enum StartType { + stValue, + stPercentage + }; + static const char *propertyNames[]; DamageParticleSystemTypes damageParticleSystemTypes; private: @@ -106,7 +111,9 @@ private: int maxHp; int hpRegeneration; int maxEp; - int startEp; + int startEpValue; + double startEpPercentage; + StartType startEpType; int epRegeneration; int maxUnitCount; @@ -181,7 +188,9 @@ public: inline int getHpRegeneration() const {return hpRegeneration;} inline int getMaxEp() const {return maxEp;} inline int getEpRegeneration() const {return epRegeneration;} - inline int getStartEp() const {return startEp;} + inline int getStartEpValue() const {return startEpValue;} + inline double getStartEpPercentage() const {return startEpPercentage;} + inline StartType getStartEpType() const {return startEpType;} inline int getMaxUnitCount() const {return maxUnitCount;} inline bool getField(Field field) const {return fields[field];} inline Field getField() const {return field;} From 94667b9ab9f8c67511387351bc883e149a1d920b Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 10:31:57 -0600 Subject: [PATCH 03/14] Error checking now active for start-ep You can no longer have both start-value and start-percentage. --- source/glest_game/types/unit_type.cpp | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index a9b264d0..960b19c5 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -250,6 +250,14 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } addItemToVault(&(this->epRegeneration),this->epRegeneration); + // Check that we don't use both start-value and start-percentage, as they are mutually + // exclusive + if(parametersNode->getChild("max-ep")->hasAttribute("start-value") && + parametersNode->getChild("max-ep")->hasAttribute("start-percentage")) { + throw megaglest_runtime_error("Unit " + name + + " has both start-value and start-percentage for EP", validationMode); + } + //startEpValue -- the *absolute* value to use for starting EP if(parametersNode->getChild("max-ep")->hasAttribute("start-value")) { //checkItemInVault(&(this->startEp),this->startEp); From 0a68e3a6a490e7fb7033df6c7224dae3e2cded43 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 10:57:34 -0600 Subject: [PATCH 04/14] Implemented starting value for HP Same syntax as for EP: Where `start-percentage` can be replaced by `start-value` to use an absolute number. Note that unlike EP, HP defaults to the max-hp value *before* upgrades are applied. This behavior is not changed. To make units spawn with their fully upgraded HP, set their start-percentage to 1.0. --- source/glest_game/type_instances/unit.cpp | 12 ++++++++- source/glest_game/types/unit_type.cpp | 33 +++++++++++++++++++++++ source/glest_game/types/unit_type.h | 6 +++++ 3 files changed, 50 insertions(+), 1 deletion(-) diff --git a/source/glest_game/type_instances/unit.cpp b/source/glest_game/type_instances/unit.cpp index 70258b7c..9ba9d44b 100644 --- a/source/glest_game/type_instances/unit.cpp +++ b/source/glest_game/type_instances/unit.cpp @@ -1951,7 +1951,17 @@ void Unit::born(const CommandType *ct) { checkItemInVault(&this->hp,this->hp); int original_hp = this->hp; - this->hp= type->getMaxHp(); + + + //set hp from start hp + checkItemInVault(&this->ep,this->ep); + if(type->getStartHpType() == UnitType::stValue) { + this->hp= type->getStartHpValue(); + } + else { + this->hp= type->getStartHpPercentage() * type->getTotalMaxHp(&totalUpgrade); + } + if(original_hp != this->hp) { //printf("File: %s line: %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__); game->getScriptManager()->onUnitTriggerEvent(this,utet_HPChanged); diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 960b19c5..c8e0be10 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -125,6 +125,9 @@ UnitType::UnitType() : ProducibleType() { epRegeneration= 0; maxUnitCount= 0; maxHp=0; + startHpValue=0; + startHpPercentage=1.0; + startHpType=stValue; maxEp=0; startEpValue=0; startEpPercentage=0; @@ -250,6 +253,36 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } addItemToVault(&(this->epRegeneration),this->epRegeneration); + // Check that we don't use both start-value and start-percentage, as they are mutually + // exclusive + if(parametersNode->getChild("max-hp")->hasAttribute("start-value") && + parametersNode->getChild("max-hp")->hasAttribute("start-percentage")) { + throw megaglest_runtime_error("Unit " + name + + " has both start-value and start-percentage for HP", validationMode); + } + + //startHpValue -- the *absolute* value to use for starting HP + if(parametersNode->getChild("max-hp")->hasAttribute("start-value")) { + //checkItemInVault(&(this->startEp),this->startEp); + startHpValue= parametersNode->getChild("max-hp")->getAttribute("start-value")->getIntValue(); + startHpType= stValue; + } + addItemToVault(&(this->startHpValue),this->startHpValue); + + //startHpPercentage -- the *relative* value to use for starting HP + if(parametersNode->getChild("max-hp")->hasAttribute("start-percentage")) { + startHpPercentage= parametersNode->getChild("max-hp")->getAttribute("start-percentage")->getFloatValue(); + startHpType= stPercentage; + } + + // No start value set; use max HP before upgrades + if(!parametersNode->getChild("max-hp")->hasAttribute("start-value") && + !parametersNode->getChild("max-hp")->hasAttribute("start-percentage")) { + startHpValue= parametersNode->getChild("max-hp")->getAttribute("value")->getIntValue(); + startHpType= stValue; + } + addItemToVault(&(this->startHpPercentage),this->startHpPercentage); + // Check that we don't use both start-value and start-percentage, as they are mutually // exclusive if(parametersNode->getChild("max-ep")->hasAttribute("start-value") && diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index 5f2a4cd9..d623eec0 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -109,6 +109,9 @@ private: //basic int id; int maxHp; + int startHpValue; + double startHpPercentage; + StartType startHpType; int hpRegeneration; int maxEp; int startEpValue; @@ -186,6 +189,9 @@ public: inline int getId() const {return id;} inline int getMaxHp() const {return maxHp;} inline int getHpRegeneration() const {return hpRegeneration;} + inline int getStartHpValue() const {return startHpValue;} + inline double getStartHpPercentage() const {return startHpPercentage;} + inline StartType getStartHpType() const {return startHpType;} inline int getMaxEp() const {return maxEp;} inline int getEpRegeneration() const {return epRegeneration;} inline int getStartEpValue() const {return startEpValue;} From 23deb957a74c608374002ec1436bee54e86ea0c3 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 15:37:59 -0600 Subject: [PATCH 05/14] First, basic looting implementation Only absolute values are obtained for now, no loss. --- source/glest_game/types/unit_type.cpp | 26 ++++++++++++++++++ source/glest_game/types/unit_type.h | 35 ++++++++++++++++++++++++ source/glest_game/world/unit_updater.cpp | 7 +++++ 3 files changed, 68 insertions(+) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index c8e0be10..6f3fb13d 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -592,6 +592,32 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } sortedItems.clear(); + // Lootable resources + if(parametersNode->hasChild("resources-death")) { + const XmlNode *deathResourcesNode= parametersNode->getChild("resources-death"); + + for(int i=0; i < deathResourcesNode->getChildCount(); ++i){ + const XmlNode *resourceNode= deathResourcesNode->getChild("resource", i); + + // TODO: Add rest of attributes and make appropriate ones optional + string name= resourceNode->getAttribute("name")->getRestrictedValue(); + int amountValue= resourceNode->getAttribute("amount-value")->getIntValue(); + + LootableResource resource; + resource.setResourceType(techTree->getResourceType(name)); + resource.setAmountValue(amountValue); + + lootableResources.push_back(resource); + + // TODO: Add checks for duplicate resources + } + } + + // TODO: For debug purposes only -- remove + for(int i = 0; i < lootableResources.size(); i++) { + printf("Lootable resource %s has amount %d\n", lootableResources[i].getResourceType()->getName().c_str(), lootableResources[i].getAmountValue()); + } + //image const XmlNode *imageNode= parametersNode->getChild("image"); image= Renderer::getInstance().newTexture2D(rsGame); diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index d623eec0..1635802f 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -63,6 +63,37 @@ public: static const Level * loadGame(const XmlNode *rootNode, const UnitType *ut); }; +// =============================== +// class LootResource +// +/// Stores information about a lootable resource. Lootable resources are stolen by the attacker on death. +// =============================== + +class LootableResource { +private: + const ResourceType *type; + int amountValue; + double amountPercentage; + int lossValue; + double lossPercentage; + +public: + const ResourceType* getResourceType() {return type;} + void setResourceType(const ResourceType *type) {this->type=type;} + + int getAmountValue() {return amountValue;} + void setAmountValue(int amountValue) {this->amountValue=amountValue;} + + double getAmountPercentage() {return amountPercentage;} + void setAmountPercentage(double amountPercentage) {this->amountPercentage=amountPercentage;} + + int getLossValue() {return lossValue;} + void setLossValue(int lossValue) {this->lossValue=lossValue;} + + double getLossPercentage() {return lossPercentage;} + void setLossPercentage(double lossPercentage) {this->lossPercentage=lossPercentage;} +}; + // =============================== // class UnitType // @@ -104,6 +135,7 @@ private: typedef vector CommandTypes; typedef vector StoredResources; typedef vector Levels; + typedef vector LootableResources; private: //basic @@ -151,6 +183,7 @@ private: CommandTypes commandTypes; StoredResources storedResources; Levels levels; + LootableResources lootableResources; //meeting point bool meetingPoint; @@ -220,6 +253,8 @@ public: int getHeight() const {return height;} int getStoredResourceCount() const {return (int)storedResources.size();} inline const Resource *getStoredResource(int i) const {return &storedResources[i];} + int getLootableResourceCount() const {return lootableResources.size();} + inline const LootableResource getLootableResource(int i) const {return lootableResources.at(i);} bool getCellMapCell(int x, int y, CardinalDir facing) const; inline bool getMeetingPoint() const {return meetingPoint;} inline bool getCountUnitDeathInStats() const {return countUnitDeathInStats;} diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index de9d6560..4ee4a4b6 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2573,6 +2573,13 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac attacker->incKills(attacked->getTeam()); } + // TODO: Add looting here + int lootableResourceCount = attacked->getType()->getLootableResourceCount(); + for(int i = 0; i < lootableResourceCount; i++) { + LootableResource resource = attacked->getType()->getLootableResource(i); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); + } + switch(this->game->getGameSettings()->getPathFinderType()) { case pfBasic: break; From df0d7aaac96188ce027190c10d50f9a5a0305124 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 16:13:09 -0600 Subject: [PATCH 06/14] Implemented rest of resource amount/loss attrs --- source/glest_game/types/unit_type.cpp | 39 ++++++++++++++++++------ source/glest_game/world/unit_updater.cpp | 14 ++++++++- 2 files changed, 43 insertions(+), 10 deletions(-) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 6f3fb13d..f4327201 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -598,14 +598,40 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, for(int i=0; i < deathResourcesNode->getChildCount(); ++i){ const XmlNode *resourceNode= deathResourcesNode->getChild("resource", i); - - // TODO: Add rest of attributes and make appropriate ones optional string name= resourceNode->getAttribute("name")->getRestrictedValue(); - int amountValue= resourceNode->getAttribute("amount-value")->getIntValue(); LootableResource resource; resource.setResourceType(techTree->getResourceType(name)); - resource.setAmountValue(amountValue); + + // All attributes are optional, although nothing happens if they aren't used. They can + // be combined freely. Percentages will take affect before absolute values. + if(resourceNode->hasAttribute("amount-value")) { + resource.setAmountValue(resourceNode->getAttribute("amount-value")->getIntValue()); + } + else { + resource.setAmountValue(0); + } + + if(resourceNode->hasAttribute("amount-percentage")) { + resource.setAmountPercentage(resourceNode->getAttribute("amount-percentage")->getFloatValue()); + } + else { + resource.setAmountPercentage(0); + } + + if(resourceNode->hasAttribute("loss-value")) { + resource.setLossValue(resourceNode->getAttribute("loss-value")->getIntValue()); + } + else { + resource.setLossValue(0); + } + + if(resourceNode->hasAttribute("loss-percentage")) { + resource.setLossPercentage(resourceNode->getAttribute("loss-percentage")->getFloatValue()); + } + else { + resource.setLossPercentage(0); + } lootableResources.push_back(resource); @@ -613,11 +639,6 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } } - // TODO: For debug purposes only -- remove - for(int i = 0; i < lootableResources.size(); i++) { - printf("Lootable resource %s has amount %d\n", lootableResources[i].getResourceType()->getName().c_str(), lootableResources[i].getAmountValue()); - } - //image const XmlNode *imageNode= parametersNode->getChild("image"); image= Renderer::getInstance().newTexture2D(rsGame); diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index 4ee4a4b6..08e4d139 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2573,10 +2573,22 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac attacker->incKills(attacked->getTeam()); } - // TODO: Add looting here int lootableResourceCount = attacked->getType()->getLootableResourceCount(); for(int i = 0; i < lootableResourceCount; i++) { LootableResource resource = attacked->getType()->getLootableResource(i); + + // Figure out how much of the resource in question that the attacked unit's faction has + int factionTotalResource = 0; + for(int j = 0; j < attacked->getFaction()->getTechTree()->getResourceTypeCount(); j++) { + if(attacked->getFaction()->getTechTree()->getResourceType(j) == resource.getResourceType()) { + factionTotalResource = attacked->getFaction()->getResource(j)->getAmount(); + break; + } + } + + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); } From 68455a819f16097518d5dba6e1c4955c137625df Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 16:38:33 -0600 Subject: [PATCH 07/14] Added setting to disable going into negatives After all, how does one loot what the other faction does not have? Still, could be useful for some places, by forcing the opponent to go into "debt". --- source/glest_game/types/unit_type.cpp | 7 +++++++ source/glest_game/types/unit_type.h | 4 ++++ source/glest_game/world/unit_updater.cpp | 17 +++++++++++++---- 3 files changed, 24 insertions(+), 4 deletions(-) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index f4327201..75a31207 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -632,6 +632,13 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, else { resource.setLossPercentage(0); } + + if(resourceNode->hasAttribute("allow-negative")) { + resource.setNegativeAllowed(resourceNode->getAttribute("allow-negative")->getBoolValue()); + } + else { + resource.setNegativeAllowed(false); + } lootableResources.push_back(resource); diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index 1635802f..b32a42ee 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -76,6 +76,7 @@ private: double amountPercentage; int lossValue; double lossPercentage; + bool negativeAllowed; public: const ResourceType* getResourceType() {return type;} @@ -92,6 +93,9 @@ public: double getLossPercentage() {return lossPercentage;} void setLossPercentage(double lossPercentage) {this->lossPercentage=lossPercentage;} + + bool isNegativeAllowed() {return negativeAllowed;} + void setNegativeAllowed(bool negativeAllowed) {this->negativeAllowed=negativeAllowed;} }; // =============================== diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index 08e4d139..b297d4ea 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2586,10 +2586,19 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac } } - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); + if(resource.isNegativeAllowed()) { + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); + } + // Can't take more resources than the faction has, otherwise we end up in the negatives + else { + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossPercentage() * factionTotalResource, factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossValue(), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountPercentage() * factionTotalResource, factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountValue(), factionTotalResource)); + } } switch(this->game->getGameSettings()->getPathFinderType()) { From 3cae2559c759f349bfd5a63dc678b7bfa93799da Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 16:44:11 -0600 Subject: [PATCH 08/14] No looting if you attack units in same faction --- source/glest_game/world/unit_updater.cpp | 47 +++++++++++++----------- 1 file changed, 25 insertions(+), 22 deletions(-) diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index b297d4ea..16c5efc5 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2573,31 +2573,34 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac attacker->incKills(attacked->getTeam()); } - int lootableResourceCount = attacked->getType()->getLootableResourceCount(); - for(int i = 0; i < lootableResourceCount; i++) { - LootableResource resource = attacked->getType()->getLootableResource(i); + // Perform resource looting iff the attack is from a different faction + if(attacker->getFaction() != attacked->getFaction()) { + int lootableResourceCount = attacked->getType()->getLootableResourceCount(); + for(int i = 0; i < lootableResourceCount; i++) { + LootableResource resource = attacked->getType()->getLootableResource(i); - // Figure out how much of the resource in question that the attacked unit's faction has - int factionTotalResource = 0; - for(int j = 0; j < attacked->getFaction()->getTechTree()->getResourceTypeCount(); j++) { - if(attacked->getFaction()->getTechTree()->getResourceType(j) == resource.getResourceType()) { - factionTotalResource = attacked->getFaction()->getResource(j)->getAmount(); - break; + // Figure out how much of the resource in question that the attacked unit's faction has + int factionTotalResource = 0; + for(int j = 0; j < attacked->getFaction()->getTechTree()->getResourceTypeCount(); j++) { + if(attacked->getFaction()->getTechTree()->getResourceType(j) == resource.getResourceType()) { + factionTotalResource = attacked->getFaction()->getResource(j)->getAmount(); + break; + } } - } - if(resource.isNegativeAllowed()) { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); - } - // Can't take more resources than the faction has, otherwise we end up in the negatives - else { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossPercentage() * factionTotalResource, factionTotalResource)); - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossValue(), factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountPercentage() * factionTotalResource, factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountValue(), factionTotalResource)); + if(resource.isNegativeAllowed()) { + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); + } + // Can't take more resources than the faction has, otherwise we end up in the negatives + else { + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossPercentage() * factionTotalResource, factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossValue(), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountPercentage() * factionTotalResource, factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountValue(), factionTotalResource)); + } } } From 75eb5c8ddf90d5c70acac26df6a8b5c5b5c6430e Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 16:52:53 -0600 Subject: [PATCH 09/14] Lootable resources now checks for dups --- source/glest_game/types/unit_type.cpp | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 75a31207..b8b07dff 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -591,8 +591,9 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } } sortedItems.clear(); + hasDup = false; - // Lootable resources + // Lootable resources (resources given/lost on death) if(parametersNode->hasChild("resources-death")) { const XmlNode *deathResourcesNode= parametersNode->getChild("resources-death"); @@ -640,9 +641,13 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, resource.setNegativeAllowed(false); } - lootableResources.push_back(resource); + // Figure out if there are duplicate resources. The value stored in the map is arbitrary, + // and exists solely because + if(std::find(lootableResources.begin(), lootableResources.end(), resource) != lootableResources.end()) { + printf("WARNING, unit type [%s] has one or more duplicate lootable resources\n", this->getName(false).c_str()); + } - // TODO: Add checks for duplicate resources + lootableResources.push_back(resource); } } From cedb20646ef62b91347a1a30209a80ee5597e3b0 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 17:43:27 -0600 Subject: [PATCH 10/14] Fixed compilation error Failed to override == --- source/glest_game/types/unit_type.h | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index b32a42ee..af2367ee 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -79,23 +79,27 @@ private: bool negativeAllowed; public: - const ResourceType* getResourceType() {return type;} + const ResourceType* getResourceType() const {return type;} void setResourceType(const ResourceType *type) {this->type=type;} - int getAmountValue() {return amountValue;} + int getAmountValue() const {return amountValue;} void setAmountValue(int amountValue) {this->amountValue=amountValue;} - double getAmountPercentage() {return amountPercentage;} + double getAmountPercentage() const {return amountPercentage;} void setAmountPercentage(double amountPercentage) {this->amountPercentage=amountPercentage;} - int getLossValue() {return lossValue;} + int getLossValue() const {return lossValue;} void setLossValue(int lossValue) {this->lossValue=lossValue;} - double getLossPercentage() {return lossPercentage;} + double getLossPercentage() const {return lossPercentage;} void setLossPercentage(double lossPercentage) {this->lossPercentage=lossPercentage;} - bool isNegativeAllowed() {return negativeAllowed;} + bool isNegativeAllowed() const {return negativeAllowed;} void setNegativeAllowed(bool negativeAllowed) {this->negativeAllowed=negativeAllowed;} + + bool operator==(const LootableResource& other) { + return type == other.getResourceType(); + } }; // =============================== From 191c353491282d19684a5cd4e5378dbdd55d76b6 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 18:07:24 -0600 Subject: [PATCH 11/14] Fixing platform inconsistency It appears that the issue is a Windows problem, with Windows providing macros for min and max that interfere with using the proper ones defined in the algorithm header file. --- source/glest_game/world/unit_updater.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index 16c5efc5..7a6ac884 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2596,10 +2596,10 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac } // Can't take more resources than the faction has, otherwise we end up in the negatives else { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossPercentage() * factionTotalResource, factionTotalResource)); - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -min(resource.getLossValue(), factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountPercentage() * factionTotalResource, factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), min(resource.getAmountValue(), factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(static_cast(resource.getLossPercentage() * factionTotalResource), factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(resource.getLossValue(), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(static_cast(resource.getAmountPercentage() * factionTotalResource), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(resource.getAmountValue(), factionTotalResource)); } } } From ef0cf706b39c82b1df18c36f91a6859d63a46708 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 18:59:11 -0600 Subject: [PATCH 12/14] Converted percentages to use int instead of float May help prevent floating point calculation errors in multiplayer. --- source/glest_game/type_instances/unit.cpp | 4 ++-- source/glest_game/types/unit_type.cpp | 4 ++-- source/glest_game/types/unit_type.h | 8 ++++---- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/source/glest_game/type_instances/unit.cpp b/source/glest_game/type_instances/unit.cpp index 9ba9d44b..74e75b49 100644 --- a/source/glest_game/type_instances/unit.cpp +++ b/source/glest_game/type_instances/unit.cpp @@ -1959,7 +1959,7 @@ void Unit::born(const CommandType *ct) { this->hp= type->getStartHpValue(); } else { - this->hp= type->getStartHpPercentage() * type->getTotalMaxHp(&totalUpgrade); + this->hp= type->getTotalMaxHp(&totalUpgrade) * 100 / type->getStartHpPercentage(); } if(original_hp != this->hp) { @@ -1975,7 +1975,7 @@ void Unit::born(const CommandType *ct) { this->ep= type->getStartEpValue(); } else { - this->ep= type->getStartEpPercentage() * type->getTotalMaxEp(&totalUpgrade); + this->ep= type->getTotalMaxEp(&totalUpgrade) * 100 / type->getStartEpPercentage(); } } diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index c8e0be10..7d926fb8 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -271,7 +271,7 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, //startHpPercentage -- the *relative* value to use for starting HP if(parametersNode->getChild("max-hp")->hasAttribute("start-percentage")) { - startHpPercentage= parametersNode->getChild("max-hp")->getAttribute("start-percentage")->getFloatValue(); + startHpPercentage= parametersNode->getChild("max-hp")->getAttribute("start-percentage")->getIntValue(); startHpType= stPercentage; } @@ -301,7 +301,7 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, //startEpPercentage -- the *relative* value to use for starting EP if(parametersNode->getChild("max-ep")->hasAttribute("start-percentage")) { - startEpPercentage= parametersNode->getChild("max-ep")->getAttribute("start-percentage")->getFloatValue(); + startEpPercentage= parametersNode->getChild("max-ep")->getAttribute("start-percentage")->getIntValue(); startEpType= stPercentage; } addItemToVault(&(this->startEpPercentage),this->startEpPercentage); diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index d623eec0..afe5cc05 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -110,12 +110,12 @@ private: int id; int maxHp; int startHpValue; - double startHpPercentage; + int startHpPercentage; StartType startHpType; int hpRegeneration; int maxEp; int startEpValue; - double startEpPercentage; + int startEpPercentage; StartType startEpType; int epRegeneration; int maxUnitCount; @@ -190,12 +190,12 @@ public: inline int getMaxHp() const {return maxHp;} inline int getHpRegeneration() const {return hpRegeneration;} inline int getStartHpValue() const {return startHpValue;} - inline double getStartHpPercentage() const {return startHpPercentage;} + inline int getStartHpPercentage() const {return startHpPercentage;} inline StartType getStartHpType() const {return startHpType;} inline int getMaxEp() const {return maxEp;} inline int getEpRegeneration() const {return epRegeneration;} inline int getStartEpValue() const {return startEpValue;} - inline double getStartEpPercentage() const {return startEpPercentage;} + inline int getStartEpPercentage() const {return startEpPercentage;} inline StartType getStartEpType() const {return startEpType;} inline int getMaxUnitCount() const {return maxUnitCount;} inline bool getField(Field field) const {return fields[field];} From f0801b3c33a2ecb5708b598e6fec29fd8a3bbf00 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 19:03:33 -0600 Subject: [PATCH 13/14] Converted floats to ints As discussed with Titi, this may prevent some issues with multiplayer getting out of sync due to different floating point calculations. --- source/glest_game/types/unit_type.cpp | 4 ++-- source/glest_game/types/unit_type.h | 12 ++++++------ source/glest_game/world/unit_updater.cpp | 8 ++++---- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/source/glest_game/types/unit_type.cpp b/source/glest_game/types/unit_type.cpp index 11ee7285..a43a2034 100644 --- a/source/glest_game/types/unit_type.cpp +++ b/source/glest_game/types/unit_type.cpp @@ -614,7 +614,7 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } if(resourceNode->hasAttribute("amount-percentage")) { - resource.setAmountPercentage(resourceNode->getAttribute("amount-percentage")->getFloatValue()); + resource.setAmountPercentage(resourceNode->getAttribute("amount-percentage")->getIntValue()); } else { resource.setAmountPercentage(0); @@ -628,7 +628,7 @@ void UnitType::loaddd(int id,const string &dir, const TechTree *techTree, } if(resourceNode->hasAttribute("loss-percentage")) { - resource.setLossPercentage(resourceNode->getAttribute("loss-percentage")->getFloatValue()); + resource.setLossPercentage(resourceNode->getAttribute("loss-percentage")->getIntValue()); } else { resource.setLossPercentage(0); diff --git a/source/glest_game/types/unit_type.h b/source/glest_game/types/unit_type.h index a0ce6a7c..0342394a 100644 --- a/source/glest_game/types/unit_type.h +++ b/source/glest_game/types/unit_type.h @@ -73,9 +73,9 @@ class LootableResource { private: const ResourceType *type; int amountValue; - double amountPercentage; + int amountPercentage; int lossValue; - double lossPercentage; + int lossPercentage; bool negativeAllowed; public: @@ -85,14 +85,14 @@ public: int getAmountValue() const {return amountValue;} void setAmountValue(int amountValue) {this->amountValue=amountValue;} - double getAmountPercentage() const {return amountPercentage;} - void setAmountPercentage(double amountPercentage) {this->amountPercentage=amountPercentage;} + int getAmountPercentage() const {return amountPercentage;} + void setAmountPercentage(int amountPercentage) {this->amountPercentage=amountPercentage;} int getLossValue() const {return lossValue;} void setLossValue(int lossValue) {this->lossValue=lossValue;} - double getLossPercentage() const {return lossPercentage;} - void setLossPercentage(double lossPercentage) {this->lossPercentage=lossPercentage;} + int getLossPercentage() const {return lossPercentage;} + void setLossPercentage(int lossPercentage) {this->lossPercentage=lossPercentage;} bool isNegativeAllowed() const {return negativeAllowed;} void setNegativeAllowed(bool negativeAllowed) {this->negativeAllowed=negativeAllowed;} diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index 7a6ac884..fe5b8384 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2589,16 +2589,16 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac } if(resource.isNegativeAllowed()) { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossPercentage() * factionTotalResource); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(factionTotalResource * 100 / resource.getLossPercentage())); attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountPercentage() * factionTotalResource); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), factionTotalResource * 100 / resource.getAmountPercentage()); attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); } // Can't take more resources than the faction has, otherwise we end up in the negatives else { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(static_cast(resource.getLossPercentage() * factionTotalResource), factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(factionTotalResource * 100 / resource.getLossPercentage(), factionTotalResource)); attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(resource.getLossValue(), factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(static_cast(resource.getAmountPercentage() * factionTotalResource), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(factionTotalResource * 100 / resource.getAmountPercentage(), factionTotalResource)); attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(resource.getAmountValue(), factionTotalResource)); } } From b9eb74d916e18c93612e7527f325825ffc9c30c9 Mon Sep 17 00:00:00 2001 From: Mike Hoffert Date: Sat, 19 Jul 2014 19:12:34 -0600 Subject: [PATCH 14/14] Percentages were wrong way around --- source/glest_game/world/unit_updater.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/source/glest_game/world/unit_updater.cpp b/source/glest_game/world/unit_updater.cpp index fe5b8384..6e0bc167 100644 --- a/source/glest_game/world/unit_updater.cpp +++ b/source/glest_game/world/unit_updater.cpp @@ -2589,16 +2589,16 @@ void UnitUpdater::damage(Unit *attacker, const AttackSkillType* ast, Unit *attac } if(resource.isNegativeAllowed()) { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(factionTotalResource * 100 / resource.getLossPercentage())); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(factionTotalResource * resource.getLossPercentage() / 100)); attacked->getFaction()->incResourceAmount(resource.getResourceType(), -resource.getLossValue()); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), factionTotalResource * 100 / resource.getAmountPercentage()); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), factionTotalResource * resource.getAmountPercentage() / 100); attacker->getFaction()->incResourceAmount(resource.getResourceType(), resource.getAmountValue()); } // Can't take more resources than the faction has, otherwise we end up in the negatives else { - attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(factionTotalResource * 100 / resource.getLossPercentage(), factionTotalResource)); + attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(factionTotalResource * resource.getLossPercentage() / 100, factionTotalResource)); attacked->getFaction()->incResourceAmount(resource.getResourceType(), -(std::min)(resource.getLossValue(), factionTotalResource)); - attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(factionTotalResource * 100 / resource.getAmountPercentage(), factionTotalResource)); + attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(factionTotalResource * resource.getAmountPercentage() / 100, factionTotalResource)); attacker->getFaction()->incResourceAmount(resource.getResourceType(), (std::min)(resource.getAmountValue(), factionTotalResource)); } }