245 lines
		
	
	
		
			9.0 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			245 lines
		
	
	
		
			9.0 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
| import { RdDRoll } from "./rdd-roll.js";
 | |
| import { Targets } from "./targets.js";
 | |
| import { ITEM_TYPES } from "./constants.js";
 | |
| import { RdDRollResult } from "./rdd-roll-result.js";
 | |
| 
 | |
| /* -------------------------------------------- */
 | |
| /* On part du principe qu'une entité démarre tjs 
 | |
| une possession via le MJ (ie un joueur ne controle pas une entité)
 | |
| Donc la compétence Possession ne peut être démarrée que par le MJ.
 | |
| */
 | |
| 
 | |
| /* -------------------------------------------- */
 | |
| export class RdDPossession {
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static init() {
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static searchPossessionFromEntite(attacker, defender) {
 | |
|     let poss = attacker.items.find(poss => poss.type == ITEM_TYPES.possession && poss.system.victime.actorid == defender.id);
 | |
|     if (!poss) {
 | |
|       poss = defender.items.find(poss => poss.type == ITEM_TYPES.possession && poss.system.victime.actorid == defender.id);
 | |
|     }
 | |
|     return poss && foundry.utils.duplicate(poss) || undefined;
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async onAttaquePossession(target, attacker, competence, suitePossession = undefined) {
 | |
|     const defender = target.actor;
 | |
|     const fromEntite = RdDPossession.searchPossessionFromEntite(attacker, defender);
 | |
|     const isNouvelle = !suitePossession && !fromEntite;
 | |
|     const possession = (suitePossession ?? fromEntite ?? (await RdDPossession.createPossession(attacker, defender)));
 | |
| 
 | |
|     RdDPossession.$updateEtatPossession(possession)
 | |
| 
 | |
|     let rollData = {
 | |
|       mode: "attaque",
 | |
|       isECNIDefender: false,
 | |
|       competence: competence,
 | |
|       possession: possession,
 | |
|       attacker: attacker,
 | |
|       defender: defender,
 | |
|       targetToken: Targets.extractTokenData(target)
 | |
|     };
 | |
|     RdDPossession.selectCompetenceDraconicOuPossession(rollData, attacker)
 | |
| 
 | |
|     await RdDPossession.$rollAttaquePossession(attacker, rollData, isNouvelle);
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async onConjurerPossession(attacker, possession) {
 | |
|     possession = foundry.utils.duplicate(possession);
 | |
|     RdDPossession.$updateEtatPossession(possession)
 | |
| 
 | |
|     const defender = game.actors.get(possession.system.entite.actorid);
 | |
|     let rollData = {
 | |
|       mode: "attaque",
 | |
|       isECNIDefender: true,
 | |
|       possession: possession,
 | |
|       attacker: attacker,
 | |
|       defender: defender,
 | |
|     };
 | |
|     RdDPossession.selectCompetenceDraconicOuPossession(rollData, attacker)
 | |
| 
 | |
|     await RdDPossession.$rollAttaquePossession(attacker, rollData);
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async onDefensePossession(attackerId, defenderId, possessionId) {
 | |
|     let attacker = game.actors.get(attackerId)
 | |
|     let possession = attacker?.getPossession(possessionId)
 | |
|     defenderId = defenderId ?? possession?.system.entite.actorid ?? undefined
 | |
|     let defender = game.actors.get(defenderId)
 | |
|     possession = possession ?? defender?.getPossession(possessionId) ?? undefined;
 | |
| 
 | |
|     if (!possession) {
 | |
|       ui.notifications.warn("Une erreur s'est produite : Aucune possession trouvée !!")
 | |
|       return
 | |
|     }
 | |
|     possession = foundry.utils.duplicate(possession)
 | |
|     // Update for draconic roll
 | |
|     let rollData = {
 | |
|       mode: "defense",
 | |
|       isECNIDefender: defender.type == "entite",
 | |
|       possession: possession,
 | |
|       attacker: attacker,
 | |
|       defender: defender,
 | |
|     }
 | |
|     RdDPossession.selectCompetenceDraconicOuPossession(rollData, defender)
 | |
|     rollData.diffLibre = RdDPossession.getInfoAttaque(rollData).diffLibre
 | |
| 
 | |
|     await RdDPossession.$rollDefensePossession(defender, rollData);
 | |
|   }
 | |
| 
 | |
|   static selectCompetenceDraconicOuPossession(rollData, rollingActor) {
 | |
|     rollData.competence = rollingActor.getDraconicOuPossession();
 | |
|     if (rollingActor.isCreatureEntite()) {
 | |
|       const carac = rollingActor.system.carac
 | |
|       rollData.carac = carac
 | |
|       rollData.competence.system.defaut_carac = 'reve'
 | |
|       rollData.selectedCarac = carac.reve
 | |
|     }
 | |
|     else {
 | |
|       rollData.forceCarac = { 'reve-actuel': { label: "Rêve Actuel", value: rollingActor.getReveActuel() } }
 | |
|       rollData.selectedCarac = rollData.forceCarac['reve-actuel']
 | |
|       rollData.competence.system.defaut_carac = 'reve-actuel'
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async $rollAttaquePossession(attacker, rollData, isNouvelle = false) {
 | |
|     const dialog = await RdDRoll.create(attacker, rollData,
 | |
|       { html: 'systems/foundryvtt-reve-de-dragon/templates/dialog-roll-competence.hbs' },
 | |
|       {
 | |
|         name: 'jet-possession',
 | |
|         label: rollData.isECNIDefender ? 'Conjurer la possession' : 'Possession',
 | |
|         callbacks: [
 | |
|           { action: async (r) => await RdDPossession.$onRollPossession(r, isNouvelle) },
 | |
|         ]
 | |
|       });
 | |
|     dialog.render(true);
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async $onRollPossession(rollData, isNouvelle = false) {
 | |
|     rollData.possession.isSuccess = rollData.rolled.isSuccess;
 | |
|     RdDPossession.$updateEtatPossession(rollData.possession, rollData);
 | |
|     if (isNouvelle) {
 | |
|       // Creer la possession sur le defenseur
 | |
|       await rollData.defender.createEmbeddedDocuments('Item', [rollData.possession.toObject()])
 | |
|     }
 | |
|     const possession = (rollData.isECNIDefender ? rollData.attacker : rollData.defender).getPossession(rollData.possession.system.possessionid)
 | |
|     RdDPossession.storePossessionAttaque(possession, rollData)
 | |
|     await RdDRollResult.displayRollData(rollData, rollData.defender, 'chat-resultat-possession.hbs');
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async $rollDefensePossession(defender, rollData) {
 | |
|     const dialog = await RdDRoll.create(defender, rollData,
 | |
|       { html: 'systems/foundryvtt-reve-de-dragon/templates/dialog-roll-defense-possession.hbs' },
 | |
|       {
 | |
|         name: 'possession',
 | |
|         label: 'Conjurer une Possession',
 | |
|         callbacks: [
 | |
|           { action: async (r) => await RdDPossession.$onRollConjuration(r) }
 | |
|         ]
 | |
|       }
 | |
|     );
 | |
|     dialog.render(true);
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async $onRollConjuration(rollData) {
 | |
|     let victime = game.actors.get(rollData.possession.system.victime.actorid)
 | |
|     let compteur = rollData.possession.system.compteur
 | |
|     if (!rollData.rolled.isSuccess) {
 | |
|       if (rollData.isECNIDefender) {
 | |
|         compteur--
 | |
|       } else {
 | |
|         compteur++
 | |
|       }
 | |
|     }
 | |
|     const possession = victime.getPossession(rollData.possession.system.possessionid)
 | |
|     await possession.update({
 | |
|       system: {
 | |
|         compteur: compteur,
 | |
|         entite: { diffLibre: 0, finesse: false },
 | |
|         victime: { diffLibre: 0, finesse: false }
 | |
|       }
 | |
|     })
 | |
|     rollData.possession = possession
 | |
|     RdDPossession.$updateEtatPossession(rollData.possession)
 | |
| 
 | |
|     await RdDRollResult.displayRollData(rollData, rollData.attacker, 'chat-resultat-possession.hbs')
 | |
|     if (rollData.possession.isPosseder || rollData.possession.isConjurer) {
 | |
|       // conjuration
 | |
|       await victime.deleteEmbeddedDocuments("Item", [rollData.possession._id])
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static $updateEtatPossession(possession) {
 | |
|     possession.ptsConjuration = 0
 | |
|     possession.ptsPossession = 0
 | |
|     console.log("Possession", possession)
 | |
|     if (possession.system.compteur > 0) {
 | |
|       possession.ptsPossession = possession.system.compteur
 | |
|     }
 | |
|     if (possession.system.compteur < 0) {
 | |
|       possession.ptsConjuration = Math.abs(possession.system.compteur)
 | |
|     }
 | |
|     possession.isPosseder = false
 | |
|     possession.isConjurer = false
 | |
|     if (possession.ptsPossession >= 2) {
 | |
|       possession.isPosseder = true
 | |
|     }
 | |
|     if (possession.ptsConjuration >= 2) {
 | |
|       possession.isConjurer = true
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static isPossessionFinesse(rollData) {
 | |
|     return RdDPossession.getInfoAttaque(rollData).finesse
 | |
|   }
 | |
|   /* -------------------------------------------- */
 | |
|   static getInfoAttaque(rollData) {
 | |
|     return rollData.possession.system[rollData.isECNIDefender ? 'victime' : 'entite'];
 | |
|   }
 | |
|   /* -------------------------------------------- */
 | |
|   static isDefensePossession(rollData) {
 | |
|     return rollData.possession && rollData.mode == "defense"
 | |
|   }
 | |
|   /* -------------------------------------------- */
 | |
|   static storePossessionAttaque(possession, rollData = undefined) {
 | |
|     const attaquant = rollData?.isECNIDefender ? 'victime' : 'entite'
 | |
|     possession.update({
 | |
|       [`system.${attaquant}`]: {
 | |
|         diffLibre: rollData?.diffLibre ?? 0,
 | |
|         finesse: rollData?.rolled.isPart ?? false
 | |
|       }
 | |
|     })
 | |
|   }
 | |
| 
 | |
|   /* -------------------------------------------- */
 | |
|   static async createPossession(attacker, defender) {
 | |
|     return await Item.create({
 | |
|       name: "Possession en cours de " + attacker.name, type: 'possession',
 | |
|       img: "systems/foundryvtt-reve-de-dragon/icons/entites/possession2.webp",
 | |
|       system: {
 | |
|         description: "", typepossession: attacker.name,
 | |
|         possede: false,
 | |
|         possessionid: foundry.utils.randomID(16),
 | |
|         entite: { actorid: attacker.id },
 | |
|         victime: { actorid: defender.id },
 | |
|         compteur: 0
 | |
|       }
 | |
|     },
 | |
|       {
 | |
|         temporary: true
 | |
|       })
 | |
|   }
 | |
| 
 | |
| } |