diff --git a/module/applications/ui/chatLog.mjs b/module/applications/ui/chatLog.mjs index 210727d7..60b6cceb 100644 --- a/module/applications/ui/chatLog.mjs +++ b/module/applications/ui/chatLog.mjs @@ -179,15 +179,15 @@ export default class DhpChatLog extends foundry.applications.sidebar.tabs.ChatLo } async onRollSimple(event, message) { - const buttonType = event.target.dataset.type ?? 'damage', - total = message.rolls.reduce((a, c) => a + Roll.fromJSON(c).total, 0), - damages = { - hitPoints: { - damageTypes: [], - roll: { total } - } - }, - targets = Array.from(game.user.targets); + const buttonType = event.target.dataset.type ?? 'damage'; + const total = message.rolls.reduce((a, c) => a + Roll.fromJSON(c).total, 0); + const damages = { + hitPoints: { + damageTypes: [], + roll: { total } + } + }; + const targets = Array.from(game.user.targets); if (targets.length === 0) return ui.notifications.info(game.i18n.localize('DAGGERHEART.UI.Notifications.noTargetsSelected')); @@ -255,7 +255,7 @@ export default class DhpChatLog extends foundry.applications.sidebar.tabs.ChatLo if (target.dataset.type === 'damage') { const { damageType, dice, result } = target.dataset; - await message.system.damage.rerollDamageDice(damageType, dice, result); + await message.system.damage.rerollDamageDie(damageType, dice, result); await message.update({ 'system.damage.types': { [damageType]: { diff --git a/module/data/chat-message/actorRoll.mjs b/module/data/chat-message/actorRoll.mjs index 002715fe..10f7ffa9 100644 --- a/module/data/chat-message/actorRoll.mjs +++ b/module/data/chat-message/actorRoll.mjs @@ -1,4 +1,5 @@ import { triggerChatRollFx } from '../../helpers/utils.mjs'; +import { ChatDamageData } from './chatDamageData.mjs'; const fields = foundry.data.fields; @@ -29,60 +30,6 @@ export const originItemField = () => actionIndex: new fields.StringField() }); -class ChatMessageRollDamage extends foundry.abstract.DataModel { - static defineSchema() { - return { - types: new fields.TypedObjectField(new fields.SchemaField({ - roll: new fields.JSONField({validate: ChatMessageRollDamage.#validateRoll}), - damageTypes: new fields.ArrayField(new fields.StringField({ choices: CONFIG.DH.GENERAL.damageTypes })) - })) - }; - } - - get active() { - return Boolean(Object.keys(this.types).length); - } - - static #validateRoll(rollJSON) { - const roll = JSON.parse(rollJSON); - if (!roll.evaluated) throw new Error('Roll objects added to ChatMessage documents must be evaluated'); - } - - prepareRolls() { - for (const key of Object.keys(this.types)) { - const type = this.types[key]; - try { - const roll = Roll.fromData(type.roll); - type.roll = roll; - type.roll.modifierTotal = CONFIG.Dice.daggerheart.DHRoll.calculateTotalModifiers(roll); - } catch {} - } - } - - async rerollDamageDice(damageType, dice, resultIndex) { - const reroll = this.types[damageType].roll; - const rerollDice = reroll.dice[dice]; - const diceResult = rerollDice.results[resultIndex]; - await rerollDice.reroll(`/r1=${diceResult.result}`); - await reroll._evaluate(); - - const rerolledResult = rerollDice.results[rerollDice.results.length - 1]; - if (rerolledResult) { - const fakeRoll = { - _evaluated: true, - dice: [new foundry.dice.terms.Die({ - ...rerollDice, - results: [rerolledResult], - total: rerolledResult.value, - faces: rerollDice.faces - })], - options: { appearance: {} } - }; - await triggerChatRollFx([fakeRoll]); - } - } -} - export default class DHActorRoll extends foundry.abstract.TypeDataModel { static defineSchema() { return { @@ -103,7 +50,7 @@ export default class DHActorRoll extends foundry.abstract.TypeDataModel { originItem: originItemField(), action: new fields.StringField() }), - damage: new fields.EmbeddedDataField(ChatMessageRollDamage), + damage: new fields.EmbeddedDataField(ChatDamageData), damageOptions: new fields.ObjectField(), costs: new fields.ArrayField(new fields.ObjectField()), successConsumed: new fields.BooleanField({ initial: false }) @@ -186,7 +133,6 @@ export default class DHActorRoll extends foundry.abstract.TypeDataModel { }); } - /* TODO: Change how damage data is stored somehow to enable better rerolling */ async getRerolledDamage() { if (!this.damage.active) return; diff --git a/module/data/chat-message/chatDamageData.mjs b/module/data/chat-message/chatDamageData.mjs new file mode 100644 index 00000000..3ba771b4 --- /dev/null +++ b/module/data/chat-message/chatDamageData.mjs @@ -0,0 +1,57 @@ +import { triggerChatRollFx } from '../../helpers/utils.mjs'; + +export class ChatDamageData extends foundry.abstract.DataModel { + static defineSchema() { + const fields = foundry.data.fields; + + return { + types: new fields.TypedObjectField(new fields.SchemaField({ + roll: new fields.JSONField({validate: ChatDamageData.#validateRoll}), + damageTypes: new fields.ArrayField(new fields.StringField({ choices: CONFIG.DH.GENERAL.damageTypes })) + })) + }; + } + + get active() { + return Boolean(Object.keys(this.types).length); + } + + static #validateRoll(rollJSON) { + const roll = JSON.parse(rollJSON); + if (!roll.evaluated) throw new Error('Roll objects added to ChatMessage documents must be evaluated'); + } + + prepareRolls() { + for (const key of Object.keys(this.types)) { + const type = this.types[key]; + try { + const roll = Roll.fromData(type.roll); + type.roll = roll; + type.roll.modifierTotal = CONFIG.Dice.daggerheart.DHRoll.calculateTotalModifiers(roll); + } catch {} + } + } + + async rerollDamageDie(damageType, dice, resultIndex) { + const reroll = this.types[damageType].roll; + const rerollDice = reroll.dice[dice]; + const diceResult = rerollDice.results[resultIndex]; + await rerollDice.reroll(`/r1=${diceResult.result}`); + await reroll._evaluate(); + + const rerolledResult = rerollDice.results[rerollDice.results.length - 1]; + if (rerolledResult) { + const fakeRoll = { + _evaluated: true, + dice: [new foundry.dice.terms.Die({ + ...rerollDice, + results: [rerolledResult], + total: rerolledResult.value, + faces: rerollDice.faces + })], + options: { appearance: {} } + }; + await triggerChatRollFx([fakeRoll]); + } + } +} \ No newline at end of file