diff --git a/daggerheart.mjs b/daggerheart.mjs index 9885b691..2b704f36 100644 --- a/daggerheart.mjs +++ b/daggerheart.mjs @@ -97,6 +97,9 @@ Hooks.once('init', () => { game.socket.on(`system.${SYSTEM.id}`, handleSocketEvent); + // Make Compendium Dialog resizable + foundry.applications.sidebar.apps.Compendium.DEFAULT_OPTIONS.window.resizable = true; + registerDHSettings(); RegisterHandlebarsHelpers.registerHelpers(); diff --git a/module/applications/sheets/pc.mjs b/module/applications/sheets/pc.mjs index 31c98b6e..2496c32e 100644 --- a/module/applications/sheets/pc.mjs +++ b/module/applications/sheets/pc.mjs @@ -37,9 +37,10 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { attackRoll: this.attackRoll, tabToLoadout: () => this.domainCardsTab(false), tabToVault: () => this.domainCardsTab(true), - sendToVault: (_, button) => this.moveDomainCard(button, true), - sentToLoadout: (_, button) => this.moveDomainCard(button, false), + sendToVault: this.moveDomainCard, + sendToLoadout: this.moveDomainCard, useDomainCard: this.useDomainCard, + removeCard: this.removeDomainCard, selectClass: this.selectClass, selectSubclass: this.selectSubclass, selectAncestry: this.selectAncestry, @@ -658,7 +659,8 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { this.render(); } - static async moveDomainCard(button, toVault) { + static async moveDomainCard(_, button) { + const toVault = button.dataset.action === 'sendToVault'; if (!toVault && this.document.system.domainCards.loadout.length >= this.document.system.domainData.maxLoadout) { return; } @@ -673,6 +675,7 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { const cls = getDocumentClass('ChatMessage'); const systemData = { title: `${game.i18n.localize('DAGGERHEART.Chat.DomainCard.Title')} - ${capitalize(button.dataset.domain)}`, + origin: this.document.id, img: card.img, name: card.name, description: card.system.effect, @@ -691,6 +694,13 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { cls.create(msg.toObject()); } + static async removeDomainCard(_, button) { + if (button.dataset.type === 'domainCard') { + const card = this.document.items.find(x => x.uuid === button.dataset.key); + await card.delete(); + } + } + static async selectClass() { (await game.packs.get('daggerheart.classes'))?.render(true); } @@ -895,6 +905,7 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { const cls = getDocumentClass('ChatMessage'); const systemData = { title: game.i18n.localize('DAGGERHEART.Chat.FeatureTitle'), + origin: this.document.id, img: item.img, name: item.name, description: item.system.description, @@ -925,6 +936,7 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { : type === 'community' ? game.i18n.localize('DAGGERHEART.Chat.FoundationCard.CommunityTitle') : game.i18n.localize('DAGGERHEART.Chat.FoundationCard.SubclassFeatureTitle'), + origin: this.document.id, img: item.img, name: item.name, description: item.system.description, @@ -952,14 +964,20 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { const title = `${item.name} - ${game.i18n.localize(`DAGGERHEART.Sheets.PC.DomainCard.${capitalize(button.dataset.key)}Title`)}`; const cls = getDocumentClass('ChatMessage'); + const systemData = { + title: game.i18n.localize('DAGGERHEART.Chat.FoundationCard.SubclassFeatureTitle'), + origin: this.document.id, + name: title, + img: item.img, + description: ability.description + }; const msg = new cls({ + type: 'abilityUse', user: game.user.id, + system: systemData, content: await foundry.applications.handlebars.renderTemplate( 'systems/daggerheart/templates/chat/ability-use.hbs', - { - title: game.i18n.localize('DAGGERHEART.Chat.FoundationCard.SubclassFeatureTitle'), - card: { name: title, img: item.img, description: ability.description } - } + systemData ) }); @@ -971,14 +989,19 @@ export default class PCSheet extends DaggerheartSheet(ActorSheetV2) { const item = this.document.items.find(x => x.uuid === button.dataset.id); const cls = getDocumentClass('ChatMessage'); + const systemData = { + title: game.i18n.localize('DAGGERHEART.Chat.FoundationCard.SubclassFeatureTitle'), + origin: this.document.id, + name: item.name, + img: item.img, + description: item.system.description + }; const msg = new cls({ user: game.user.id, + system: systemData, content: await foundry.applications.handlebars.renderTemplate( 'systems/daggerheart/templates/chat/ability-use.hbs', - { - title: game.i18n.localize('DAGGERHEART.Chat.FoundationCard.SubclassFeatureTitle'), - card: { name: item.name, img: item.img, description: item.system.description } - } + systemData ) }); diff --git a/module/data/abilityUse.mjs b/module/data/abilityUse.mjs index 5d95cd11..c95a9ff3 100644 --- a/module/data/abilityUse.mjs +++ b/module/data/abilityUse.mjs @@ -4,11 +4,12 @@ export default class DhpAbilityUse extends foundry.abstract.TypeDataModel { return { title: new fields.StringField({}), + origin: new fields.StringField({}), img: new fields.StringField({}), name: new fields.StringField({}), description: new fields.StringField({}), actions: new fields.ArrayField( - new fields.SchemaField({ + new fields.ObjectField({ name: new fields.StringField({}), damage: new fields.SchemaField({ type: new fields.StringField({}), @@ -19,11 +20,11 @@ export default class DhpAbilityUse extends foundry.abstract.TypeDataModel { value: new fields.StringField({}) }), cost: new fields.SchemaField({ - type: new fields.StringField({ nullable: true }), - value: new fields.NumberField({ nullable: true }) + type: new fields.StringField({}), + value: new fields.NumberField({}) }), target: new fields.SchemaField({ - type: new fields.StringField({}) + type: new fields.StringField({ nullable: true }) }) }) ) diff --git a/module/documents/actor.mjs b/module/documents/actor.mjs index 012377c7..97ccb1db7 100644 --- a/module/documents/actor.mjs +++ b/module/documents/actor.mjs @@ -5,12 +5,15 @@ import { GMUpdateEvent, socketEvent } from '../helpers/socket.mjs'; import { setDiceSoNiceForDualityRoll } from '../helpers/utils.mjs'; export default class DhpActor extends Actor { - _preCreate(data, changes, user) { - if (data.type === 'pc') { - data.prototypeToken = { actorLink: true, disposition: 1, sight: { enabled: true } }; - } - - super._preCreate(data, changes, user); + async _preCreate(data, options, user) { + if ( (await super._preCreate(data, options, user)) === false ) return false; + + // Configure prototype token settings + const prototypeToken = {}; + if ( this.type === "pc" ) Object.assign(prototypeToken, { + sight: { enabled: true }, actorLink: true, disposition: CONST.TOKEN_DISPOSITIONS.FRIENDLY + }); + this.updateSource({ prototypeToken }); } prepareData() { @@ -450,10 +453,20 @@ export default class DhpActor extends Actor { let update = {}; switch (type) { case SYSTEM.GENERAL.healingTypes.health.id: - update = { 'system.resources.health.value': Math.max(this.system.resources.health.value - healing, 0) }; + update = { + 'system.resources.health.value': Math.min( + this.system.resources.health.value + healing, + this.system.resources.health.max + ) + }; break; case SYSTEM.GENERAL.healingTypes.stress.id: - update = { 'system.resources.stress.value': Math.max(this.system.resources.stress.value - healing, 0) }; + update = { + 'system.resources.stress.value': Math.min( + this.system.resources.stress.value + healing, + this.system.resources.stress.max + ) + }; break; } @@ -486,7 +499,10 @@ export default class DhpActor extends Actor { } if (action.cost.type != null && action.cost.value != null) { - if (this.system.resources[action.cost.type].value < action.cost.value - 1) { + if ( + this.system.resources[action.cost.type].value - action.cost.value <= + this.system.resources[action.cost.type].min + ) { ui.notifications.error(game.i18n.localize(`Insufficient ${action.cost.type} to use this ability`)); return; } diff --git a/module/ui/chatLog.mjs b/module/ui/chatLog.mjs index 183060b0..1b575aa8 100644 --- a/module/ui/chatLog.mjs +++ b/module/ui/chatLog.mjs @@ -36,7 +36,7 @@ export default class DhpChatLog extends foundry.applications.sidebar.tabs.ChatLo element.addEventListener('click', event => this.selectAdvantage.bind(this)(event, data.message)) ); html.querySelectorAll('.ability-use-button').forEach(element => - element.addEventListener('click', this.abilityUseButton.bind(this)(event, data.message)) + element.addEventListener('click', event => this.abilityUseButton.bind(this)(event, data.message)) ); }; @@ -134,6 +134,7 @@ export default class DhpChatLog extends foundry.applications.sidebar.tabs.ChatLo event.stopPropagation(); const action = message.system.actions[Number.parseInt(event.currentTarget.dataset.index)]; - await game.user.character.useAction(action); + const actor = game.actors.get(message.system.origin); + await actor.useAction(action); }; } diff --git a/styles/chat.less b/styles/chat.less index e6bb20c2..ea9c95ef 100644 --- a/styles/chat.less +++ b/styles/chat.less @@ -547,6 +547,11 @@ margin-top: @tinyMargin; } } + + .ability-card-action-cost { + margin: auto; + font-size: 1.5em; + } } img { diff --git a/styles/daggerheart.css b/styles/daggerheart.css index 0540c0d5..1d705e64 100755 --- a/styles/daggerheart.css +++ b/styles/daggerheart.css @@ -1770,6 +1770,10 @@ .daggerheart.chat.domain-card .ability-card-footer button:nth-of-type(n + 3) { margin-top: 2px; } +.daggerheart.chat.domain-card .ability-card-footer .ability-card-action-cost { + margin: auto; + font-size: 1.5em; +} .daggerheart.chat.domain-card img { width: 80px; } diff --git a/templates/chat/ability-use.hbs b/templates/chat/ability-use.hbs index c719d02f..51d56ace 100644 --- a/templates/chat/ability-use.hbs +++ b/templates/chat/ability-use.hbs @@ -10,6 +10,7 @@ + {{#if action.cost.value}}