diff --git a/app/imports/api/engine/actions/applyPropertyByType/applyAction.js b/app/imports/api/engine/actions/applyPropertyByType/applyAction.js index 560e0bba..3551bf0b 100644 --- a/app/imports/api/engine/actions/applyPropertyByType/applyAction.js +++ b/app/imports/api/engine/actions/applyPropertyByType/applyAction.js @@ -8,6 +8,8 @@ import { damagePropertyWork } from '/imports/api/creature/creatureProperties/met import numberToSignedString from '/imports/api/utility/numberToSignedString.js'; import { applyNodeTriggers } from '/imports/api/engine/actions/applyTriggers.js'; import { resetProperties } from '/imports/api/creature/creatures/methods/restCreature.js'; +import { getPropertyDecendants } from '/imports/api/engine/loadCreatures.js'; +import { nodeArrayToTree } from '/imports/api/parenting/nodesToTree.js'; export default function applyAction(node, actionContext) { applyNodeTriggers(node, 'before', actionContext); @@ -211,6 +213,7 @@ function spendResources(prop, actionContext) { let itemQuantityAdjustments = []; let spendLog = []; let gainLog = []; + let ammoChildren = []; try { prop.resources.itemsConsumed.forEach(itemConsumed => { recalculateCalculation(itemConsumed.quantity, actionContext); @@ -221,9 +224,6 @@ function spendResources(prop, actionContext) { if (!item || item.ancestors[0].id !== prop.ancestors[0].id) { throw 'The prop\'s ammo was not found on the creature'; } - if (!item.equipped) { - throw 'The selected ammo is not equipped'; - } if ( !itemConsumed.quantity.value || !isFinite(itemConsumed.quantity.value) @@ -242,6 +242,7 @@ function spendResources(prop, actionContext) { } else if (itemConsumed.quantity.value < 0) { gainLog.push(logName + ': ' + -itemConsumed.quantity.value); } + ammoChildren.push(...getItemChildren(item, actionContext, prop)); }); } catch (e) { actionContext.addLog({ @@ -303,4 +304,36 @@ function spendResources(prop, actionContext) { value: spendLog.join('\n'), inline: true, }); + + // Apply the ammo children + ammoChildren.forEach(prop => { + applyProperty(prop, actionContext); + }); +} + +function getItemChildren(item, actionContext, prop) { + // Skip if the prop or the item are ancestors of one another, otherwise infinite loop + if (hasAncestorRelationship(item, prop)) return []; + // Get the item children + const itemProperties = getPropertyDecendants(actionContext.creature._id, item._id); + // Tree them up + const propertyForest = nodeArrayToTree(itemProperties); + return propertyForest +} + +function hasAncestorRelationship(a, b) { + let top, bottom; + if (a.ancestors.length === b.ancestors.length) { + // Can't be ancestors of one another if they have the same number of ancestors + return false; + } else if (a.ancestors.length > b.ancestors.length) { + // longer ancestor list goes on the bottom + top = b; + bottom = a; + } else { + top = a; + bottom = b; + } + const expectedAncestorPosition = top.ancestors.length; + return bottom.ancestors[expectedAncestorPosition]?.id === top._id; }