Ragoût de Klampin #588
@ -133,7 +133,7 @@ export class RdDActorSheet extends ActorSheet {
|
||||
async _onDropItem(event, dragData) {
|
||||
const destItemId = $(event.target)?.closest('.item').attr('data-item-id')
|
||||
const dropParams = RdDSheetUtility.prepareItemDropParameters(destItemId, this.actor, dragData, this.objetVersConteneur)
|
||||
if (dropParams){
|
||||
if (dropParams) {
|
||||
const callSuper = await this.actor.processDropItem(dropParams)
|
||||
if (callSuper) {
|
||||
await super._onDropItem(event, dragData)
|
||||
@ -164,31 +164,11 @@ export class RdDActorSheet extends ActorSheet {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
RdDSheetUtility.splitItem(item, this.actor);
|
||||
});
|
||||
html.find('.item-edit').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor)
|
||||
item.sheet.render(true)
|
||||
})
|
||||
html.find('.display-label a').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item.sheet.render(true);
|
||||
});
|
||||
html.find('.item-delete').click(async event => {
|
||||
const li = RdDSheetUtility.getEventElement(event);
|
||||
const item = this.actor.getObjet(li.data("item-id"));
|
||||
RdDUtility.confirmerSuppressionItem(this, item, li);
|
||||
});
|
||||
html.find('.item-vendre').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item?.proposerVente();
|
||||
});
|
||||
html.find('.item-montrer').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item?.postItem();
|
||||
});
|
||||
html.find('.item-action').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor)
|
||||
this.actor.actionItem(item);
|
||||
});
|
||||
html.find('.item-edit').click(async event => RdDSheetUtility.getItem(event, this.actor)?.sheet.render(true))
|
||||
html.find('.item-delete').click(async event => RdDUtility.confirmerSuppressionItem(this, RdDSheetUtility.getItem(event, this.actor)));
|
||||
html.find('.item-vendre').click(async event => RdDSheetUtility.getItem(event, this.actor)?.proposerVente());
|
||||
html.find('.item-montrer').click(async event => RdDSheetUtility.getItem(event, this.actor)?.postItem());
|
||||
html.find('.item-action').click(async event => RdDSheetUtility.getItem(event, this.actor)?.actionPrincipale(this.actor));
|
||||
html.find('.subacteur-delete').click(async event => {
|
||||
const li = RdDSheetUtility.getEventElement(event);
|
||||
const actorId = li.data("actor-id");
|
||||
|
230
module/actor.js
230
module/actor.js
@ -250,7 +250,7 @@ export class RdDActor extends Actor {
|
||||
}
|
||||
/* -------------------------------------------- */
|
||||
getReveActuel() {
|
||||
switch(this.type) {
|
||||
switch (this.type) {
|
||||
case 'personnage':
|
||||
return Misc.toInt(this.system.reve?.reve?.value ?? this.carac.reve.value);
|
||||
case 'creature':
|
||||
@ -258,7 +258,7 @@ export class RdDActor extends Actor {
|
||||
return Misc.toInt(this.system.carac.reve?.value)
|
||||
case 'vehicule':
|
||||
default:
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
@ -400,8 +400,8 @@ export class RdDActor extends Actor {
|
||||
return duplicate(possessions[0]);
|
||||
}
|
||||
const draconics = [...this.getDraconicList().filter(it => it.system.niveau >= 0),
|
||||
POSSESSION_SANS_DRACONIC]
|
||||
.sort(Misc.descending(it => it.system.niveau));
|
||||
POSSESSION_SANS_DRACONIC]
|
||||
.sort(Misc.descending(it => it.system.niveau));
|
||||
return duplicate(draconics[0]);
|
||||
}
|
||||
|
||||
@ -620,18 +620,18 @@ export class RdDActor extends Actor {
|
||||
content: 'Remise à neuf de ' + this.name
|
||||
});
|
||||
const updates = {
|
||||
'system.sante.endurance.value' : this.system.sante.endurance.max
|
||||
'system.sante.endurance.value': this.system.sante.endurance.max
|
||||
};
|
||||
if (!this.isEntite([ENTITE_INCARNE, ENTITE_BLURETTE])) {
|
||||
if (this.system.blessures) {
|
||||
updates['system.blessures.legeres.liste'] = [PAS_DE_BLESSURE, PAS_DE_BLESSURE, PAS_DE_BLESSURE, PAS_DE_BLESSURE, PAS_DE_BLESSURE];
|
||||
updates['system.blessures.graves.liste'] = [PAS_DE_BLESSURE, PAS_DE_BLESSURE];
|
||||
updates['system.blessures.graves.liste'] = [PAS_DE_BLESSURE, PAS_DE_BLESSURE];
|
||||
updates['system.blessures.critiques.liste'] = [PAS_DE_BLESSURE];
|
||||
}
|
||||
updates['system.sante.vie.value'] = this.system.sante.vie.max;
|
||||
updates['system.sante.fatigue.value'] = 0;
|
||||
if (this.isPersonnage()) {
|
||||
updates['system.compteurs.ethylisme'] = { value:1, nb_doses: 0, jet_moral: false};
|
||||
updates['system.compteurs.ethylisme'] = { value: 1, nb_doses: 0, jet_moral: false };
|
||||
}
|
||||
}
|
||||
await this.update(updates);
|
||||
@ -809,8 +809,7 @@ export class RdDActor extends Actor {
|
||||
name: 'maitrise',
|
||||
label: 'Maîtriser le Rêve de Dragon',
|
||||
callbacks: [
|
||||
{ action: async r =>
|
||||
this.resultCombatReveDeDragon(r) }
|
||||
{ action: async r => this.resultCombatReveDeDragon(r) }
|
||||
]
|
||||
}
|
||||
);
|
||||
@ -829,11 +828,12 @@ export class RdDActor extends Actor {
|
||||
/* -------------------------------------------- */
|
||||
async sortMisEnReserve(sort, draconic, coord, ptreve) {
|
||||
await this.createEmbeddedDocuments("Item", [{
|
||||
type: 'sortreserve',
|
||||
name: sort.name,
|
||||
img: sort.img,
|
||||
system: { sortid: sort._id, draconic: (draconic?.name ?? sort.system.draconic), ptreve: ptreve, coord: coord, heurecible: 'Vaisseau' } }],
|
||||
{ renderSheet: false});
|
||||
type: 'sortreserve',
|
||||
name: sort.name,
|
||||
img: sort.img,
|
||||
system: { sortid: sort._id, draconic: (draconic?.name ?? sort.system.draconic), ptreve: ptreve, coord: coord, heurecible: 'Vaisseau' }
|
||||
}],
|
||||
{ renderSheet: false });
|
||||
this.currentTMR.updateTokens();
|
||||
}
|
||||
|
||||
@ -923,7 +923,7 @@ export class RdDActor extends Actor {
|
||||
return;
|
||||
}
|
||||
const xpUtilise = Math.max(0, Math.min(stress, xpRequis));
|
||||
const gainNiveau = (xpUtilise >= xpRequis || xpRequis <=0) ? 1 : 0;
|
||||
const gainNiveau = (xpUtilise >= xpRequis || xpRequis <= 0) ? 1 : 0;
|
||||
const nouveauNiveau = niveau + gainNiveau;
|
||||
const nouveauXp = gainNiveau > 0 ? Math.max(competence.system.xp - xpSuivant, 0) : (competence.system.xp + xpUtilise);
|
||||
await competence.update({
|
||||
@ -1158,7 +1158,7 @@ export class RdDActor extends Actor {
|
||||
await this.updateEmbeddedDocuments('Item', [{
|
||||
_id: conteneur.id,
|
||||
'system.contenu': [...conteneur.system.contenu, item.id]
|
||||
}]);
|
||||
}]);
|
||||
onAjouterDansConteneur(item.id, conteneur.id);
|
||||
}
|
||||
}
|
||||
@ -1209,7 +1209,7 @@ export class RdDActor extends Actor {
|
||||
const cible = this.getContenantOrParent(dest);
|
||||
const [empilable, message] = item.isInventaireEmpilable(dest);
|
||||
if (empilable) {
|
||||
await this.regrouperEquipementsSimilaires(item, dest);
|
||||
await dest.empiler(item)
|
||||
result = false;
|
||||
}
|
||||
// changer de conteneur
|
||||
@ -1309,11 +1309,6 @@ export class RdDActor extends Actor {
|
||||
return itemMap;
|
||||
}
|
||||
|
||||
async regrouperEquipementsSimilaires(item, dest) {
|
||||
await dest.quantiteIncDec(item.system.quantite);
|
||||
await item.delete();
|
||||
}
|
||||
|
||||
isSurenc() {
|
||||
return this.isPersonnage() ? (this.computeMalusSurEncombrement() < 0) : false
|
||||
}
|
||||
@ -1374,8 +1369,8 @@ export class RdDActor extends Actor {
|
||||
async computeMalusArmure() {
|
||||
if (this.isPersonnage()) {
|
||||
const malusArmure = this.filterItems(it => it.type == 'armure' && it.system.equipe)
|
||||
.map(it => it.system.malus ?? 0)
|
||||
.reduce(Misc.sum(), 0);
|
||||
.map(it => it.system.malus ?? 0)
|
||||
.reduce(Misc.sum(), 0);
|
||||
// Mise à jour éventuelle du malus armure
|
||||
if (this.system.attributs?.malusarmure?.value != malusArmure) {
|
||||
await this.updateAttributeValue("malusarmure", malusArmure);
|
||||
@ -1568,7 +1563,7 @@ export class RdDActor extends Actor {
|
||||
async deleteTMRRencontreAtPosition() {
|
||||
const demiReve = this.getDemiReve()
|
||||
let rencontreIds = this.items.filter(it => it.type == 'rencontre' && it.system.coord == demiReve).map(it => it.id);
|
||||
if (rencontreIds.length>0) {
|
||||
if (rencontreIds.length > 0) {
|
||||
await this.deleteEmbeddedDocuments('Item', rencontreIds);
|
||||
}
|
||||
}
|
||||
@ -1576,7 +1571,7 @@ export class RdDActor extends Actor {
|
||||
/* -------------------------------------------- */
|
||||
async addTMRRencontre(currentRencontre) {
|
||||
const toCreate = currentRencontre.toObject();
|
||||
console.log('actor.addTMRRencontre(', toCreate,')');
|
||||
console.log('actor.addTMRRencontre(', toCreate, ')');
|
||||
this.createEmbeddedDocuments('Item', [toCreate]);
|
||||
}
|
||||
|
||||
@ -1813,7 +1808,7 @@ export class RdDActor extends Actor {
|
||||
const value = this.system.etat[name].value;
|
||||
const max = this.system.etat[name].max;
|
||||
const newValue = value + inc;
|
||||
if (0 <= newValue && newValue <=max) {
|
||||
if (0 <= newValue && newValue <= max) {
|
||||
await this.update({ [`system.etat.${name}.value`]: newValue })
|
||||
}
|
||||
}
|
||||
@ -1949,25 +1944,33 @@ export class RdDActor extends Actor {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async actionItem(item, onActionItem = async () => { }) {
|
||||
if (!item.getActionPrincipale()) return;
|
||||
switch (item.type) {
|
||||
case 'nourritureboisson': return await this.actionNourritureboisson(item, onActionItem);
|
||||
case 'potion': return await this.consommerPotion(item, onActionItem);
|
||||
case 'livre': return await this.actionLire(item);
|
||||
case 'conteneur': return await item.sheet.render(true);
|
||||
case 'herbe': {
|
||||
if (item.isHerbeAPotion()) {
|
||||
return this.dialogFabriquerPotion(item);
|
||||
}
|
||||
return;
|
||||
}
|
||||
case 'queue': case 'ombre': return await this.actionRefoulement(item);
|
||||
}
|
||||
item.actionPrincipale(this, onActionItem);
|
||||
}
|
||||
|
||||
async actionNourritureboisson(item, onActionItem) {
|
||||
const dialog = await DialogConsommer.create(this, item, onActionItem);
|
||||
dialog.render(true);
|
||||
switch (item.isComestible()) {
|
||||
case 'brut': {
|
||||
let d = new Dialog({
|
||||
title: "Nourriture brute",
|
||||
content: `Que faire de votre ${item.name}`,
|
||||
buttons: {
|
||||
'cuisiner': { icon: '<i class="fas fa-check"></i>', label: 'Cuisiner', callback: async () => await this.preparerNourriture(item) },
|
||||
'manger': { icon: '<i class="fas fa-check"></i>', label: 'Manger cru', callback: async () => await this.mangerNourriture(item, onActionItem) }
|
||||
}
|
||||
});
|
||||
d.render(true);
|
||||
return true;
|
||||
}
|
||||
case 'pret':
|
||||
await this.mangerNourriture(item, onActionItem);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
async mangerNourriture(item, onActionItem) {
|
||||
return (await DialogConsommer.create(this, item, onActionItem)).render(true);
|
||||
}
|
||||
|
||||
async actionLire(item) {
|
||||
@ -1976,11 +1979,18 @@ export class RdDActor extends Actor {
|
||||
await this.rollTache(tache.id);
|
||||
}
|
||||
}
|
||||
async actionHerbe(item) {
|
||||
if (item.isHerbeAPotion()) {
|
||||
return this.dialogFabriquerPotion(item);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async consommer(item, choix) {
|
||||
switch (item.type) {
|
||||
case 'nourritureboisson':
|
||||
case 'herbe': case 'faune':
|
||||
return await this.consommerNourritureboisson(item.id, choix);
|
||||
case 'potion':
|
||||
return await this.consommerPotion(item)
|
||||
@ -1988,18 +1998,18 @@ export class RdDActor extends Actor {
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async consommerNourritureboisson(itemId, choix = { doses: 1, seForcer: false, supprimerSiZero: false}, userId = undefined) {
|
||||
async consommerNourritureboisson(itemId, choix = { doses: 1, seForcer: false, supprimerSiZero: false }, userId = undefined) {
|
||||
if (userId != undefined && userId != game.user.id) {
|
||||
RdDActor.remoteActorCall({
|
||||
actorId: this.id,
|
||||
method: 'consommerNourritureboisson',
|
||||
args: [itemId, choix, userId]
|
||||
},
|
||||
userId)
|
||||
userId)
|
||||
return;
|
||||
}
|
||||
const item = this.getObjet(itemId)
|
||||
if (item.type != 'nourritureboisson') {
|
||||
if (!item.isComestible()) {
|
||||
return;
|
||||
}
|
||||
if (choix.doses > item.system.quantite) {
|
||||
@ -2297,9 +2307,9 @@ export class RdDActor extends Actor {
|
||||
if (xpData) {
|
||||
const content = await renderTemplate(`systems/foundryvtt-reve-de-dragon/templates/chat-actor-gain-xp.html`, xpData);
|
||||
if (hideChatMessage) {
|
||||
ChatUtility.blindMessageToGM({ content: content});
|
||||
ChatUtility.blindMessageToGM({ content: content });
|
||||
}
|
||||
else{
|
||||
else {
|
||||
ChatMessage.create({
|
||||
whisper: ChatUtility.getWhisperRecipientsAndGMs(this.name),
|
||||
content: content
|
||||
@ -2583,7 +2593,7 @@ export class RdDActor extends Actor {
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async rollCompetence(idOrName, options = {tryTarget: true}) {
|
||||
async rollCompetence(idOrName, options = { tryTarget: true }) {
|
||||
let rollData = {
|
||||
carac: this.system.carac,
|
||||
competence: this.getCompetence(idOrName)
|
||||
@ -2591,14 +2601,14 @@ export class RdDActor extends Actor {
|
||||
if (rollData.competence.type == 'competencecreature') {
|
||||
if (rollData.competence.system.iscombat && options.tryTarget && Targets.hasTargets()) {
|
||||
Targets.selectOneToken(target => {
|
||||
if (rollData.competence.system.ispossession) {
|
||||
RdDPossession.onAttaquePossession(target, this, rollData.competence)
|
||||
}
|
||||
else {
|
||||
const arme = RdDItemCompetenceCreature.armeNaturelle(rollData.competence)
|
||||
RdDCombat.rddCombatTarget(target, this).attaque(competence, arme)
|
||||
}
|
||||
});
|
||||
if (rollData.competence.system.ispossession) {
|
||||
RdDPossession.onAttaquePossession(target, this, rollData.competence)
|
||||
}
|
||||
else {
|
||||
const arme = RdDItemCompetenceCreature.armeNaturelle(rollData.competence)
|
||||
RdDCombat.rddCombatTarget(target, this).attaque(competence, arme)
|
||||
}
|
||||
});
|
||||
return;
|
||||
}
|
||||
// Transformer la competence de créature
|
||||
@ -2705,14 +2715,15 @@ export class RdDActor extends Actor {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async _rollArt(artData, selected, oeuvre, callBackResult = r => this._resultArt(r)) {
|
||||
oeuvre.system.niveau = oeuvre.system.niveau ?? 0;
|
||||
mergeObject(artData,
|
||||
{
|
||||
oeuvre: oeuvre,
|
||||
art: oeuvre.type,
|
||||
competence: duplicate(this.getCompetence(artData.compName ?? oeuvre.system.competence ?? artData.art)),
|
||||
diffLibre: - (oeuvre.system.niveau ?? 0),
|
||||
diffLibre: - oeuvre.system.niveau,
|
||||
diffConditions: 0,
|
||||
use: { libre: false, conditions: true },
|
||||
use: { libre: false, conditions: true, surenc: false },
|
||||
selectedCarac: duplicate(this.system.carac[selected])
|
||||
},
|
||||
{ overwrite: false });
|
||||
@ -2721,8 +2732,6 @@ export class RdDActor extends Actor {
|
||||
artData.forceCarac = {};
|
||||
artData.forceCarac[selected] = duplicate(this.system.carac[selected]);
|
||||
}
|
||||
console.log("rollArt !!!", artData);
|
||||
|
||||
const dialog = await RdDRoll.create(this, artData,
|
||||
{ html: `systems/foundryvtt-reve-de-dragon/templates/dialog-roll-${oeuvre.type}.html` },
|
||||
{
|
||||
@ -2739,8 +2748,9 @@ export class RdDActor extends Actor {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async _resultArt(artData) {
|
||||
const baseQualite = (artData.rolled.isSuccess ? artData.oeuvre.system.niveau : artData.competence.system.niveau);
|
||||
artData.qualiteFinale = Math.min(baseQualite, artData.oeuvre.system.niveau) + artData.rolled.ptQualite;
|
||||
const niveau = artData.oeuvre.system.niveau ?? 0;
|
||||
const baseQualite = (artData.rolled.isSuccess ? niveau : artData.competence.system.niveau);
|
||||
artData.qualiteFinale = Math.min(baseQualite, niveau) + artData.rolled.ptQualite;
|
||||
|
||||
await RdDResolutionTable.displayRollData(artData, this.name, `chat-resultat-${artData.art}.html`);
|
||||
}
|
||||
@ -2794,32 +2804,64 @@ export class RdDActor extends Actor {
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async _resultRecetteCuisine(artData) {
|
||||
const baseQualite = (artData.rolled.isSuccess ? artData.oeuvre.system.niveau : artData.competence.system.niveau);
|
||||
const sust = artData.oeuvre.system.sust * artData.proportions;
|
||||
artData.qualiteFinale = Math.min(baseQualite, artData.oeuvre.system.niveau) + artData.rolled.ptQualite;
|
||||
artData.exotismeFinal = Math.min(Math.min(artData.qualiteFinale, artData.oeuvre.system.exotisme ?? 0), 0);
|
||||
//console.log("OEUVRE", artData.art, artData)
|
||||
async _resultRecetteCuisine(cuisine) {
|
||||
const niveauRecette = cuisine.oeuvre.system.niveau ?? 0;
|
||||
const baseQualite = (cuisine.rolled.isSuccess ? niveauRecette : cuisine.competence.system.niveau);
|
||||
cuisine.qualiteFinale = Math.min(baseQualite, niveauRecette) + cuisine.rolled.ptQualite;
|
||||
cuisine.exotismeFinal = Math.min(Math.min(cuisine.qualiteFinale, cuisine.oeuvre.system.exotisme ?? 0), 0);
|
||||
cuisine.sust = cuisine.oeuvre.system.sust * Math.min(cuisine.proportions, cuisine.proportionsMax ?? cuisine.proportions)
|
||||
const platCuisine = {
|
||||
name: artData.oeuvre.name,
|
||||
name: cuisine.oeuvre.name,
|
||||
type: 'nourritureboisson',
|
||||
img: 'systems/foundryvtt-reve-de-dragon/icons/objets/provision_cuite.webp',
|
||||
system: {
|
||||
"description": artData.oeuvre.system.description,
|
||||
"sust": Math.min(sust, 1),
|
||||
"qualite": artData.qualiteFinale,
|
||||
"exotisme": artData.exotismeFinal,
|
||||
"description": cuisine.oeuvre.system.description,
|
||||
"sust": 1,
|
||||
"qualite": cuisine.qualiteFinale,
|
||||
"exotisme": cuisine.exotismeFinal,
|
||||
"encombrement": 0.1,
|
||||
"quantite": Math.max(1, Math.floor(sust)),
|
||||
"cout": Math.max(artData.qualiteFinale) * 0.01
|
||||
"quantite": Math.max(1, Math.floor(cuisine.sust)),
|
||||
"cout": Math.max(cuisine.qualiteFinale) * 0.01
|
||||
}
|
||||
};
|
||||
if (artData.ajouterEquipement) {
|
||||
}
|
||||
if (cuisine.ajouterEquipement) {
|
||||
await this.createEmbeddedDocuments('Item', [platCuisine]);
|
||||
ui.notifications.info(`${platCuisine.system.quantite} rations de ${platCuisine.name} ont été ajoutés à votre équipement`);
|
||||
}
|
||||
artData.platCuisine = platCuisine;
|
||||
await RdDResolutionTable.displayRollData(artData, this.name, `chat-resultat-${artData.art}.html`);
|
||||
cuisine.platCuisine = platCuisine;
|
||||
await RdDResolutionTable.displayRollData(cuisine, this.name, `chat-resultat-${cuisine.art}.html`);
|
||||
}
|
||||
|
||||
async preparerNourriture(item) {
|
||||
if (item.isComestible() == 'brut') {
|
||||
const nourriture = {
|
||||
name: 'Plat de ' + item.name,
|
||||
type: 'recettecuisine',
|
||||
img: item.img,
|
||||
system: {
|
||||
sust: 1,
|
||||
exotisme: item.system.exotisme,
|
||||
ingredients: item.name
|
||||
}
|
||||
};
|
||||
const artData = {
|
||||
verbe: 'Préparer',
|
||||
compName: 'cuisine',
|
||||
proportions: 1,
|
||||
proportionsMax: Math.min(50, item.system.sust),
|
||||
ajouterEquipement: true
|
||||
};
|
||||
await this._rollArt(artData, 'odoratgout', nourriture, async (cuisine) => {
|
||||
await this._resultRecetteCuisine(cuisine);
|
||||
const remaining = Math.max(item.system.quantite - cuisine.proportions, 0);
|
||||
if (remaining > 0) {
|
||||
await item.update({ 'system.quantite': remaining })
|
||||
}
|
||||
else {
|
||||
await this.deleteEmbeddedDocuments('Item', [item.id]);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
@ -3171,7 +3213,7 @@ export class RdDActor extends Actor {
|
||||
|
||||
const caracList = Object.entries(carac);
|
||||
let entry = Misc.findFirstLike(name, caracList, { mapper: it => it[0], description: 'caractéristique' });
|
||||
if (!entry || entry.length ==0) {
|
||||
if (!entry || entry.length == 0) {
|
||||
entry = Misc.findFirstLike(name, caracList, { mapper: it => it[1].label, description: 'caractéristique' });
|
||||
}
|
||||
return entry && entry.length > 0 ? carac[entry[0]] : undefined;
|
||||
@ -3207,7 +3249,7 @@ export class RdDActor extends Actor {
|
||||
ui.notifications.warn("Vous êtes déja dans les TMR....");
|
||||
return
|
||||
}
|
||||
if (mode != 'visu' && this.getEffect(STATUSES.StatusDemiReve)) {
|
||||
if (mode != 'visu' && this.getEffect(STATUSES.StatusDemiReve)) {
|
||||
ui.notifications.warn("Le joueur ou le MJ est déja dans les Terres Médianes avec ce personnage ! Visualisation uniquement");
|
||||
mode = "visu"; // bascule le mode en visu automatiquement
|
||||
}
|
||||
@ -3265,13 +3307,13 @@ export class RdDActor extends Actor {
|
||||
title: 'Ne pas utiliser les automatisation de combat',
|
||||
buttonLabel: "Pas d'automatisation",
|
||||
onAction: async () => {
|
||||
this.rollCompetence(arme.system.competence, {tryTarget: false})
|
||||
this.rollCompetence(arme.system.competence, { tryTarget: false })
|
||||
}
|
||||
});
|
||||
return;
|
||||
}
|
||||
Targets.selectOneToken(target => {
|
||||
if (Targets.isTargetEntite(target)){
|
||||
if (Targets.isTargetEntite(target)) {
|
||||
ui.notifications.warn(`Vous ne pouvez pas attaquer une entité non incarnée avec votre ${arme.name}!!!!`);
|
||||
return;
|
||||
}
|
||||
@ -3395,12 +3437,12 @@ export class RdDActor extends Actor {
|
||||
|
||||
async validerEncaissement(rollData, show) {
|
||||
if (ReglesOptionelles.isUsing('validation-encaissement-gr') && !game.user.isGM) {
|
||||
RdDActor.remoteActorCall({
|
||||
actorId: this.id,
|
||||
method: 'validerEncaissement',
|
||||
args: [rollData, show]
|
||||
});
|
||||
return;
|
||||
RdDActor.remoteActorCall({
|
||||
actorId: this.id,
|
||||
method: 'validerEncaissement',
|
||||
args: [rollData, show]
|
||||
});
|
||||
return;
|
||||
}
|
||||
const armure = await this.computeArmure(rollData);
|
||||
if (ReglesOptionelles.isUsing('validation-encaissement-gr')) {
|
||||
@ -3880,7 +3922,7 @@ export class RdDActor extends Actor {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
addSubActeur(subActor) {
|
||||
if(subActor?.id == this.id){
|
||||
if (subActor?.id == this.id) {
|
||||
ui.notifications.warn("Vous ne pouvez pas attacher un acteur à lui même")
|
||||
}
|
||||
else if (!subActor?.isOwner) {
|
||||
@ -4107,10 +4149,10 @@ export class RdDActor extends Actor {
|
||||
}
|
||||
console.log("setEffect", statusId, status)
|
||||
const effect = this.getEffect(statusId);
|
||||
if (!status && effect){
|
||||
if (!status && effect) {
|
||||
await this.deleteEmbeddedDocuments('ActiveEffect', [effect.id]);
|
||||
}
|
||||
if (status && !effect ) {
|
||||
if (status && !effect) {
|
||||
await this.createEmbeddedDocuments("ActiveEffect", [StatusEffects.status(statusId)]);
|
||||
}
|
||||
}
|
||||
@ -4136,7 +4178,6 @@ export class RdDActor extends Actor {
|
||||
await this.checkCompetenceXP(item.name, item.system.xp);
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async onCreateItem(item, options, id) {
|
||||
switch (item.type) {
|
||||
@ -4147,6 +4188,7 @@ export class RdDActor extends Actor {
|
||||
await this.onCreateOwnedDraconique(item, options, id);
|
||||
break;
|
||||
}
|
||||
await item.onCreateDecoupeComestible(this);
|
||||
}
|
||||
|
||||
async onDeleteItem(item, options, id) {
|
||||
|
@ -2,13 +2,13 @@ import { Misc } from "./misc.js";
|
||||
|
||||
export class DialogConsommer extends Dialog {
|
||||
|
||||
static async create(actor, item, onActionItem = async ()=>{}) {
|
||||
static async create(actor, item, onActionItem = async () => { }) {
|
||||
const consommerData = DialogConsommer.prepareData(actor, item);
|
||||
const html = await renderTemplate('systems/foundryvtt-reve-de-dragon/templates/dialog-item-consommer.html', consommerData);
|
||||
return new DialogConsommer(actor, item, consommerData, html, onActionItem)
|
||||
}
|
||||
|
||||
constructor(actor, item, consommerData, html, onActionItem = async ()=>{}) {
|
||||
constructor(actor, item, consommerData, html, onActionItem = async () => { }) {
|
||||
const options = { classes: ["dialogconsommer"], width: 350, height: 'fit-content', 'z-index': 99999 };
|
||||
let conf = {
|
||||
title: consommerData.title,
|
||||
@ -18,7 +18,8 @@ export class DialogConsommer extends Dialog {
|
||||
[consommerData.buttonName]: {
|
||||
label: consommerData.buttonName, callback: async it => {
|
||||
await this.onConsommer(it);
|
||||
await onActionItem();}
|
||||
await onActionItem();
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
@ -38,9 +39,8 @@ export class DialogConsommer extends Dialog {
|
||||
|
||||
/* -------------------------------------------- */
|
||||
static prepareData(actor, item) {
|
||||
item = duplicate(item);
|
||||
let consommerData = {
|
||||
item: item,
|
||||
item: duplicate(item),
|
||||
cuisine: actor.getCompetence('cuisine'),
|
||||
choix: {
|
||||
doses: 1,
|
||||
@ -48,25 +48,47 @@ export class DialogConsommer extends Dialog {
|
||||
}
|
||||
}
|
||||
switch (item.type) {
|
||||
case 'herbe': case 'faune':
|
||||
consommerData.title = 'Manger une portion crue: ';
|
||||
consommerData.buttonName = "Manger";
|
||||
break;
|
||||
case 'nourritureboisson':
|
||||
consommerData.title = item.system.boisson ? `${item.name}: boire une dose` : `${item.name}: manger une portion`;
|
||||
consommerData.title = item.system.boisson ? 'Boire une dose: ' : 'Manger une portion: ';
|
||||
consommerData.buttonName = item.system.boisson ? "Boire" : "Manger";
|
||||
break;
|
||||
case 'potion':
|
||||
consommerData.title = `${item.name}: boire la potion`;
|
||||
consommerData.title = 'Boire la potion: ';
|
||||
consommerData.buttonName = "Boire";
|
||||
break;
|
||||
}
|
||||
DialogConsommer.calculDoses(consommerData, consommerData.choix.doses)
|
||||
consommerData.title += item.name;
|
||||
DialogConsommer.calculDoses(consommerData, item)
|
||||
return consommerData;
|
||||
}
|
||||
|
||||
static calculDoses(consommer) {
|
||||
static calculDoses(consommer, item) {
|
||||
const doses = consommer.choix.doses;
|
||||
consommer.totalSust = Misc.keepDecimals(doses * (consommer.item.system.sust ?? 0), 2);
|
||||
consommer.totalDesaltere = consommer.item.system.boisson
|
||||
? Misc.keepDecimals(doses * (consommer.item.system.desaltere ?? 0), 2)
|
||||
: 0;
|
||||
switch (item.type) {
|
||||
case 'herbe': case 'faune':
|
||||
consommer.totalSust = doses;
|
||||
consommer.totalDesaltere = 0;
|
||||
consommer.choix.sust = 1;
|
||||
consommer.choix.quantite = 0;
|
||||
consommer.choix.encombrement = Misc.keepDecimals(consommer.item.system.encombrement / item.system.sust, 2);
|
||||
return;
|
||||
case 'nourritureboisson':
|
||||
consommer.choix.sust = consommer.item.system.sust;
|
||||
consommer.choix.quantite = doses;
|
||||
consommer.choix.encombrement = 0
|
||||
consommer.totalSust = Misc.keepDecimals(doses * (consommer.item.system.sust ?? 0), 2);
|
||||
consommer.totalDesaltere = consommer.item.system.boisson
|
||||
? Misc.keepDecimals(doses * (consommer.item.system.desaltere ?? 0), 2)
|
||||
: 0;
|
||||
break;
|
||||
case 'potion':
|
||||
consommer.totalSust = 0
|
||||
consommer.totalDesaltere = 0
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -84,7 +106,7 @@ export class DialogConsommer extends Dialog {
|
||||
|
||||
selectDoses(event) {
|
||||
this.consommerData.choix.doses = Number(event.currentTarget.value);
|
||||
DialogConsommer.calculDoses(this.consommerData);
|
||||
DialogConsommer.calculDoses(this.consommerData, this.item);
|
||||
$(".total-sust").text(this.consommerData.totalSust);
|
||||
$(".total-desaltere").text(this.consommerData.totalDesaltere);
|
||||
}
|
||||
|
@ -281,4 +281,36 @@ export class RdDItemCompetence extends Item {
|
||||
return duplicate(limitesArchetypes);
|
||||
}
|
||||
|
||||
static triVisible(competences) {
|
||||
return competences.filter(it => it.system.isVisible)
|
||||
.sort((a, b) => RdDItemCompetence.compare(a,b))
|
||||
}
|
||||
|
||||
static $positionTri(comp) {
|
||||
if (comp.name.startsWith("Survie")) {
|
||||
if (comp.name.includes("Cité")) return 0;
|
||||
if (comp.name.includes("Extérieur")) return 1;
|
||||
return 2;
|
||||
}
|
||||
if (comp.system.categorie.startsWith("melee")) {
|
||||
if (comp.name.includes("Corps")) return 0;
|
||||
if (comp.name.includes("Dague")) return 1;
|
||||
if (comp.name.includes("Esquive")) return 2;
|
||||
return 3;
|
||||
}
|
||||
if (comp.system.categorie.startsWith("draconic")) {
|
||||
if (comp.name.includes("Oniros")) return 0;
|
||||
if (comp.name.includes("Hypnos")) return 1;
|
||||
if (comp.name.includes("Narcos")) return 2;
|
||||
if (comp.name.includes("Thanatos")) return 3;
|
||||
return 4;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static compare(a,b) {
|
||||
const diff = RdDItemCompetence.$positionTri(a) - RdDItemCompetence.$positionTri(b);
|
||||
return diff ? diff : a.name.localeCompare(b.name);
|
||||
}
|
||||
|
||||
}
|
@ -11,6 +11,7 @@ export class RdDConteneurItemSheet extends RdDItemSheet {
|
||||
if (this.actor) {
|
||||
this.prepareConteneurData(formData);
|
||||
}
|
||||
return formData;
|
||||
}
|
||||
|
||||
activateListeners(html) {
|
||||
|
@ -26,21 +26,22 @@ export class RdDFauneItemSheet extends RdDItemSheet {
|
||||
EnvironmentSheetHelper.activateListeners(this, html);
|
||||
|
||||
html.find("a.linked-actor-delete").click(event => this.onDeleteLinkedActor());
|
||||
|
||||
html.find("a.preparer-nourriture").click(event => this.preparerNourriture(event));
|
||||
html.find("a.manger-nourriture").click(event => this.mangerNourriture(event));
|
||||
}
|
||||
|
||||
async _onDropActor(event, dragData) {
|
||||
console.log('faune:dropActor', event, dragData)
|
||||
const actor = fromUuidSync(dragData.uuid);
|
||||
if (actor?.pack) {
|
||||
const linkedActor = fromUuidSync(dragData.uuid);
|
||||
if (linkedActor?.pack) {
|
||||
this.item.update({
|
||||
'system.actor.pack': actor.pack,
|
||||
'system.actor.id': actor._id,
|
||||
'system.actor.name': actor.name
|
||||
'system.actor.pack': linkedActor.pack,
|
||||
'system.actor.id': linkedActor._id,
|
||||
'system.actor.name': linkedActor.name
|
||||
});
|
||||
}
|
||||
else {
|
||||
ui.notifications.warn(`${actor.name} ne provient pas d'eun compendium.
|
||||
ui.notifications.warn(`${linkedActor.name} ne provient pas d'un compendium.
|
||||
<br>Choisissez une créature du compendium pour représenter un élément de faune générique`)
|
||||
}
|
||||
}
|
||||
@ -51,4 +52,16 @@ export class RdDFauneItemSheet extends RdDItemSheet {
|
||||
'system.actor.name': ''
|
||||
});
|
||||
}
|
||||
|
||||
async preparerNourriture(event) {
|
||||
if (this.actor) {
|
||||
await this.actor.preparerNourriture(this.item);
|
||||
}
|
||||
}
|
||||
async mangerNourriture(event) {
|
||||
if (this.actor) {
|
||||
await this.actor.mangerNourriture(this.item);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -99,7 +99,8 @@ export class RdDItemSheet extends ItemSheet {
|
||||
cssClass: this.isEditable ? "editable" : "locked",
|
||||
isSoins: false,
|
||||
description: await TextEditor.enrichHTML(this.item.system.description, { async: true }),
|
||||
descriptionmj: await TextEditor.enrichHTML(this.item.system.descriptionmj, { async: true })
|
||||
descriptionmj: await TextEditor.enrichHTML(this.item.system.descriptionmj, { async: true }),
|
||||
isComestible: this.item.isComestible()
|
||||
}
|
||||
|
||||
const competences = await SystemCompendiums.getCompetences(this.actor?.type);
|
||||
@ -166,7 +167,6 @@ export class RdDItemSheet extends ItemSheet {
|
||||
this.form.ondragstart = (event) => this._onDragStart(event);
|
||||
this.form.ondrop = (event) => this._onDrop(event);
|
||||
|
||||
|
||||
// Select competence categorie
|
||||
html.find(".categorie").change(event => this._onSelectCategorie(event));
|
||||
|
||||
@ -182,60 +182,34 @@ export class RdDItemSheet extends ItemSheet {
|
||||
this.dateUpdated = game.system.rdd.calendrier.getIndexFromDate(jour, mois);
|
||||
});
|
||||
|
||||
html.find('.creer-tache-livre').click((event) => {
|
||||
let actorId = event.currentTarget.attributes['data-actor-id'].value;
|
||||
let actor = game.actors.get(actorId);
|
||||
actor.creerTacheDepuisLivre(this.item);
|
||||
});
|
||||
html.find('.consommer-potion').click((event) => {
|
||||
let actorId = event.currentTarget.attributes['data-actor-id'].value;
|
||||
let actor = game.actors.get(actorId);
|
||||
actor.consommerPotion(this.item);
|
||||
});
|
||||
html.find('.creer-potion-base').click((event) => {
|
||||
let actorId = event.currentTarget.attributes['data-actor-id'].value;
|
||||
let actor = game.actors.get(actorId);
|
||||
actor.dialogFabriquerPotion(this.item);
|
||||
});
|
||||
html.find('.creer-tache-livre').click((event) => this._getEventActor(event).creerTacheDepuisLivre(this.item));
|
||||
html.find('.consommer-potion').click((event) => this._getEventActor(event).consommerPotion(this.item));
|
||||
html.find('.creer-potion-base').click((event) => this._getEventActor(event).dialogFabriquerPotion(this.item));
|
||||
|
||||
html.find('.alchimie-tache a').click((event) => {
|
||||
let actorId = event.currentTarget.attributes['data-actor-id'].value;
|
||||
let recetteId = event.currentTarget.attributes['data-recette-id'].value;
|
||||
let tacheName = event.currentTarget.attributes['data-alchimie-tache'].value;
|
||||
let tacheData = event.currentTarget.attributes['data-alchimie-data'].value;
|
||||
let actor = game.actors.get(actorId);
|
||||
let actor = this._getEventActor(event);
|
||||
if (actor) {
|
||||
let recetteId = event.currentTarget.attributes['data-recette-id'].value;
|
||||
let tacheName = event.currentTarget.attributes['data-alchimie-tache'].value;
|
||||
let tacheData = event.currentTarget.attributes['data-alchimie-data'].value;
|
||||
actor.effectuerTacheAlchimie(recetteId, tacheName, tacheData);
|
||||
} else {
|
||||
ui.notifications.info("Impossible trouver un acteur pour réaliser cette tache Alchimique.");
|
||||
}
|
||||
});
|
||||
|
||||
html.find('.item-split').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
await RdDSheetUtility.splitItem(item, this.actor, async () => itemSheetDialog.render(true));
|
||||
});
|
||||
html.find('.item-edit').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item.sheet.render(true);
|
||||
});
|
||||
html.find('.item-delete').click(async event => {
|
||||
const li = RdDSheetUtility.getEventElement(event);
|
||||
const item = this.actor.getObjet(li.data("item-id"));
|
||||
RdDUtility.confirmerSuppressionItem(this, item, li);
|
||||
});
|
||||
html.find('.item-vendre').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item?.proposerVente();
|
||||
});
|
||||
html.find('.item-montrer').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
item?.postItem();
|
||||
});
|
||||
html.find('.item-action').click(async event => {
|
||||
const item = RdDSheetUtility.getItem(event, this.actor);
|
||||
this.actor.actionItem(item, async () => itemSheetDialog.render(true));
|
||||
});
|
||||
html.find('.item-split').click(async event => RdDSheetUtility.splitItem(RdDSheetUtility.getItem(event, this.actor), this.actor, async () => itemSheetDialog.render(true)));
|
||||
html.find('.item-edit').click(async event => RdDSheetUtility.getItem(event, this.actor)?.sheet.render(true));
|
||||
html.find('.item-delete').click(async event => RdDUtility.confirmerSuppressionItem(this, RdDSheetUtility.getItem(event, this.actor)));
|
||||
html.find('.item-vendre').click(async event => RdDSheetUtility.getItem(event, this.actor)?.proposerVente());
|
||||
html.find('.item-montrer').click(async event => RdDSheetUtility.getItem(event, this.actor)?.postItem());
|
||||
html.find('.item-action').click(async event => RdDSheetUtility.getItem(event, this.actor)?.actionPrincipale(this.actor, async () => itemSheetDialog.render(true)));
|
||||
}
|
||||
|
||||
_getEventActor(event) {
|
||||
let actorId = event.currentTarget.attributes['data-actor-id'].value;
|
||||
let actor = game.actors.get(actorId);
|
||||
return actor;
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
|
126
module/item.js
126
module/item.js
@ -1,5 +1,6 @@
|
||||
import { DialogItemVente } from "./dialog-item-vente.js";
|
||||
import { Grammar } from "./grammar.js";
|
||||
import { Misc } from "./misc.js";
|
||||
import { RdDHerbes } from "./rdd-herbes.js";
|
||||
import { RdDUtility } from "./rdd-utility.js";
|
||||
|
||||
@ -91,10 +92,16 @@ export class RdDItem extends Item {
|
||||
return true;
|
||||
}
|
||||
|
||||
static getUniteQuantite(type) {
|
||||
switch (type) {
|
||||
getUniteQuantite() {
|
||||
switch (this.type) {
|
||||
case "monnaie": return "(Pièces)"
|
||||
case "herbe": return "(Brins)"
|
||||
case "herbe":
|
||||
switch (this.system.categorie) {
|
||||
case 'Alchimie': case 'Repos': case 'Soin':
|
||||
return "(Brins)"
|
||||
case 'Cuisine': return '';
|
||||
}
|
||||
return '';
|
||||
case "ingredient": return "(Pépins ou Brins)"
|
||||
}
|
||||
return '';
|
||||
@ -165,9 +172,25 @@ export class RdDItem extends Item {
|
||||
return !this.isConteneur() || (this.system.contenu?.length ?? 0) == 0;
|
||||
}
|
||||
|
||||
isAlcool() {
|
||||
return this.type == 'nourritureboisson' && this.system.boisson && this.system.alcoolise;
|
||||
isNourritureBoisson() {
|
||||
return this.type == 'nourritureboisson';
|
||||
}
|
||||
|
||||
isComestible() {
|
||||
switch (this.type) {
|
||||
case 'nourritureboisson': return 'pret';
|
||||
case 'herbe':
|
||||
return this.system.categorie == 'Cuisine' && this.system.sust > 0 ? 'brut' : '';
|
||||
case 'faune':
|
||||
return this.system.sust > 0 ? 'brut' : '';
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
isAlcool() {
|
||||
return this.isNourritureBoisson() && this.system.boisson && this.system.alcoolise;
|
||||
}
|
||||
|
||||
isHerbeAPotion() {
|
||||
return this.type == 'herbe' && (this.system.categorie == 'Soin' || this.system.categorie == 'Repos');
|
||||
}
|
||||
@ -193,13 +216,22 @@ export class RdDItem extends Item {
|
||||
getEnc() {
|
||||
switch (this.type) {
|
||||
case 'herbe':
|
||||
return encBrin;
|
||||
return this.getEncHerbe();
|
||||
case 'gemme':
|
||||
return encPepin * this.system.taille;
|
||||
}
|
||||
return Math.max(this.system.encombrement ?? 0, 0);
|
||||
}
|
||||
|
||||
getEncHerbe() {
|
||||
switch (this.system.categorie) {
|
||||
case 'Repos': case 'Soin': case 'Alchimie':
|
||||
return encBrin;
|
||||
}
|
||||
return this.system.encombrement;
|
||||
|
||||
}
|
||||
|
||||
valeurTotale() {
|
||||
return this.getQuantite() * this.valeur()
|
||||
}
|
||||
@ -231,18 +263,42 @@ export class RdDItem extends Item {
|
||||
}
|
||||
|
||||
getActionPrincipale(options = { warnIfNot: true }) {
|
||||
const warn = options.warnIfNot;
|
||||
switch (this.type) {
|
||||
case 'nourritureboisson': return this._actionOrWarnQuantiteZero(this.system.boisson ? 'Boire' : 'Manger', warn);
|
||||
case 'potion': return this._actionOrWarnQuantiteZero('Boire', warn);
|
||||
case 'livre': return this._actionOrWarnQuantiteZero('Lire', warn);
|
||||
case 'conteneur': return 'Ouvrir';
|
||||
case 'herbe': return this.isHerbeAPotion() ? this._actionOrWarnQuantiteZero('Décoction', warn) : undefined;
|
||||
case 'queue': case 'ombre': return this.system.refoulement > 0 ? 'Refouler' : undefined;
|
||||
}
|
||||
if (this.actor?.isPersonnage()) {
|
||||
const warn = options.warnIfNot;
|
||||
if (this.isComestible() == 'brut') {
|
||||
return 'Utiliser';
|
||||
}
|
||||
switch (this.type) {
|
||||
case 'nourritureboisson': return this._actionOrWarnQuantiteZero(this.system.boisson ? 'Boire' : 'Manger', warn);
|
||||
case 'potion': return this._actionOrWarnQuantiteZero('Boire', warn);
|
||||
case 'livre': return this._actionOrWarnQuantiteZero('Lire', warn);
|
||||
case 'herbe': return this.isHerbeAPotion() ? this._actionOrWarnQuantiteZero('Décoction', warn) : undefined;
|
||||
case 'queue': case 'ombre': return this.system.refoulement > 0 ? 'Refouler' : undefined;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
async actionPrincipale(actor, onActionItem = async () => { }) {
|
||||
if (!this.getActionPrincipale()) {
|
||||
return;
|
||||
}
|
||||
if (await actor.actionNourritureboisson(this, onActionItem)) {
|
||||
return;
|
||||
}
|
||||
switch (this.type) {
|
||||
case 'potion': return await actor.consommerPotion(this, onActionItem);
|
||||
case 'livre': return await actor.actionLire(this);
|
||||
case 'conteneur': return await this.sheet.render(true);
|
||||
case 'herbe': return await actor.actionHerbe(this);
|
||||
case 'queue': case 'ombre': return await actor.actionRefoulement(this);
|
||||
}
|
||||
}
|
||||
|
||||
_actionOrWarnQuantiteZero(actionName, warn) {
|
||||
if ((this.system.quantite ?? 0) <= 0) {
|
||||
if (warn) {
|
||||
@ -260,6 +316,42 @@ export class RdDItem extends Item {
|
||||
await this.quantiteIncDec(-nombre, options);
|
||||
}
|
||||
|
||||
async onCreateDecoupeComestible(actor) {
|
||||
if (actor && this.isComestible() == 'brut' && this.system.sust != 1) {
|
||||
if (this.system.sust < 1) {
|
||||
await actor.updateEmbeddedDocuments('Item', [{
|
||||
_id: this.id,
|
||||
'system.sust': 0
|
||||
}])
|
||||
}
|
||||
else {
|
||||
const sust = Math.floor(this.system.sust);
|
||||
await actor.updateEmbeddedDocuments('Item', [{
|
||||
_id: this.id,
|
||||
'system.quantite': this.system.quantite * sust,
|
||||
'system.encombrement': Misc.keepDecimals(this.system.encombrement / sust, 2),
|
||||
'system.cout': Misc.keepDecimals(this.system.cout / sust, 2),
|
||||
'system.sust': 1
|
||||
}])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async empiler(item) {
|
||||
if (this.isComestible() == 'brut') {
|
||||
const sust = this.system.sust + item.system.sust;
|
||||
const encombrement = this.system.encombrement + item.system.encombrement;
|
||||
await this.update({
|
||||
"system.sust": sust,
|
||||
"system.encombrement": encombrement
|
||||
});
|
||||
}
|
||||
else {
|
||||
await this.quantiteIncDec(item.system.quantite);
|
||||
}
|
||||
await item.delete();
|
||||
}
|
||||
|
||||
async quantiteIncDec(nombre, options = { diminuerQuantite: true, supprimerSiZero: false }) {
|
||||
const quantite = Number(this.system.quantite ?? -1);
|
||||
if (quantite >= 0) {
|
||||
@ -287,7 +379,6 @@ export class RdDItem extends Item {
|
||||
if (!other || !this.isInventaire()) {
|
||||
return [false, undefined];
|
||||
}
|
||||
|
||||
if (this.system.quantite == undefined) {
|
||||
return [false, `Impossible de regrouper des ${this.type}, ils ne sont pas empilables`];
|
||||
}
|
||||
@ -298,8 +389,13 @@ export class RdDItem extends Item {
|
||||
return [false, `Impossible de regrouper ${this.name} avec ${other.name}`];
|
||||
}
|
||||
else {
|
||||
const differences = Object.entries(this.system)
|
||||
.filter(([key, value]) => !['quantite', 'cout', 'encTotal'].includes(key) && value != other.system[key]);
|
||||
const excludedProperties = ['quantite', 'cout', 'encTotal'];
|
||||
if (this.isComestible()) {
|
||||
excludedProperties.push('sust', 'encombrement');
|
||||
}
|
||||
let differences = Object.entries(this.system)
|
||||
.filter(([key, value]) => !excludedProperties.includes(key))
|
||||
.filter(([key, value]) => value != other.system[key])
|
||||
if (differences.length > 0) {
|
||||
let message = `Impossible de regrouper les ${this.type} ${this.name}: `;
|
||||
for (const [key, value] of differences) {
|
||||
|
@ -14,6 +14,7 @@ import { RdDNameGen } from "./rdd-namegen.js";
|
||||
import { RdDConfirm } from "./rdd-confirm.js";
|
||||
import { RdDCalendrier } from "./rdd-calendrier.js";
|
||||
import { Environnement } from "./environnement.js";
|
||||
import { RdDItemCompetence } from "./item-competence.js";
|
||||
|
||||
/* -------------------------------------------- */
|
||||
// This table starts at 0 -> niveau -10
|
||||
@ -170,6 +171,7 @@ export class RdDUtility {
|
||||
//Items
|
||||
'systems/foundryvtt-reve-de-dragon/templates/scripts/autocomplete-script.hbs',
|
||||
'systems/foundryvtt-reve-de-dragon/templates/scripts/autocomplete.hbs',
|
||||
'systems/foundryvtt-reve-de-dragon/templates/item/boutons-comestible.html',
|
||||
'systems/foundryvtt-reve-de-dragon/templates/item/partial-inventaire.html',
|
||||
'systems/foundryvtt-reve-de-dragon/templates/item/partial-environnement.html',
|
||||
'systems/foundryvtt-reve-de-dragon/templates/item/partial-tab-environnement.html',
|
||||
@ -279,6 +281,7 @@ export class RdDUtility {
|
||||
'systems/foundryvtt-reve-de-dragon/templates/chat-signe-draconique-actor.html'
|
||||
];
|
||||
|
||||
Handlebars.registerHelper('either', (a, b) => a ?? b);
|
||||
Handlebars.registerHelper('upperFirst', str => Misc.upperFirst(str ?? 'Null'));
|
||||
Handlebars.registerHelper('lowerFirst', str => Misc.lowerFirst(str ?? 'Null'));
|
||||
Handlebars.registerHelper('upper', str => str?.toUpperCase() ?? 'NULL');
|
||||
@ -296,46 +299,18 @@ export class RdDUtility {
|
||||
Handlebars.registerHelper('min', (...args) => Math.min(...args.slice(0, -1)));
|
||||
Handlebars.registerHelper('regle-optionnelle', (option) => ReglesOptionelles.isUsing(option));
|
||||
Handlebars.registerHelper('trier', list => list.sort((a, b) => a.name.localeCompare(b.name)));
|
||||
Handlebars.registerHelper('filtreTriCompetences', competences => competences.filter(it => it.system.isVisible)
|
||||
.sort((a, b) => {
|
||||
if (a.name.startsWith("Survie") && b.name.startsWith("Survie")) {
|
||||
if (a.name.includes("Cité")) return -1;
|
||||
if (b.name.includes("Cité")) return 1;
|
||||
if (a.name.includes("Extérieur")) return -1;
|
||||
if (b.name.includes("Extérieur")) return 1;
|
||||
return a.name.localeCompare(b.name);
|
||||
}
|
||||
if (a.system.categorie.startsWith("melee") && b.system.categorie.startsWith("melee")) {
|
||||
if (a.name.includes("Corps")) return -1;
|
||||
if (b.name.includes("Corps")) return 1;
|
||||
if (a.name.includes("Dague")) return -1;
|
||||
if (b.name.includes("Dague")) return 1;
|
||||
if (a.name.includes("Esquive")) return -1;
|
||||
if (b.name.includes("Esquive")) return 1;
|
||||
return a.name.localeCompare(b.name);
|
||||
}
|
||||
if (a.name.startsWith("Voie") && b.name.startsWith("Voie")) {
|
||||
if (a.name.includes("Oniros")) return -1;
|
||||
if (b.name.includes("Oniros")) return 1;
|
||||
if (a.name.includes("Hypnos")) return -1;
|
||||
if (b.name.includes("Hypnos")) return 1;
|
||||
if (a.name.includes("Narcos")) return -1;
|
||||
if (b.name.includes("Narcos")) return 1;
|
||||
if (a.name.includes("Thanatos")) return -1;
|
||||
if (b.name.includes("Thanatos")) return 1;
|
||||
return a.name.localeCompare(b.name);
|
||||
}
|
||||
return a.name.localeCompare(b.name);
|
||||
})
|
||||
);
|
||||
Handlebars.registerHelper('linkCompendium', (pack, id, name)=> RdDUtility.linkCompendium(pack, id, name));
|
||||
Handlebars.registerHelper('uniteQuantite', (type) => RdDItem.getUniteQuantite(type));
|
||||
Handlebars.registerHelper('filtreTriCompetences', competences => RdDItemCompetence.triVisible(competences));
|
||||
Handlebars.registerHelper('linkCompendium', (pack, id, name) => RdDUtility.linkCompendium(pack, id, name));
|
||||
Handlebars.registerHelper('uniteQuantite', (itemId, actorId) => RdDUtility.getItem(itemId, actorId)?.getUniteQuantite());
|
||||
Handlebars.registerHelper('isFieldInventaireModifiable', (type, field) => RdDItem.isFieldInventaireModifiable(type, field));
|
||||
Handlebars.registerHelper('getFrequenceRarete', (rarete, field) => Environnement.getFrequenceRarete(rarete, field));
|
||||
Handlebars.registerHelper('either', (a, b) => a ?? b);
|
||||
return loadTemplates(templatePaths);
|
||||
}
|
||||
|
||||
static getItem(itemId, actorId = undefined) {
|
||||
return actorId ? game.actors.get(actorId)?.getObjet(itemId) : game.items.get(itemId);
|
||||
}
|
||||
|
||||
static linkCompendium(pack, id, name) {
|
||||
return `@Compendium[${pack}.${id}]{${name}}`;
|
||||
}
|
||||
@ -1001,7 +976,7 @@ export class RdDUtility {
|
||||
}
|
||||
|
||||
static slideOnDelete(sheet, htmlToDelete) {
|
||||
return htmlToDelete.slideUp(200, () => sheet.render(false));
|
||||
return htmlToDelete?.slideUp(200, () => sheet.render(false));
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
|
@ -63,7 +63,7 @@ export const referenceAjustements = {
|
||||
},
|
||||
encTotal: {
|
||||
isVisible: (rollData, actor) => RdDCarac.isAgiliteOuDerivee(rollData.selectedCarac) && RdDItemCompetence.isMalusEncombrementTotal(rollData.competence),
|
||||
isUsed: (rollData, actor) => RdDCarac.isAgiliteOuDerivee(rollData.selectedCarac) && RdDItemCompetence.isMalusEncombrementTotal(rollData.competence) && rollData.use.encTotal,
|
||||
isUsed: (rollData, actor) => !rollData.oeuvre && RdDCarac.isAgiliteOuDerivee(rollData.selectedCarac) && RdDItemCompetence.isMalusEncombrementTotal(rollData.competence) && rollData.use.encTotal,
|
||||
getLabel: (rollData, actor) => 'Encombrement total',
|
||||
getValue: (rollData, actor) => -actor.getEncTotal()
|
||||
},
|
||||
|
@ -1,8 +1,8 @@
|
||||
{
|
||||
"id": "foundryvtt-reve-de-dragon",
|
||||
"title": "Rêve de Dragon",
|
||||
"version": "10.3.5",
|
||||
"download": "https://www.uberwald.me/gitea/public/foundryvtt-reve-de-dragon/archive/foundryvtt-reve-de-dragon-10.3.5.zip",
|
||||
"version": "10.3.6",
|
||||
"download": "https://www.uberwald.me/gitea/public/foundryvtt-reve-de-dragon/archive/foundryvtt-reve-de-dragon-10.3.6.zip",
|
||||
"manifest": "https://www.uberwald.me/gitea/public/foundryvtt-reve-de-dragon/raw/v10/system.json",
|
||||
"compatibility": {
|
||||
"minimum": "10",
|
||||
|
@ -595,6 +595,10 @@
|
||||
"environnement": {
|
||||
"milieu": "",
|
||||
"environnement": []
|
||||
},
|
||||
"comestible": {
|
||||
"sust": 0,
|
||||
"exotisme": 0
|
||||
}
|
||||
},
|
||||
"competence": {
|
||||
@ -699,13 +703,12 @@
|
||||
"templates": [ "description", "inventaire" ]
|
||||
},
|
||||
"nourritureboisson": {
|
||||
"templates": [ "description", "inventaire" ],
|
||||
"templates": [ "description", "inventaire", "comestible"],
|
||||
"cuisinier": "",
|
||||
"boisson": false,
|
||||
"desaltere": 0,
|
||||
"alcoolise": false,
|
||||
"force": 0,
|
||||
"sust": 0,
|
||||
"exotisme": 0
|
||||
"force": 0
|
||||
},
|
||||
"herbe": {
|
||||
"templates": [ "description", "inventaire", "environnement"],
|
||||
@ -714,17 +717,14 @@
|
||||
"categorie": ""
|
||||
},
|
||||
"ingredient": {
|
||||
"templates": [ "description", "inventaire", "environnement" ],
|
||||
"templates": [ "description", "inventaire", "environnement", "comestible"],
|
||||
"niveau": 0,
|
||||
"base": 0,
|
||||
"sust": 0,
|
||||
"exotisme": 0,
|
||||
"categorie": ""
|
||||
},
|
||||
"faune": {
|
||||
"templates": [ "description", "inventaire", "environnement"],
|
||||
"sust": 0,
|
||||
"exotisme": 0,
|
||||
"templates": [ "description", "inventaire", "environnement", "comestible"],
|
||||
"categorie": "",
|
||||
"actor": {
|
||||
"id": "",
|
||||
"pack": "",
|
||||
|
@ -1,6 +1,6 @@
|
||||
<li class="item flexrow" data-attribute={{key}} data-item-id="{{queue._id}}">
|
||||
<img class="sheet-competence-img" src="{{queue.img}}" />
|
||||
<span class="display-label flex-grow">
|
||||
<span class="item-edit flex-grow">
|
||||
{{#if (eq queue.type 'ombre')}}
|
||||
<img class="sheet-competence-img" src="systems/foundryvtt-reve-de-dragon/icons/competence_thanatos.webp" />
|
||||
{{/if}}
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each souffles as |souffle key|}}
|
||||
<li class="item flexrow" data-attribute={{key}} data-item-id="{{souffle._id}}">
|
||||
<img class="sheet-competence-img" src="{{souffle.img}}" />
|
||||
<span class="display-label flex-grow"><a>{{souffle.name}}</a></span>
|
||||
<span class="item-edit flex-grow"><a>{{souffle.name}}</a></span>
|
||||
<div class="item-controls flex-shrink">
|
||||
<a class="item-delete" title="Delete Item"><i class="fas fa-trash"></i></a>
|
||||
</div>
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each tetes as |tete key|}}
|
||||
<li class="item flexrow" data-attribute={{key}} data-item-id="{{tete._id}}">
|
||||
<img class="sheet-competence-img" src="{{tete.img}}" />
|
||||
<span class="display-label flex-grow"><a>{{tete.name}}</a></span>
|
||||
<span class="item-edit flex-grow"><a>{{tete.name}}</a></span>
|
||||
<div class="item-controls flex-shrink">
|
||||
<a class="item-delete" title="Delete Item"><i class="fas fa-trash"></i></a>
|
||||
</div>
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each casestmr as |casetmr key|}}
|
||||
<li class="item list-item flexrow" data-item-id="{{casetmr.id}}" data-attribute="{{key}}">
|
||||
<img class="sheet-competence-img" src="{{casetmr.img}}" />
|
||||
<span class="display-label"><a>{{casetmr.name}}</a></span>
|
||||
<span class="item-edit"><a>{{casetmr.name}}</a></span>
|
||||
<span>{{casetmr.system.coord}} - {{caseTmr-label casetmr.system.coord}}</span>
|
||||
<div class="item-controls flex-shrink">
|
||||
<a class="item-delete" title="Supprimer"><i class="fas fa-trash"></i></a>
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each rencontres as |rencontre key|}}
|
||||
<li class="item flexrow" data-item-id="{{rencontre._id}}" data-attribute="{{key}}">
|
||||
<img class="sheet-competence-img" src="{{rencontre.img}}" />
|
||||
<span class="display-label flex-grow"><a>
|
||||
<span class="item-edit flex-grow"><a>
|
||||
{{rencontre.name}} r{{rencontre.system.force}} ({{rencontre.system.coord}} - {{caseTmr-label rencontre.system.coord}})
|
||||
</a></span>
|
||||
{{#if rencontre.system.date}}
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each signesdraconiques as |signe key|}}
|
||||
<li class="item list-item flexrow" data-item-id="{{signe._id}}" data-attribute="{{key}}">
|
||||
<img class="sheet-competence-img" src="{{signe.img}}" />
|
||||
<span class="display-label flex-grow"><a>{{signe.name}}</a></span>
|
||||
<span class="item-edit flex-grow"><a>{{signe.name}}</a></span>
|
||||
<span class="flex-shrink">{{signe.system.difficulte}}</span>
|
||||
<div class="item-controls flex-shrink">
|
||||
<a class="item-delete" title="Supprimer"><i class="fas fa-trash"></i></a>
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each sortsReserve as |sort key|}}
|
||||
<li class="item list-item flexrow" data-item-id="{{sort._id}}" data-attribute="{{key}}">
|
||||
<img class="sheet-competence-img" src="{{sort.img}}" />
|
||||
<span class="display-label"><a>{{#if sort.system.echectotal}}Echec total: {{/if}}{{sort.name}} r{{sort.system.ptreve}}</a></span>
|
||||
<span class="item-edit"><a>{{#if sort.system.echectotal}}Echec total: {{/if}}{{sort.name}} r{{sort.system.ptreve}}</a></span>
|
||||
<span>{{sort.system.coord}} - {{caseTmr-label sort.system.coord}}</span>
|
||||
<div class="item-controls flex-shrink">
|
||||
<a class="item-delete flex-shrink" title="Supprimer"><i class="fas fa-trash"></i></a>
|
||||
|
@ -4,7 +4,7 @@
|
||||
{{#each sorts as |sort key|}}
|
||||
<li class="item list-item flexrow" data-item-id="{{sort._id}}" data-attribute="{{key}}">
|
||||
<img class="sheet-competence-img" src="{{sort.img}}" />
|
||||
<span class="display-label flex-grow-2">
|
||||
<span class="item-edit flex-grow-2">
|
||||
<a data-item-id="{{sort._id}}">{{sort.name}}
|
||||
- {{#if sort.system.caseTMRspeciale}}{{sort.system.caseTMRspeciale}}{{else}}{{upperFirst sort.system.caseTMR}}{{/if}}
|
||||
</a>
|
||||
|
@ -3,6 +3,7 @@
|
||||
<img class="profile-img" src="{{img}}" data-edit="img" title="{{name}}" />
|
||||
<div class="header-fields">
|
||||
<h1 class="charname"><input name="name" type="text" value="{{name}}" placeholder="Name" /></h1>
|
||||
{{>'systems/foundryvtt-reve-de-dragon/templates/item/boutons-comestible.html'}}
|
||||
</div>
|
||||
</header>
|
||||
|
||||
@ -28,14 +29,18 @@
|
||||
<label>Créature correspondante</label>
|
||||
<div>
|
||||
{{#if system.actor.id}}
|
||||
{{#if isGM}}
|
||||
<label>
|
||||
{{>'systems/foundryvtt-reve-de-dragon/templates/common/compendium-link.hbs'
|
||||
pack=system.actor.pack id=system.actor.id name=system.actor.name}}
|
||||
</label>
|
||||
<a class="linked-actor-delete" title="Supprimer"><i class="fas fa-trash"></i></a>
|
||||
{{else}}
|
||||
<label>Pas de fiche de créature</label>
|
||||
<label>{{system.actor.name}}</label>
|
||||
{{/if}}
|
||||
{{else}}
|
||||
<label>Pas de fiche de créature</label>
|
||||
{{/if}}
|
||||
</div>
|
||||
</div>
|
||||
{{>"systems/foundryvtt-reve-de-dragon/templates/item/partial-inventaire.html"}}
|
||||
|
@ -8,6 +8,7 @@
|
||||
<span><a class="creer-potion-base chat-card-button" data-actor-id="{{actorId}}">Fabriquer une potion depuis cette plante</a></span>
|
||||
</div>
|
||||
{{/if}}
|
||||
{{>'systems/foundryvtt-reve-de-dragon/templates/item/boutons-comestible.html'}}
|
||||
</div>
|
||||
</header>
|
||||
|
||||
@ -19,10 +20,6 @@
|
||||
<section class="sheet-body">
|
||||
<div class="tab items" data-group="primary" data-tab="informations">
|
||||
<div class="flexcol">
|
||||
<div class="form-group">
|
||||
<label>Niveau (si applicable)</label>
|
||||
<input class="attribute-value" type="text" name="system.niveau" value="{{system.niveau}}" data-dtype="Number" />
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label>Catégorie</label>
|
||||
<select name="system.categorie" class="categorie" data-dtype="String">
|
||||
@ -31,6 +28,23 @@
|
||||
{{/select}}
|
||||
</select>
|
||||
</div>
|
||||
{{#if (eq isComestible 'brut')}}
|
||||
<div class="form-group">
|
||||
<label for="system.sust">Sustentation</label>
|
||||
<input class="attribute-value" type="number" name="system.sust" value="{{system.sust}}" data-dtype="Number" min="0"/>
|
||||
</div>
|
||||
{{#if (gt system.sust 0)}}
|
||||
<div class="form-group">
|
||||
<label for="system.exotisme">Exotisme</label>
|
||||
<input class="attribute-value" type="number" name="system.exotisme" value="{{system.exotisme}}" data-dtype="Number" min="-10" max="0"/>
|
||||
</div>
|
||||
{{/if}}
|
||||
{{else}}
|
||||
<div class="form-group">
|
||||
<label>Niveau (si applicable)</label>
|
||||
<input class="attribute-value" type="text" name="system.niveau" value="{{system.niveau}}" data-dtype="Number" />
|
||||
</div>
|
||||
{{/if}}
|
||||
|
||||
{{>"systems/foundryvtt-reve-de-dragon/templates/item/partial-inventaire.html"}}
|
||||
{{>"systems/foundryvtt-reve-de-dragon/templates/partial-item-description.html"}}
|
||||
|
8
templates/item/boutons-comestible.html
Normal file
8
templates/item/boutons-comestible.html
Normal file
@ -0,0 +1,8 @@
|
||||
{{#if (and isOwned isComestible)}}
|
||||
<div class="form-group">
|
||||
{{#if (eq isComestible 'brut')}}
|
||||
<span><a class="preparer-nourriture chat-card-button" data-actor-id="{{actorId}}">Cuisiner</a></span>
|
||||
{{/if}}
|
||||
<span><a class="manger-nourriture chat-card-button" data-actor-id="{{actorId}}">Manger cru</a></span>
|
||||
</div>
|
||||
{{/if}}
|
@ -9,9 +9,9 @@
|
||||
{{#unless (isFieldInventaireModifiable type 'encombrement')}}disabled{{/unless}}/>
|
||||
</div>
|
||||
<div class="form-group">
|
||||
<label for="system.quantite">Quantité {{uniteQuantite type}}</label>
|
||||
<label for="system.quantite">Quantité {{uniteQuantite id actorId}}</label>
|
||||
<input class="attribute-value" type="text" name="system.quantite" value="{{system.quantite}}" data-dtype="Number"
|
||||
{{#unless (isFieldInventaireModifiable type 'quantite')}}disabled{{/unless}}/>
|
||||
{{#unless (isFieldInventaireModifiable type 'quantite')}}disabled{{/unless}}/>
|
||||
</div>
|
||||
<div class="form-group item-cout">
|
||||
<label for="system.cout">Prix (sols) </label>
|
||||
|
Loading…
Reference in New Issue
Block a user