Fix messages

- undefined dans certains cas (lancer de sort)
- promise pour la maîtrise de case humides
- ajout de message au joueur pour les jets de rencontre
- messages au joueur + GM pour les résultats de rencontres
- message au joueur + GM lors de la montée et dans les cas où les TMRs sont quittées
This commit is contained in:
Vincent Vandemeulebrouck 2020-11-29 18:06:19 +01:00
parent ec4166d2da
commit c9a214adca
4 changed files with 106 additions and 89 deletions

View File

@ -150,7 +150,6 @@ export class RdDActor extends Actor {
/* -------------------------------------------- */
async continueRoll(rollData) {
let rolled = rollData.rolled;
let result = rolled.roll;
let quality = rolled.quality
@ -1169,7 +1168,7 @@ export class RdDActor extends Actor {
isRapide: isRapide
}
let html = await renderTemplate('systems/foundryvtt-reve-de-dragon/templates/dialog-tmr.html', data );
this.currentTMR = new RdDTMRDialog(html, this, data, mode == "visu");
this.currentTMR = new RdDTMRDialog(html, this, data, mode);
this.currentTMR.render(true);
}

View File

@ -7,22 +7,17 @@ export class ChatUtility {
static chatWithRollMode(chatOptions, name) {
let rollMode = game.settings.get("core", "rollMode");
chatOptions.user = game.user._id;
switch (rollMode) {
case "blindroll": {//GM only
case "blindroll": // GM only
if (!game.user.isGM) {
ChatUtility.blindMessageToGM(chatOptions);
chatOptions = {
user: game.user._id,
whisper: [game.user._id],
content: "Message envoyé en aveugle au Gardien"
}
chatOptions.whisper = [game.user._id];
chatOptions.content = "Message envoyé en aveugle au Gardien";
}
else {
chatOptions.whisper = ChatUtility.getUsers(user => user.isGM);
}
}
break;
case "gmroll": // GM + rolling player
chatOptions.user = game.user._id;

View File

@ -21,7 +21,7 @@ const tmrConstants = {
export class RdDTMRDialog extends Dialog {
/* -------------------------------------------- */
constructor(html, actor, tmrData, viewOnly) {
constructor(html, actor, tmrData, mode) {
const dialogConf = {
title: "Terres Médianes de Rêve",
content: html,
@ -41,19 +41,23 @@ export class RdDTMRDialog extends Dialog {
this.tmrdata = duplicate(tmrData);
this.actor = actor;
this.actor.tmrApp = this; // reference this app in the actor structure
this.viewOnly = viewOnly
this.viewOnly = mode == "visu"
this.nbFatigue = this.viewOnly ? 0 : 1; // 1 premier point de fatigue du à la montée
this.rencontresExistantes = duplicate(this.actor.data.data.reve.rencontre.list);
this.sortReserves = duplicate(this.actor.data.data.reve.reserve.list);
this.allTokens = [];
this.rencontreState = 'aucune';
this.pixiApp = new PIXI.Application({ width: 720, height: 860 });
if (!this.viewOnly){
this._tellToGM(this.actor.name + " monte dans les terres médianes (" + mode + ")");
}
}
/* -------------------------------------------- */
close() {
this.actor.santeIncDec("fatigue", this.nbFatigue).then(super.close()); // moving 1 cell costs 1 fatigue
this.actor.tmrApp = undefined; // Cleanup reference
this._tellToGM(this.actor.name + " a quitté les terres médianes")
}
/* -------------------------------------------- */
@ -169,15 +173,15 @@ export class RdDTMRDialog extends Dialog {
/* -------------------------------------------- */
checkQuitterTMR() {
if ( this.actor.data.data.reve.reve.value == 0) {
ChateMessage.create( { content: "Vos Points de Rêve sont à 0 : vous quittez les Terres médianes !"} );
this._tellToGM("Vos Points de Rêve sont à 0 : vous quittez les Terres médianes !");
this.close();
}
if ( this.nbFatigue == this.actor.data.data.sante.fatigue.max ) {
ChateMessage.create({ content: "Vous vous écroulez de fatigue : vous quittez les Terres médianes !"});
this._tellToGM("Vous vous écroulez de fatigue : vous quittez les Terres médianes !");
this.close();
}
if ( this.actor.data.data.sante.vie.value == 0 ) {
ChateMessage.create({ content: "Vous n'avez plus de Points de Vie : vous quittez les Terres médianes !"});
this._tellToGM("Vous n'avez plus de Points de Vie : vous quittez les Terres médianes !");
this.close();
}
}
@ -202,14 +206,15 @@ export class RdDTMRDialog extends Dialog {
if (rolled.isEchec) {
rencontreData = await TMRUtility.processRencontreEchec(this.actor, this.currentRencontre, rolled, this);
message += rencontreData.message;
this._tellToUser("Vous avez <strong>échoué</strong> à maîtriser un " + this.currentRencontre.name + " de force " + this.currentRencontre.force
+ message);
if (this.currentRencontre.data.quitterTMR) // Selon les rencontres, quitter TMR ou pas
this._tellToGM("Vous avez <strong>échoué</strong> à maîtriser un " + this.currentRencontre.name + " de force " + this.currentRencontre.force + message);
if (this.currentRencontre.data.quitterTMR) { // Selon les rencontres, quitter TMR ou pas
this.close();
}
} else {
rencontreData = await TMRUtility.processRencontreReussite(this.actor, this.currentRencontre, rolled);
message += rencontreData.message;
this._tellToUser("Vous avez <strong>réussi</strong> à maîtriser un " + this.currentRencontre.name + " de force " + this.currentRencontre.force + message);
this._tellToGM("Vous avez <strong>réussi</strong> à maîtriser un " + this.currentRencontre.name + " de force " + this.currentRencontre.force + message);
}
await this.rencontrePostProcess( rencontreData );
@ -224,7 +229,7 @@ export class RdDTMRDialog extends Dialog {
/* -------------------------------------------- */
_tellToUser(message) {
ChatMessage.create({ content: message, user: game.user._id });
ChatMessage.create({ content: message, user: game.user._id, whisper: [game.user._id] });
}
/* -------------------------------------------- */
@ -238,15 +243,7 @@ export class RdDTMRDialog extends Dialog {
return;
}
this.currentRencontre = undefined;
let rencontre = this.rencontresExistantes.find(prev => prev.coord == coordTMR);
if (rencontre == undefined) {
let myRoll = new Roll("d7").roll();
if (myRoll.total == 7) {
rencontre = await TMRUtility.rencontreTMRRoll(coordTMR, cellDescr);
}
}
if ( TMRUtility.isForceRencontre() )
rencontre = await TMRUtility.rencontreTMRRoll(coordTMR, cellDescr);
let rencontre = await this._jetDeRencontre(coordTMR, cellDescr);
if (rencontre) { // Manages it
if (rencontre.rencontre) rencontre = rencontre.rencontre; // Manage stored rencontres
@ -267,6 +264,24 @@ export class RdDTMRDialog extends Dialog {
}
}
async _jetDeRencontre(coordTMR, cellDescr) {
let rencontre = this.rencontresExistantes.find(prev => prev.coord == coordTMR);
if (rencontre == undefined) {
let myRoll = new Roll("d7").roll();
if (myRoll.total == 7) {
rencontre = await TMRUtility.rencontreTMRRoll(coordTMR, cellDescr);
}
else {
this._tellToUser(myRoll.total + ": Pas de rencontre en " + cellDescr.label + " (" + coordTMR + ")");
}
}
if (TMRUtility.isForceRencontre()) {
return await TMRUtility.rencontreTMRRoll(coordTMR, cellDescr);
}
return rencontre;
}
/* -------------------------------------------- */
performRoll(html) {
if (this.viewOnly) {
@ -313,7 +328,7 @@ export class RdDTMRDialog extends Dialog {
// TODO: ajouter l'état général?
const etatGeneral = this.actor.data.data.compteurs.etat.value
let difficulte = draconic.data.niveau - 7;
let rolled = RdDResolutionTable.roll(carac, difficulte);
let rolled = await RdDResolutionTable.roll(carac, difficulte);
console.log("manageCaseHumide >>", rolled);
@ -363,7 +378,7 @@ export class RdDTMRDialog extends Dialog {
const declenchementSort = "Vous avez déclenché le sort <strong>" + sortReserve.sort.name
+ "</strong> en réserve en " + sortReserve.coord + " (" + TMRUtility.getTMRDescription(sortReserve.coord).label
+ ") avec " + sortReserve.sort.ptreve_reel + " points de Rêve";
this._tellToUser(declenchementSort);
this._tellToGM(declenchementSort);
this.close();
}
}
@ -436,11 +451,16 @@ export class RdDTMRDialog extends Dialog {
if ( deplacementType == 'normal') { // Pas de rencontres après un saut de type passeur/changeur/...
await myself.manageRencontre(coordTMR, cellDescr);
}
myself.manageCaseHumide(cellDescr);
await myself.manageCaseHumide(cellDescr);
await myself.declencheSortEnReserve(coordTMR);
} else if (deplacementType == 'messager') { // Dans ce cas, ouverture du lancement de sort sur la case visée
myself.actor.rollUnSort( coordTMR );
/*
TODO: si la case a un sort en réserve, lancer ce sort.
Si la case est le demi-rêve, ne pas lancer de sort.
Si un lancement de sort est en cours, trouver un moyen de réafficher cette fenêtre si on essaie de lancer un sort (ou bloquer le lancer de sort)
*/
await myself.actor.rollUnSort( coordTMR );
myself.nettoyerRencontre();
} else {

View File

@ -321,29 +321,28 @@ export class TMRUtility {
/* -------------------------------------------- */
static async rencontreTMRRoll( coordTMR, cellDescr )
{
if ( this.forceRencontre ) {
// Forced
let rencontre = duplicate(rencontresTable[this.forceRencontre.id]);
rencontre.force = this.forceRencontre.force;
rencontre.coord = coordTMR;
rencontre.nbCases = 0; // Utilisé pour les Tourbillons
return rencontre;
}
let rencontre = await this.rencontreTMRTypeCase(cellDescr.type);
//let rencontre = rencontresTable[4];
if (rencontre) {
rencontre = duplicate(rencontre);
rencontre.force = this.evaluerForceRencontre(rencontre);
rencontre.force = await this.evaluerForceRencontre(rencontre);
rencontre.coord = coordTMR;
rencontre.nbCases = 0; // Utilisé pour les Tourbillons
}
if ( this.forceRencontre ) {
// Forced
rencontre = rencontresTable[this.forceRencontre.id];
rencontre.force = this.forceRencontre.force;
rencontre.coord = coordTMR;
rencontre.nbCases = 0; // Utilisé pour les Tourbillons
}
return rencontre;
}
/* -------------------------------------------- */
static async rencontreTMRTypeCase(typeTMR, roll=undefined) {
if (!roll)
{
if (!roll) {
//roll = await RdDDice.show(new Roll("d100").evaluate()).total;
roll = new Roll("d100").roll().total;
console.log("rencontreTMRTypeCase", roll);
@ -368,19 +367,23 @@ export class TMRUtility {
* @param {*} caseName
* @param {*} roll
*/
static getRencontre( caseName, roll ) {
if (!roll) {
roll = new Roll("1d100").roll().total;
}
static async getRencontre( caseName, roll ) {
if ( !caseName) {
ChatMessage.create({ content: "Un nom de case doit être indiqué (ie /tmrr desert ou /tmrr cite)" });
return false;
}
if (roll == undefined) {
roll = new Roll("d100").evaluate().total;
}
roll = Math.max(1, Math.min(roll, 100));
let rencontre = this.rencontreTMRTypeCase(caseName, roll);
let rencontre = await this.rencontreTMRTypeCase(caseName, roll);
if (rencontre) {
let force = this.evaluerForceRencontre(rencontre);
ChatMessage.create({ content: "Rencontre en " + caseName + "(jet : " + roll + "%)<br>Vous rencontrez un " + rencontre.name + " d'une force de " + force + " Points de Rêve" });
let force = await this.evaluerForceRencontre(rencontre);
ChatMessage.create({
user: game.user._id,
whisper: [game.user._id],
content: "Rencontre en " + caseName + "(jet : " + roll + "%)<br>Vous rencontrez un " + rencontre.name + " d'une force de " + force + " Points de Rêve"});
}
return false;
}
@ -398,9 +401,9 @@ export class TMRUtility {
}
/* -------------------------------------------- */
static evaluerForceRencontre(rencontre) {
static async evaluerForceRencontre(rencontre) {
if (this.isReveDeDragon(rencontre)) {
let ddr = RdDDice.deDraconique();
let ddr = await RdDDice.deDraconique();
return ddr + 7;
}
else {
@ -416,96 +419,96 @@ export class TMRUtility {
/* -------------------------------------------- */
static async processRencontreReussite( actor, rencontre, rolled ) {
let msg = "<br>";
let message = "<br>";
let state = "aucune";
console.log("processRencontreReussite", actor, rencontre);
if (rencontre.name == "Messagers des Rêves") {
msg += "Le Messager des Rêves vous permet de lancer votre sort à XX cases !";
state = "messager";
message += "Le Messager des Rêves vous permet de lancer votre sort à " + rencontre.force + " cases !";
state = 'messager';
} else if (rencontre.name == "Passeur des Rêves") {
msg += "Le Passeur des Rêves vous permet de vous téléporter à " + rencontre.force + " cases !";
state = "passeur";
message += "Le Passeur des Rêves vous permet de vous téléporter à " + rencontre.force + " cases !";
state = 'passeur';
} else if (rencontre.name == "Fleur des Rêves") {
await actor.reveActuelIncDec( rencontre.force );
msg += "La Fleur des rêves s'évanouit en vous fournissant " + rencontre.force + " Points de Rêve";
message += "La Fleur des rêves s'évanouit en vous fournissant " + rencontre.force + " Points de Rêve";
} else if (rencontre.name == "Mangeur de Rêve") {
msg += "Ce Mangeur des Rêves disparait !"
message += "Ce Mangeur des Rêves disparait !"
} else if (rencontre.name == "Changeur de Rêve") {
msg += "Ce Changeur des Rêves vous propose de vous déplacer sur une autre case de même type."
state = "changeur";
message += "Ce Changeur des Rêves vous propose de vous déplacer sur une autre case de même type."
state = 'changeur';
} else if (rencontre.name == "Briseur de Rêve") {
msg += "Ce Briseur des Rêves disparait !"
message += "Ce Briseur des Rêves disparait !"
} else if (rencontre.name == "Reflet d'ancien Rêve") {
msg += "Ce Reflet d'ancien Rêve disparait !"
message += "Ce Reflet d'ancien Rêve disparait !"
} else if (rencontre.name == "Tourbillon blanc") {
msg += "Ce Tourbillon Blanc disparait !"
message += "Ce Tourbillon Blanc disparait !"
} else if (rencontre.name == "Tourbillon noir") {
msg += "Ce Tourbillon Noir disparait !"
message += "Ce Tourbillon Noir disparait !"
} else if (rencontre.name == "Rêve de Dragon") {
// TODO: xp particulière
msg += "Vous maîtrisez le Rêve de Dragon !"
msg += actor.appliquerReveDeDragon(rolled, rencontre.force);
message += "Vous maîtrisez le Rêve de Dragon !"
message += actor.appliquerReveDeDragon(rolled, rencontre.force);
}
return { msg: msg, state: state };
return { message: message, state: state };
}
/* -------------------------------------------- */
static async processRencontreEchec( actor, rencontre, rolled, tmrDialog ) {
let msg = "<br>";
let message = "<br>";
let state = "aucune";
if (rencontre.name == "Messagers des Rêves") {
msg += "Le Messager des Rêves s'éloigne de vous !";
message += "Le Messager des Rêves s'éloigne de vous !";
} else if (rencontre.name == "Passeur des Rêves") {
msg += "Le Passeur des Rêves s'éloigne de vous !";
message += "Le Passeur des Rêves s'éloigne de vous !";
} else if (rencontre.name == "Fleur des Rêves") {
msg += "La Fleur des rêves s'éloigne de vous et se perd dans les Terres Médianes";
message += "La Fleur des rêves s'éloigne de vous et se perd dans les Terres Médianes";
} else if (rencontre.name == "Mangeur de Rêve") {
await actor.reveActuelIncDec( -rencontre.force );
msg += "Ce Mangeur des Rêves croque votre Rêve ! Vous perdez " + rencontre.force + " points de rêve actuels, votre nouveau total est de " + actor.data.data.reve.reve.value;
message += "Ce Mangeur des Rêves croque votre Rêve ! Vous perdez " + rencontre.force + " points de rêve actuels, votre nouveau total est de " + actor.data.data.reve.reve.value;
} else if (rencontre.name == "Changeur de Rêve") {
msg += "Ce Changeur des Rêves vous déplace sur un autre case du même type.<br>"
message += "Ce Changeur des Rêves vous déplace sur un autre case du même type.<br>"
let locList = this.getLocationTypeList( actor.data.data.reve.tmrpos.coord );
let index = new Roll("1d"+locList.length + " - 1").roll().total;
let newCoord = locList[index];
tmrDialog.forceDemiRevePosition(newCoord);
let cellDescr = TMRUtility.getTMRDescription(newCoord);
msg += "Vous avez été téléporté en " + newCoord + " - " + cellDescr.label;
message += "Vous avez été téléporté en " + newCoord + " - " + cellDescr.label;
} else if (rencontre.name == "Briseur de Rêve") {
msg += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
message += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
} else if (rencontre.name == "Reflet d'ancien Rêve") {
msg += "Votre Rêve est figé, vous restez sur cette case tant que ce Reflet n'est pas vaincu!";
message += "Votre Rêve est figé, vous restez sur cette case tant que ce Reflet n'est pas vaincu!";
state = "reflet";
} else if (rencontre.name == "Tourbillon blanc") {
msg += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
message += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
state = "tourbillonblanc";
} else if (rencontre.name == "Tourbillon noir") {
msg += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
message += "Votre Rêve est Brisé, vous quittez les Terres Médianes";
state = "tourbillonnoir";
} else if (rencontre.name == "Rêve de Dragon") {
msg += "Le Rêve de Dragon tourne au cauchemar !"
msg += actor.appliquerReveDeDragon(rolled, rencontre.force);
message += "Le Rêve de Dragon tourne au cauchemar !"
message += actor.appliquerReveDeDragon(rolled, rencontre.force);
}
return { msg: msg, state: state };
return { message: message, state: state };
}
/* -------------------------------------------- */