1
0
forked from mirrors/0ad

Add a {native} civ replacement in buildable and trainable template names

Reviewed By: wraitii, elexis, with inputs from s0600204
Differential Revision: https://code.wildfiregames.com/D1084
This was SVN commit r20603.
This commit is contained in:
mimo
2017-12-07 18:33:08 +00:00
parent 6bbd8297db
commit 2a6fcafbae
7 changed files with 132 additions and 27 deletions
@@ -104,7 +104,7 @@ function getTemplateListsFromUnit(templateName)
if (template.Builder && template.Builder.Entities._string)
for (let build of template.Builder.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build) && templateLists.structures.indexOf(build) === -1)
templateLists.structures.push(build);
}
@@ -114,7 +114,7 @@ function getTemplateListsFromUnit(templateName)
if (template.ProductionQueue.Entities)
for (let build of template.ProductionQueue.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build) && templateLists.units.indexOf(build) === -1)
templateLists.units.push(build);
}
@@ -158,7 +158,7 @@ function getTemplateListsFromStructure(templateName)
if (template.ProductionQueue.Entities && template.ProductionQueue.Entities._string)
for (let build of template.ProductionQueue.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build) && templateLists.units.indexOf(build) === -1)
templateLists.units.push(build);
}
@@ -21,7 +21,7 @@ function getActualUpgradeData(upgradesInfo)
let newUpgrades = [];
for (let upgrade of upgradesInfo)
{
upgrade.entity = upgrade.entity.replace("{civ}", g_SelectedCiv);
upgrade.entity = upgrade.entity.replace(/\{(civ|native)\}/g, g_SelectedCiv);
let data = GetTemplateDataHelper(loadTemplate(upgrade.entity), null, g_AuraData, g_ResourceData, g_DamageTypes);
data.cost = upgrade.cost;
@@ -117,7 +117,7 @@ function loadUnit(templateName)
unit.production.units = [];
for (let build of template.ProductionQueue.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build))
unit.production.units.push(build);
}
@@ -147,7 +147,7 @@ function loadUnit(templateName)
unit.builder = [];
for (let build of template.Builder.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build))
unit.builder.push(build);
}
@@ -183,7 +183,7 @@ function loadStructure(templateName)
if (template.ProductionQueue.Entities && template.ProductionQueue.Entities._string)
for (let build of template.ProductionQueue.Entities._string.split(" "))
{
build = build.replace("{civ}", g_SelectedCiv);
build = build.replace(/\{(civ|native)\}/g, g_SelectedCiv);
if (Engine.TemplateExists(build))
structure.production.units.push(build);
}
@@ -5,13 +5,13 @@ Builder.prototype.Schema =
"<a:example>" +
"<Rate>1.0</Rate>" +
"<Entities datatype='tokens'>" +
"\n structures/{civ}_barracks\n structures/{civ}_civil_centre\n structures/pers_apadana\n " +
"\n structures/{civ}_barracks\n structures/{native}_civil_centre\n structures/pers_apadana\n " +
"</Entities>" +
"</a:example>" +
"<element name='Rate' a:help='Construction speed multiplier (1.0 is normal speed, higher values are faster).'>" +
"<ref name='positiveDecimal'/>" +
"</element>" +
"<element name='Entities' a:help='Space-separated list of entity template names that this unit can build. The special string \"{civ}\" will be automatically replaced by the civ code of the unit&apos;s owner. This element can also be empty, in which case no new foundations may be placed by the unit, but they can still repair existing buildings.'>" +
"<element name='Entities' a:help='Space-separated list of entity template names that this unit can build. The special string \"{civ}\" will be automatically replaced by the civ code of the unit&apos;s owner, while the string \"{native}\" will be automatically replaced by the unit&apos;s civ code. This element can also be empty, in which case no new foundations may be placed by the unit, but they can still repair existing buildings.'>" +
"<attribute name='datatype'>" +
"<value>tokens</value>" +
"</attribute>" +
@@ -34,6 +34,10 @@ Builder.prototype.GetEntitiesList = function()
if (!cmpPlayer)
return [];
let cmpIdentity = Engine.QueryInterface(this.entity, IID_Identity);
if (cmpIdentity)
string = string.replace(/\{native\}/g, cmpIdentity.GetCiv());
let entities = string.replace(/\{civ\}/g, cmpPlayer.GetCiv()).split(/\s+/);
let disabledTemplates = cmpPlayer.GetDisabledTemplates();
@@ -8,14 +8,14 @@ ProductionQueue.prototype.Schema =
"<a:example>" +
"<BatchTimeModifier>0.7</BatchTimeModifier>" +
"<Entities datatype='tokens'>" +
"\n units/{civ}_support_female_citizen\n units/{civ}_support_trader\n units/athen_infantry_spearman_b\n " +
"\n units/{civ}_support_female_citizen\n units/{native}_support_trader\n units/athen_infantry_spearman_b\n " +
"</Entities>" +
"</a:example>" +
"<element name='BatchTimeModifier' a:help='Modifier that influences the time benefit for batch training'>" +
"<ref name='nonNegativeDecimal'/>" +
"</element>" +
"<optional>" +
"<element name='Entities' a:help='Space-separated list of entity template names that this entity can train. The special string \"{civ}\" will be automatically replaced by the civ code of the entity&apos;s owner.'>" +
"<element name='Entities' a:help='Space-separated list of entity template names that this entity can train. The special string \"{civ}\" will be automatically replaced by the civ code of the entity&apos;s owner, while the string \"{native}\" will be automatically replaced by the entity&apos;s civ code.'>" +
"<attribute name='datatype'>" +
"<value>tokens</value>" +
"</attribute>" +
@@ -96,31 +96,33 @@ ProductionQueue.prototype.CalculateEntitiesList = function()
if (!this.template.Entities)
return;
var string = this.template.Entities._string;
let string = this.template.Entities._string;
if (!string)
return;
// Replace the "{civ}" codes with this entity's civ ID
var cmpTemplateManager = Engine.QueryInterface(SYSTEM_ENTITY, IID_TemplateManager);
var cmpPlayer = QueryOwnerInterface(this.entity);
// Replace the "{civ}" and "{native}" codes with the owner's civ ID and entity's civ ID.
let cmpTemplateManager = Engine.QueryInterface(SYSTEM_ENTITY, IID_TemplateManager);
let cmpPlayer = QueryOwnerInterface(this.entity);
if (!cmpPlayer)
return;
var entitiesList = string.replace(/\{civ\}/g, cmpPlayer.GetCiv()).split(/\s+/);
let cmpIdentity = Engine.QueryInterface(this.entity, IID_Identity);
if (cmpIdentity)
string = string.replace(/\{native\}/g, cmpIdentity.GetCiv());
let entitiesList = string.replace(/\{civ\}/g, cmpPlayer.GetCiv()).split(/\s+/);
// filter out disabled and invalid entities
var disabledEntities = cmpPlayer.GetDisabledTemplates();
entitiesList = entitiesList.filter(
function(v) { return !disabledEntities[v] && cmpTemplateManager.TemplateExists(v); }
);
let disabledEntities = cmpPlayer.GetDisabledTemplates();
entitiesList = entitiesList.filter(ent => !disabledEntities[ent] && cmpTemplateManager.TemplateExists(ent));
// check if some templates need to show their advanced or elite version
var upgradeTemplate = function(templateName)
let upgradeTemplate = function(templateName)
{
var template = cmpTemplateManager.GetTemplate(templateName);
let template = cmpTemplateManager.GetTemplate(templateName);
while (template && template.Promotion !== undefined)
{
var requiredXp = ApplyValueModificationsToTemplate("Promotion/RequiredXp", +template.Promotion.RequiredXp, cmpPlayer.GetPlayerID(), template);
let requiredXp = ApplyValueModificationsToTemplate("Promotion/RequiredXp", +template.Promotion.RequiredXp, cmpPlayer.GetPlayerID(), template);
if (requiredXp > 0)
break;
templateName = template.Promotion.Entity;
@@ -13,7 +13,7 @@ AddMock(SYSTEM_ENTITY, IID_TemplateManager, {
let cmpBuilder = ConstructComponent(builderId, "Builder", {
"Rate": 1.0,
"Entities": { "_string": "structures/{civ}_barracks structures/{civ}_civil_centre" }
"Entities": { "_string": "structures/{civ}_barracks structures/{civ}_civil_centre structures/{native}_house" }
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), []);
@@ -32,7 +32,11 @@ AddMock(builderId, IID_Ownership, {
"GetOwner": () => playerId
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_barracks", "structures/iber_civil_centre"]);
AddMock(builderId, IID_Identity, {
"GetCiv": () => "iber"
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_barracks", "structures/iber_civil_centre", "structures/iber_house"]);
AddMock(SYSTEM_ENTITY, IID_TemplateManager, {
"TemplateExists": name => name == "structures/iber_civil_centre"
@@ -50,7 +54,7 @@ AddMock(playerEntityID, IID_Player, {
"GetPlayerID": () => playerId
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_barracks", "structures/iber_civil_centre"]);
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_barracks", "structures/iber_civil_centre", "structures/iber_house"]);
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "iber",
@@ -58,7 +62,15 @@ AddMock(playerEntityID, IID_Player, {
"GetPlayerID": () => playerId
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_civil_centre"]);
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/iber_civil_centre", "structures/iber_house"]);
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "athen",
"GetDisabledTemplates": () => ({ "structures/athen_barracks": true }),
"GetPlayerID": () => playerId
});
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetEntitiesList(), ["structures/athen_civil_centre", "structures/iber_house"]);
TS_ASSERT_UNEVAL_EQUALS(cmpBuilder.GetRange(), { "max": 2, "min": 0 });
@@ -0,0 +1,87 @@
Resources = {
"BuildSchema": (a, b) => {}
};
Engine.LoadHelperScript("Player.js");
Engine.LoadComponentScript("interfaces/ProductionQueue.js");
Engine.LoadComponentScript("ProductionQueue.js");
const productionQueueId = 6;
const playerId = 1;
const playerEntityID = 2;
AddMock(SYSTEM_ENTITY, IID_TemplateManager, {
"TemplateExists": () => true,
"GetTemplate": name => {}
});
let cmpProductionQueue = ConstructComponent(productionQueueId, "ProductionQueue", {
"Entities": { "_string": "units/{civ}_cavalry_javelinist_b units/{civ}_infantry_swordsman_b " +
"units/{native}_support_female_citizen" }
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), []);
AddMock(SYSTEM_ENTITY, IID_PlayerManager, {
"GetPlayerByID": id => playerEntityID
});
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "iber",
"GetDisabledTemplates": () => ({}),
"GetPlayerID": () => playerId
});
AddMock(productionQueueId, IID_Ownership, {
"GetOwner": () => playerId
});
AddMock(productionQueueId, IID_Identity, {
"GetCiv": () => "iber"
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), ["units/iber_cavalry_javelinist_b", "units/iber_infantry_swordsman_b",
"units/iber_support_female_citizen"]);
AddMock(SYSTEM_ENTITY, IID_TemplateManager, {
"TemplateExists": name => name == "units/iber_support_female_citizen",
"GetTemplate": name => {}
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), ["units/iber_support_female_citizen"]);
AddMock(SYSTEM_ENTITY, IID_TemplateManager, {
"TemplateExists": () => true,
"GetTemplate": name => {}
});
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "iber",
"GetDisabledTemplates": () => ({ "units/athen_infantry_swordsman_b": true }),
"GetPlayerID": () => playerId
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), ["units/iber_cavalry_javelinist_b", "units/iber_infantry_swordsman_b",
"units/iber_support_female_citizen"]);
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "iber",
"GetDisabledTemplates": () => ({ "units/iber_infantry_swordsman_b": true }),
"GetPlayerID": () => playerId
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), ["units/iber_cavalry_javelinist_b", "units/iber_support_female_citizen"]);
AddMock(playerEntityID, IID_Player, {
"GetCiv": () => "athen",
"GetDisabledTemplates": () => ({ "units/athen_infantry_swordsman_b": true }),
"GetPlayerID": () => playerId
});
cmpProductionQueue.CalculateEntitiesList();
TS_ASSERT_UNEVAL_EQUALS(cmpProductionQueue.GetEntitiesList(), ["units/athen_cavalry_javelinist_b", "units/iber_support_female_citizen"]);