MAnage spell/miracle spending points and favor/disfavor for shield rolls
Release Creation / build (release) Successful in 43s

This commit is contained in:
2026-05-10 17:49:53 +02:00
parent ac44419b7a
commit 54421e4a83
4 changed files with 85 additions and 1 deletions
+67
View File
@@ -828,6 +828,73 @@ Hooks.on("createChatMessage", async (message) => {
}
})
// Hook: deduct aether when a spell-attack or spell-power roll is posted to chat
Hooks.on("createChatMessage", async (message) => {
if (!["spell-attack", "spell-power"].includes(message.rolls[0]?.options?.rollType)) return
const actorId = message.rolls[0]?.options?.actorId
if (!actorId) return
const actor = game.actors.get(actorId)
if (!actor) return
// Only the primary controller (player owner or GM) handles this
const activePlayerOwners = game.users.filter(u => u.active && !u.isGM && actor.testUserPermission(u, "OWNER"))
const isPrimary = activePlayerOwners.length > 0
? activePlayerOwners[0].id === game.user.id
: game.user.isGM
if (!isPrimary) return
const rollTarget = message.rolls[0]?.options?.rollTarget
const spellId = rollTarget?.id || rollTarget?._id
const spell = spellId ? actor.items.get(spellId) : null
if (!spell || spell.type !== "spell") return
const cost = Number(spell.system?.cost) || 0
if (cost <= 0) return
const currentAether = Number(actor.system.aetherPoints?.value) || 0
const newAether = Math.max(0, currentAether - cost)
await actor.update({ "system.aetherPoints.value": newAether })
await ChatMessage.create({
content: `<p>🔮 <strong>${actor.name}</strong> casts <em>${spell.name}</em> — spends <strong>${cost}</strong> Aether <span style="color:#888;">(${currentAether}${newAether})</span>.</p>`,
speaker: ChatMessage.getSpeaker({ actor })
})
})
// Hook: deduct grace when a miracle-attack or miracle-power roll is posted to chat
Hooks.on("createChatMessage", async (message) => {
if (!["miracle-attack", "miracle-power"].includes(message.rolls[0]?.options?.rollType)) return
const actorId = message.rolls[0]?.options?.actorId
if (!actorId) return
const actor = game.actors.get(actorId)
if (!actor) return
const activePlayerOwners = game.users.filter(u => u.active && !u.isGM && actor.testUserPermission(u, "OWNER"))
const isPrimary = activePlayerOwners.length > 0
? activePlayerOwners[0].id === game.user.id
: game.user.isGM
if (!isPrimary) return
const rollTarget = message.rolls[0]?.options?.rollTarget
const miracleId = rollTarget?.id || rollTarget?._id
const miracle = miracleId ? actor.items.get(miracleId) : null
if (!miracle || miracle.type !== "miracle") return
const cost = Number(miracle.system?.level) || 0
if (cost <= 0) return
const currentGrace = Number(actor.system.divinityPoints?.value) || 0
const newGrace = Math.max(0, currentGrace - cost)
await actor.update({ "system.divinityPoints.value": newGrace })
await ChatMessage.create({
content: `<p>✨ <strong>${actor.name}</strong> invokes <em>${miracle.name}</em> — spends <strong>${cost}</strong> Grace <span style="color:#888;">(${currentGrace}${newGrace})</span>.</p>`,
speaker: ChatMessage.getSpeaker({ actor })
})
})
// Hook pour appliquer automatiquement les dégâts si une cible est définie
Hooks.on("createChatMessage", async (message) => {
// Vérifier si c'est un message de dégâts avec un defenderId