Changeset View
Changeset View
Standalone View
Standalone View
binaries/data/mods/public/simulation/ai/petra/baseManager.js
Show First 20 Lines • Show All 160 Lines • ▼ Show 20 Lines | for (let type of dropsite.resourceDropsiteTypes()) | ||||
let nearby = this.dropsiteSupplies[type].nearby; | let nearby = this.dropsiteSupplies[type].nearby; | ||||
let medium = this.dropsiteSupplies[type].medium; | let medium = this.dropsiteSupplies[type].medium; | ||||
let faraway = this.dropsiteSupplies[type].faraway; | let faraway = this.dropsiteSupplies[type].faraway; | ||||
resources.forEach(function(supply) | resources.forEach(function(supply) | ||||
{ | { | ||||
if (!supply.position()) | if (!supply.position()) | ||||
return; | return; | ||||
if (supply.hasClass("Animal")) // moving resources are treated differently | // Moving resources and fields are treated differently. | ||||
return; | if (supply.hasClasses(["Animal", "Field"])) | ||||
if (supply.hasClass("Field")) // fields are treated separately | |||||
return; | return; | ||||
// quick accessibility check | // quick accessibility check | ||||
if (PETRA.getLandAccess(gameState, supply) != accessIndex) | if (PETRA.getLandAccess(gameState, supply) != accessIndex) | ||||
return; | return; | ||||
let dist = API3.SquareVectorDistance(supply.position(), dropsitePos); | let dist = API3.SquareVectorDistance(supply.position(), dropsitePos); | ||||
if (dist < maxDistResourceSquare) | if (dist < maxDistResourceSquare) | ||||
{ | { | ||||
▲ Show 20 Lines • Show All 88 Lines • ▼ Show 20 Lines | |||||
/** | /** | ||||
* Returns the position of the best place to build a new dropsite for the specified resource and dropsite template. | * Returns the position of the best place to build a new dropsite for the specified resource and dropsite template. | ||||
*/ | */ | ||||
PETRA.BaseManager.prototype.findBestDropsiteLocation = function(gameState, resource, templateName) | PETRA.BaseManager.prototype.findBestDropsiteLocation = function(gameState, resource, templateName) | ||||
{ | { | ||||
const template = gameState.getTemplate(gameState.applyCiv(templateName)); | const template = gameState.getTemplate(gameState.applyCiv(templateName)); | ||||
// CCs and Docks are handled elsewhere. | // CCs and Docks are handled elsewhere. | ||||
if (template.hasClass("CivCentre") || template.hasClass("Dock")) | if (template.hasClasses(["CivCentre", "Dock"])) | ||||
return { "quality": 0, "pos": [0, 0] }; | return { "quality": 0, "pos": [0, 0] }; | ||||
let halfSize = 0; | let halfSize = 0; | ||||
if (template.get("Footprint/Square")) | if (template.get("Footprint/Square")) | ||||
halfSize = Math.max(+template.get("Footprint/Square/@depth"), +template.get("Footprint/Square/@width")) / 2; | halfSize = Math.max(+template.get("Footprint/Square/@depth"), +template.get("Footprint/Square/@width")) / 2; | ||||
else if (template.get("Footprint/Circle")) | else if (template.get("Footprint/Circle")) | ||||
halfSize = +template.get("Footprint/Circle/@radius"); | halfSize = +template.get("Footprint/Circle/@radius"); | ||||
▲ Show 20 Lines • Show All 233 Lines • ▼ Show 20 Lines | |||||
PETRA.BaseManager.prototype.assignRolelessUnits = function(gameState, roleless) | PETRA.BaseManager.prototype.assignRolelessUnits = function(gameState, roleless) | ||||
{ | { | ||||
if (!roleless) | if (!roleless) | ||||
roleless = this.units.filter(API3.Filters.not(API3.Filters.byHasMetadata(PlayerID, "role"))).values(); | roleless = this.units.filter(API3.Filters.not(API3.Filters.byHasMetadata(PlayerID, "role"))).values(); | ||||
for (let ent of roleless) | for (let ent of roleless) | ||||
{ | { | ||||
if (ent.hasClass("Worker") || ent.hasClass("CitizenSoldier") || ent.hasClass("FishingBoat")) | if (ent.hasClasses(["Worker", "CitizenSoldier", "FishingBoat"])) | ||||
ent.setMetadata(PlayerID, "role", "worker"); | ent.setMetadata(PlayerID, "role", "worker"); | ||||
} | } | ||||
}; | }; | ||||
/** | /** | ||||
* If the numbers of workers on the resources is unbalanced then set some of workers to idle so | * If the numbers of workers on the resources is unbalanced then set some of workers to idle so | ||||
* they can be reassigned by reassignIdleWorkers. | * they can be reassigned by reassignIdleWorkers. | ||||
* TODO: actually this probably should be in the HQ. | * TODO: actually this probably should be in the HQ. | ||||
▲ Show 20 Lines • Show All 246 Lines • ▼ Show 20 Lines | PETRA.BaseManager.prototype.assignToFoundations = function(gameState, noRepair) | ||||
} | } | ||||
for (let target of foundations.values()) | for (let target of foundations.values()) | ||||
{ | { | ||||
if (target.hasClass("Field")) | if (target.hasClass("Field")) | ||||
continue; // we do not build fields | continue; // we do not build fields | ||||
if (gameState.ai.HQ.isNearInvadingArmy(target.position())) | if (gameState.ai.HQ.isNearInvadingArmy(target.position())) | ||||
if (!target.hasClass("CivCentre") && !target.hasClass("Wall") && | if (!target.hasClasses(["CivCentre", "Wall"]) && | ||||
(!target.hasClass("Wonder") || !gameState.getVictoryConditions().has("wonder"))) | (!target.hasClass("Wonder") || !gameState.getVictoryConditions().has("wonder"))) | ||||
continue; | continue; | ||||
// if our territory has shrinked since this foundation was positioned, do not build it | // if our territory has shrinked since this foundation was positioned, do not build it | ||||
if (PETRA.isNotWorthBuilding(gameState, target)) | if (PETRA.isNotWorthBuilding(gameState, target)) | ||||
continue; | continue; | ||||
let assigned = gameState.getOwnEntitiesByMetadata("target-foundation", target.id()).length; | let assigned = gameState.getOwnEntitiesByMetadata("target-foundation", target.id()).length; | ||||
let maxTotalBuilders = Math.ceil(workers.length * builderRatio); | let maxTotalBuilders = Math.ceil(workers.length * builderRatio); | ||||
if (maxTotalBuilders < 2 && workers.length > 1) | if (maxTotalBuilders < 2 && workers.length > 1) | ||||
maxTotalBuilders = 2; | maxTotalBuilders = 2; | ||||
if (target.hasClass("House") && gameState.getPopulationLimit() < gameState.getPopulation() + 5 && | if (target.hasClass("House") && gameState.getPopulationLimit() < gameState.getPopulation() + 5 && | ||||
gameState.getPopulationLimit() < gameState.getPopulationMax()) | gameState.getPopulationLimit() < gameState.getPopulationMax()) | ||||
maxTotalBuilders += 2; | maxTotalBuilders += 2; | ||||
let targetNB = 2; | let targetNB = 2; | ||||
if (target.hasClass("Fortress") || target.hasClass("Wonder") || | if (target.hasClasses(["Fortress", "Wonder"]) || | ||||
target.getMetadata(PlayerID, "phaseUp") == true) | target.getMetadata(PlayerID, "phaseUp") == true) | ||||
targetNB = 7; | targetNB = 7; | ||||
else if (target.hasClass("Barracks") || target.hasClass("Range") || target.hasClass("Stable") || | else if (target.hasClasses(["Barracks", "Range", "Stable", "Tower", "Market"])) | ||||
target.hasClass("Tower") || target.hasClass("Market")) | |||||
targetNB = 4; | targetNB = 4; | ||||
else if (target.hasClass("House") || target.hasClass("DropsiteWood")) | else if (target.hasClasses(["House", "DropsiteWood"])) | ||||
targetNB = 3; | targetNB = 3; | ||||
if (target.getMetadata(PlayerID, "baseAnchor") == true || | if (target.getMetadata(PlayerID, "baseAnchor") == true || | ||||
target.hasClass("Wonder") && gameState.getVictoryConditions().has("wonder")) | target.hasClass("Wonder") && gameState.getVictoryConditions().has("wonder")) | ||||
{ | { | ||||
targetNB = 15; | targetNB = 15; | ||||
maxTotalBuilders = Math.max(maxTotalBuilders, 15); | maxTotalBuilders = Math.max(maxTotalBuilders, 15); | ||||
} | } | ||||
▲ Show 20 Lines • Show All 55 Lines • ▼ Show 20 Lines | PETRA.BaseManager.prototype.assignToFoundations = function(gameState, noRepair) | ||||
for (let target of damagedBuildings.values()) | for (let target of damagedBuildings.values()) | ||||
{ | { | ||||
// Don't repair if we're still under attack, unless it's a vital (civcentre or wall) building | // Don't repair if we're still under attack, unless it's a vital (civcentre or wall) building | ||||
// that's being destroyed. | // that's being destroyed. | ||||
if (gameState.ai.HQ.isNearInvadingArmy(target.position())) | if (gameState.ai.HQ.isNearInvadingArmy(target.position())) | ||||
{ | { | ||||
if (target.healthLevel() > 0.5 || | if (target.healthLevel() > 0.5 || | ||||
!target.hasClass("CivCentre") && !target.hasClass("Wall") && | !target.hasClasses(["CivCentre", "Wall"]) && | ||||
(!target.hasClass("Wonder") || !gameState.getVictoryConditions().has("wonder"))) | (!target.hasClass("Wonder") || !gameState.getVictoryConditions().has("wonder"))) | ||||
continue; | continue; | ||||
} | } | ||||
else if (noRepair && !target.hasClass("CivCentre")) | else if (noRepair && !target.hasClass("CivCentre")) | ||||
continue; | continue; | ||||
if (target.decaying()) | if (target.decaying()) | ||||
continue; | continue; | ||||
let assigned = gameState.getOwnEntitiesByMetadata("target-foundation", target.id()).length; | let assigned = gameState.getOwnEntitiesByMetadata("target-foundation", target.id()).length; | ||||
let maxTotalBuilders = Math.ceil(workers.length * builderRatio); | let maxTotalBuilders = Math.ceil(workers.length * builderRatio); | ||||
let targetNB = 1; | let targetNB = 1; | ||||
if (target.hasClass("Fortress") || target.hasClass("Wonder")) | if (target.hasClasses(["Fortress", "Wonder"])) | ||||
targetNB = 3; | targetNB = 3; | ||||
if (target.getMetadata(PlayerID, "baseAnchor") == true || | if (target.getMetadata(PlayerID, "baseAnchor") == true || | ||||
target.hasClass("Wonder") && gameState.getVictoryConditions().has("wonder")) | target.hasClass("Wonder") && gameState.getVictoryConditions().has("wonder")) | ||||
{ | { | ||||
maxTotalBuilders = Math.ceil(workers.length * Math.max(0.3, builderRatio)); | maxTotalBuilders = Math.ceil(workers.length * Math.max(0.3, builderRatio)); | ||||
targetNB = 5; | targetNB = 5; | ||||
if (target.healthLevel() < 0.3) | if (target.healthLevel() < 0.3) | ||||
{ | { | ||||
▲ Show 20 Lines • Show All 202 Lines • Show Last 20 Lines |
Wildfire Games · Phabricator