diff --git a/module/actor/actor.js b/module/actor/actor.js index cd1e73b..4a7f1a2 100644 --- a/module/actor/actor.js +++ b/module/actor/actor.js @@ -6,51 +6,79 @@ import { fromIdUuid } from "../mosh.js"; */ export class MothershipActor extends Actor { - //Augment the basic actor data with additional dynamic data. - prepareData() { - //console.log(game.release.generation); - super.prepareData(); + // augment the basic actor data with additional dynamic data + prepareDerivedData() { - const actorData = this; - const data = actorData.system; - const flags = actorData.flags; - - // Make separate methods for each Actor type (character, npc, etc.) to keep - // things organized. - if (actorData.type === 'character') this._prepareCharacterData(actorData); - else if (actorData.type === 'creature') this._prepareCreatureData(actorData); - else if (actorData.type === 'ship') this._prepareShipData(actorData); + super.prepareDerivedData(); + const system = this.system; + // ----- per-type derived ----- + if (this.type === "character") this._deriveCharacter(); + else if (this.type === "creature") this._deriveCreature(); + else if (this.type === "ship") this._deriveShip(); } - //Prepare Character type specific data - _prepareCharacterData(actorData) { - const data = actorData.system; - - let armorPoints = 0; - let damageReduction = 0; - const armors = this.getEmbeddedCollection("Item").filter(e => "armor" === e.type); - - for (let armor of armors) { - if (armor.system.equipped) { - armorPoints += armor.system.armorPoints; - damageReduction += armor.system.damageReduction; + // Prepare Character type specific data + _deriveCharacter() { + const system = this.system; + //armor points + damage reduction + //init vars + let armorPoints = 0; + let damageReduction = 0; + //count values + for (const armor of this.items.filter(i => i.type === "armor")) { + if (armor.system?.equipped) { + armorPoints += Number(armor.system.armorPoints ?? 0); + damageReduction += Number(armor.system.damageReduction ?? 0); + } } - } - - data.stats.armor.mod = armorPoints; - data.stats.armor.total = armorPoints + data.stats.armor.value; - data.stats.armor.damageReduction = damageReduction; + //set values + system.stats.armor.mod = armorPoints; + system.stats.armor.total = armorPoints + Number(system.stats.armor.value ?? 0); + system.stats.armor.damageReduction = damageReduction; + //net hp + //init vars + let netHPvalue = 0; + let netHPmax = 0; + //check if actor has netHP + system.netHP ??= { value: 0, min: 0, max: 0, label: "Net HP"}; + //set values + system.netHP.value = ((Number(system.hits.max ?? 0)-Number(system.hits.value ?? 0)-1) * Number(system.health.max ?? 0)) + Number(system.health.value ?? 0); + system.netHP.max = Number(system.health.max ?? 0) * Number(system.hits.max ?? 0); } - //Prepare Creature type specific data - _prepareCreatureData(actorData) { - const data = actorData; + // Prepare Creature type specific data + _deriveCreature() { + const system = this.system; + //armor points + damage reduction + //init vars + let armorPoints = 0; + let damageReduction = 0; + //count values + for (const armor of this.items.filter(i => i.type === "armor")) { + if (armor.system?.equipped) { + armorPoints += Number(armor.system.armorPoints ?? 0); + damageReduction += Number(armor.system.damageReduction ?? 0); + } + } + //set values + system.stats.armor.mod = armorPoints; + system.stats.armor.total = armorPoints + Number(system.stats.armor.value ?? 0); + system.stats.armor.damageReduction = damageReduction; + //net hp + //init vars + let netHPvalue = 0; + let netHPmax = 0; + //check if actor has netHP + system.netHP ??= { value: 0, min: 0, max: 0, label: "Net HP"}; + //set values + system.netHP.value = ((Number(system.hits.max ?? 0)-Number(system.hits.value ?? 0)-1) * Number(system.health.max ?? 0)) + Number(system.health.value ?? 0); + system.netHP.max = Number(system.health.max ?? 0) * Number(system.hits.max ?? 0); } - //Prepare Ship type specific data - _prepareShipData(actorData) { - const data = actorData; + // Prepare Ship type specific data + _deriveShip() { + //nothing needed yet } //central flavor text library for all chat messages @@ -1494,18 +1522,27 @@ export class MothershipActor extends Actor { if (firstEdition) { //if calm not enabled if (!useCalm) { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //increase stress by 1 and retrieve the flavor text from the result - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } } else { - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //increase stress by 1 and retrieve the flavor text from the result + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } } //if 0e } else { @@ -1513,20 +1550,31 @@ export class MothershipActor extends Actor { if (!useCalm) { //on Save failure if (attribute === 'sanity' || attribute === 'fear' || attribute === 'body' || attribute === 'armor') { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //gain 1 stress - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } } } else { - //output standard failure - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + //on Save failure + if (attribute === 'sanity' || attribute === 'fear' || attribute === 'body' || attribute === 'armor') { + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //gain 1 stress + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } + } } } } @@ -1572,8 +1620,16 @@ export class MothershipActor extends Actor { if (useCalm) { //prep text based on success or failure if (parsedRollResult.success === false && this.type === 'character') { - //set fail text - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //increase stress by 1 and retrieve the flavor text from the result + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } } else if (parsedRollResult.success === true && this.type === 'character') { //calculate stress reduction let onesValue = Number(String(parsedRollResult.total).charAt(String(parsedRollResult.total).length - 1)); @@ -1585,13 +1641,13 @@ export class MothershipActor extends Actor { } else { //prep text based on success or failure if (parsedRollResult.success === false && this.type === 'character') { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //increase stress by 1 and retrieve the flavor text from the result - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } @@ -1609,8 +1665,16 @@ export class MothershipActor extends Actor { if (useCalm) { //prep text based on success or failure if (parsedRollResult.success === false && this.type === 'character') { - //set fail text - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //increase stress by 1 and retrieve the flavor text from the result + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } } else if (parsedRollResult.success === true && this.type === 'character') { //calculate stress reduction let succeedBy = Math.floor((rollTarget - parsedRollResult.total) / 10); @@ -1626,13 +1690,13 @@ export class MothershipActor extends Actor { } else { //prep text based on success or failure if (parsedRollResult.success === false && this.type === 'character') { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //increase stress by 1 and retrieve the flavor text from the result - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } @@ -1711,18 +1775,27 @@ export class MothershipActor extends Actor { if (firstEdition) { //if calm not enabled if (!useCalm) { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //increase stress by 1 and retrieve the flavor text from the result - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } } else { - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //increase stress by 1 and retrieve the flavor text from the result + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } } //if 0e } else { @@ -1730,20 +1803,28 @@ export class MothershipActor extends Actor { if (!useCalm) { //on Save failure if (attribute === 'sanity' || attribute === 'fear' || attribute === 'body' || attribute === 'armor') { - if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled //gain 1 stress - let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); + let addStress = await this.modifyActor('system.other.stress.value', 1, null, false); flavorText = addStress[1]; } - //if critical failure, make sure to ask for panic check - if (parsedRollResult.critical === true) { + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { //set crit fail critFail = true; } } } else { - //output standard failure - flavorText = game.i18n.localize("Mosh.YouSenseTheWeightOfYourSetbacks"); + if (game.settings.get('mosh', 'autoStress')) { //If the automatic stress option is enabled + //gain 1 stress + let removeCalm = await this.modifyActor('system.other.stress.value', null, '-1d10', false); + flavorText = removeCalm[1]; + } + //if critical failure, make sure to ask for panic check + if (parsedRollResult.critical === true) { + //set crit fail + critFail = true; + } } } } else if (parsedRollResult.success === true && this.type === 'character') { diff --git a/module/mosh.js b/module/mosh.js index 05d8d50..4db7b33 100644 --- a/module/mosh.js +++ b/module/mosh.js @@ -121,87 +121,6 @@ Hooks.once("ready", async function () { } }); - //Calm & 1e/0e character updates - // if the user has calm enabled at the start, - if (game.settings.get('mosh','useCalm')) { - //get list of actors - let actorList = game.actors; - let actorName = ''; - let minStart = null; - let valueStart = null; - let maxStart = null; - let labelStart = ''; - let minEnd = null; - let valueEnd = null; - let maxEnd = null; - let labelEnd = ''; - //loop through all actors and update their stress values - actorList.forEach(function(actor){ - //loop through each result - if (actor.type === 'character') { - //set character name - actorName = actor.name; - //set current values - minStart = actor.system.other.stress.min; - valueStart = actor.system.other.stress.value; - maxStart = actor.system.other.stress.max; - labelStart = actor.system.other.stress.label; - //if the label does not say Calm - if (actor.system.other.stress.label != 'Calm') { - //change it to calm - actor.update({'system.other.stress.label': 'Calm'}); - //log - labelEnd = 'Calm'; - } - //if the MIN value is not 0, this is an old character - if (actor.system.other.stress.min != 0) { - //put this value as the maximum - //change it to calm - actor.update({'system.other.stress.max': actor.system.other.stress.min}); - //log - maxEnd = actor.system.other.stress.min; - //set the minimum to zero - //change it to calm - actor.update({'system.other.stress.min': 0}); - //log - minEnd = 0; - } - //log change - console.log(actorName + " stress.min changed from " + minStart + " to " + minEnd); - console.log(actorName + " stress.max changed from " + maxStart + " to " + maxEnd); - console.log(actorName + " stress.label changed from " + labelStart + " to " + labelEnd); - //rerender this sheet - actor.render(); - } - }); - //user does not have calm enabled - } else { - //if the user has Zero edition enabled - if (!game.settings.get('mosh','firstEdition')) { - //loop through all actors and update their stress values - actorList.forEach(function(actor){ - //loop through each result - if (actor.type === 'character') { - //set character name - actorName = actor.name; - //set current values - maxStart = actor.system.other.stress.max; - //if the max value, this is an old character - if (actor.system.other.stress.max != 999) { - //put this value as the maximum - //change it to calm - actor.update({'system.other.stress.max': 999}); - //log - maxEnd = 999; - } - //log change - console.log(actorName + " stress.max changed from " + maxStart + " to " + maxEnd); - //rerender this sheet - actor.render(); - } - }); - } - } }); //add custom damage dice for MOSH @@ -255,38 +174,42 @@ Hooks.once('diceSoNiceReady', (dice3d) => { ) }) -//Hooks.on("preCreateActor", (createData) => { -/** - * Set default values for new actors' tokens - */ +//set initial things when creating an actor Hooks.on("preCreateActor", (document, createData, options, userId) => { - let disposition = CONST.TOKEN_DISPOSITIONS.NEUTRAL; + console.log("preCreateActor fired for:", createData?.name, createData?.type); - if (createData.type == "creature") { - disposition = CONST.TOKEN_DISPOSITIONS.HOSTILE + const disposition = + createData.type === "creature" + ? CONST.TOKEN_DISPOSITIONS.HOSTILE + : CONST.TOKEN_DISPOSITIONS.NEUTRAL; + + // Apply prototype token defaults (v12+) + document.updateSource({ + "prototypeToken.bar1.attribute": "system.health", // <-- use full system path + "prototypeToken.bar2.attribute": "system.hits", // adjust to your schema + "prototypeToken.displayName": CONST.TOKEN_DISPLAY_MODES.OWNER_HOVER, + "prototypeToken.displayBars": CONST.TOKEN_DISPLAY_MODES.OWNER_HOVER, + "prototypeToken.disposition": disposition, + "prototypeToken.name": createData.name + }); + + if (createData.type === "character") { + document.updateSource({ + "prototypeToken.disposition": CONST.TOKEN_DISPOSITIONS.FRIENDLY, + "prototypeToken.actorLink": true, + "prototypeToken.vision": true + }); + + if (game.settings.get("mosh", "useCalm")) { + document.updateSource({ + "system.other.stress.min": 0, + "system.other.stress.value": 85, + "system.other.stress.max": 85, + "system.other.stress.label": "Calm" + }); + } } - - // Set wounds, advantage, and display name visibility - foundry.utils.mergeObject(createData, - { - "token.bar1": { "attribute": "health" }, // Default Bar 1 to Health - "token.bar2": { "attribute": "hits" }, // Default Bar 2 to Insanity - "token.displayName": CONST.TOKEN_DISPLAY_MODES.OWNER_HOVER, // Default display name to be on owner hover - "token.displayBars": CONST.TOKEN_DISPLAY_MODES.OWNER_HOVER, // Default display bars to be on owner hover - "token.disposition": disposition, // Default disposition to neutral - "token.name": createData.name // Set token name to actor name - }) - - console.log(createData); - console.log("Created!"); - - if (createData.type == "character") { - console.log("Got here"); - const prototypeToken = { disposition: 1, actorLink: true, vision: true}; // Set disposition to "Friendly" - document.updateSource({ prototypeToken }); - - } -}) +}); /* -------------------------------------------- */ diff --git a/module/settings.js b/module/settings.js index 0ddcc15..9b33412 100644 --- a/module/settings.js +++ b/module/settings.js @@ -196,15 +196,29 @@ export const registerSettings = function () { valueStart = actor.system.other.stress.value; maxStart = actor.system.other.stress.max; labelStart = actor.system.other.stress.label; - //convert min stress to max calm - actor.update({'system.other.stress.max': Math.round(85-(actor.system.other.stress.min*3))}); - maxEnd = Math.round(85-(actor.system.other.stress.min*3)); + //update max calm + //set max calm to 85 if min stress is 2 + if (minStart === 2) { + actor.update({'system.other.stress.max': 85}); + maxEnd = 85; + //otherwise convert the min stress to max calm + } else { + actor.update({'system.other.stress.max': Math.round(85-(actor.system.other.stress.value*3))}); + maxEnd = Math.round(85-(actor.system.other.stress.value*3)); + } //set min stress to 0 actor.update({'system.other.stress.min': 0}); minEnd = 0; - //convert stress to calm - actor.update({'system.other.stress.value': Math.round(85-(actor.system.other.stress.value*3))}); - valueEnd = Math.round(85-(actor.system.other.stress.value*3)); + //update calm + //set calm to 85 if stress is 2 + if (valueStart === 2) { + actor.update({'system.other.stress.value': 85}); + valueEnd = 85; + //otherwise convert stress to calm + } else { + actor.update({'system.other.stress.value': Math.round(85-(actor.system.other.stress.value*3))}); + valueEnd = Math.round(85-(actor.system.other.stress.value*3)); + } //set stress label to Calm actor.update({'system.other.stress.label': 'Calm'}); labelEnd = 'Calm'; @@ -234,7 +248,7 @@ export const registerSettings = function () { //set min stress to 20 if > 20 if (Math.round((85-actor.system.other.stress.max)/3) > 20) { actor.update({'system.other.stress.min': 20}); - minEnd = 2; + minEnd = 20; //set min stress to 2 if < 2 } else if (Math.round((85-actor.system.other.stress.max)/3) < 2) { actor.update({'system.other.stress.min': 2}); diff --git a/template.json b/template.json index aff2133..f684c29 100644 --- a/template.json +++ b/template.json @@ -19,6 +19,12 @@ "max" : 2, "label" : "Wounds" }, + "netHP": { + "value": 20, + "min": 0, + "max" : 20, + "label" : "Net HP" + }, "bleeding": { "value": 0, "min": 0, @@ -36,9 +42,6 @@ "current" : 0, "capacity" : 0 }, - "settings" : { - "useCalm" : false - }, "class": { "value": "" },