From 4550661a59d88ae1d9caa7a615b3f41c283cb8a8 Mon Sep 17 00:00:00 2001 From: Stefan Zermatten Date: Sat, 6 May 2023 10:45:03 +0200 Subject: [PATCH] Tested and fixed proficiencies by tag --- .../buildComputation/linkTypeDependencies.js | 3 + .../computeByType/computeCalculation.js | 3 +- .../tests/computeProficiencies.testFn.js | 64 +++++++++++++++++++ .../computeComputation/tests/index.js | 18 ++++-- app/imports/api/properties/Proficiencies.js | 2 +- 5 files changed, 80 insertions(+), 10 deletions(-) create mode 100644 app/imports/api/engine/computation/computeComputation/tests/computeProficiencies.testFn.js diff --git a/app/imports/api/engine/computation/buildComputation/linkTypeDependencies.js b/app/imports/api/engine/computation/buildComputation/linkTypeDependencies.js index 80d72970..33034cf3 100644 --- a/app/imports/api/engine/computation/buildComputation/linkTypeDependencies.js +++ b/app/imports/api/engine/computation/buildComputation/linkTypeDependencies.js @@ -272,6 +272,9 @@ function linkProficiencies(dependencyGraph, prop, computation) { // The stats depend on the proficiency if (prop.inactive) return; if (prop.targetByTags) { + // Tag targeted proficiencies depend on the creature's proficiencyBonus, + // since they add it directly to the targeted field + dependencyGraph.addLink(prop._id, 'proficiencyBonus', 'skillProficiencyBonus'); getEffectTagTargets(prop, computation).forEach(targetId => { const targetProp = computation.propsById[targetId]; if ( diff --git a/app/imports/api/engine/computation/computeComputation/computeByType/computeCalculation.js b/app/imports/api/engine/computation/computeComputation/computeByType/computeCalculation.js index 3bd59ab4..de395906 100644 --- a/app/imports/api/engine/computation/computeComputation/computeByType/computeCalculation.js +++ b/app/imports/api/engine/computation/computeComputation/computeByType/computeCalculation.js @@ -61,8 +61,7 @@ function aggregateCalculationProficiencies(node, computation) { if (!linkedNode.data) return; // Ignore inactive props if (linkedNode.data.inactive) return; - - // Collate effects + // Collate proficiencies calcObj.proficiencies = calcObj.proficiencies || []; calcObj.proficiencies.push({ _id: linkedNode.data._id, diff --git a/app/imports/api/engine/computation/computeComputation/tests/computeProficiencies.testFn.js b/app/imports/api/engine/computation/computeComputation/tests/computeProficiencies.testFn.js new file mode 100644 index 00000000..b61395da --- /dev/null +++ b/app/imports/api/engine/computation/computeComputation/tests/computeProficiencies.testFn.js @@ -0,0 +1,64 @@ +import { buildComputationFromProps } from '/imports/api/engine/computation/buildCreatureComputation.js'; +import { assert } from 'chai'; +import computeCreatureComputation from '../../computeCreatureComputation.js'; +import clean from '../../utility/cleanProp.testFn.js'; + +export default function () { + const computation = buildComputationFromProps(testProperties); + computeCreatureComputation(computation); + const prop = id => computation.propsById[id]; + assert.equal( + prop('strengthId').value, 8, + 'The proficiency bonus should not change the strength score' + ); + assert.equal( + prop('strengthId').modifier, -1, + 'The proficiency bonus should not change the strength modifier' + ); + assert.exists(prop('actionId').attackRoll.proficiencies, 'The proficiency aggregator should be here') + assert.exists(prop('actionId').attackRoll.proficiencies[0], 'The proficiency should be here') + // attack roll = strength.mod + proficiencyBonus/2 rounded down + // = -1 + 13/2 = -1 + 6 = 5 + assert.equal( + prop('actionId').attackRoll.value, 5, + 'The proficiency should apply correctly to modify the attack roll' + ); +} + +var testProperties = [ + clean({ + _id: 'strengthId', + variableName: 'strength', + type: 'attribute', + attributeType: 'ability', + baseValue: { + calculation: '8' + }, + }), + clean({ + _id: 'actionId', + type: 'action', + ancestors: [{ id: 'charId' }], + attackRoll: { + calculation: 'strength.modifier', + }, + tags: ['rapier', 'martial weapon', 'weapon', 'attack'] + }), + clean({ + _id: 'profBonusId', + type: 'attribute', + variableName: 'proficiencyBonus', + ancestors: [{ id: 'charId' }], + baseValue: { + calculation: '13' + }, + }), + clean({ + _id: 'tagTargetedProficiency', + type: 'proficiency', + stats: ['strength'], // Should be ignored, we are targeting by tags + value: 0.49, + targetByTags: true, + targetTags: ['martial weapon'] + }), +]; diff --git a/app/imports/api/engine/computation/computeComputation/tests/index.js b/app/imports/api/engine/computation/computeComputation/tests/index.js index b9c8baf7..768fee2d 100644 --- a/app/imports/api/engine/computation/computeComputation/tests/index.js +++ b/app/imports/api/engine/computation/computeComputation/tests/index.js @@ -6,29 +6,33 @@ import computeInventory from './computeInventory.testFn.js'; import computeDamageMultipliers from './computeDamageMultipliers.testFn.js'; import computeEffects from './computeEffects.testFn.js'; import computeSkills from './computeSkills.testFn.js'; +import computeProficiencies from './computeProficiencies.testFn.js'; export default [{ text: 'Computes actions', fn: computeAction, -},{ +}, { text: 'Computes attributes', fn: computeAttribute, -},{ +}, { text: 'Computes classes', fn: computeClasses, -},{ +}, { text: 'Computes constants', fn: computeConstants, -},{ +}, { text: 'Computes inventory', fn: computeInventory, -},{ +}, { text: 'Computes damage multipliers', fn: computeDamageMultipliers, -},{ +}, { text: 'Computes effects', fn: computeEffects, -},{ +}, { text: 'Computes skills', fn: computeSkills, +}, { + text: 'Computes proficiencies', + fn: computeProficiencies, }]; diff --git a/app/imports/api/properties/Proficiencies.js b/app/imports/api/properties/Proficiencies.js index 8c33fefb..151f5509 100644 --- a/app/imports/api/properties/Proficiencies.js +++ b/app/imports/api/properties/Proficiencies.js @@ -35,7 +35,7 @@ let ProficiencySchema = new SimpleSchema({ optional: true, max: STORAGE_LIMITS.variableName, }, - // Which tags the effect is applied to + // Which tags the proficiency is applied to targetTags: { type: Array, optional: true,