mirror of
https://github.com/Foundryborne/daggerheart.git
synced 2026-01-12 03:31:07 +01:00
[Fix] Downtime Actions (#1295)
* Fixed so downtime actiosn can be used again * Update module/data/fields/action/targetField.mjs Co-authored-by: Carlos Fernandez <CarlosFdez@users.noreply.github.com> * . --------- Co-authored-by: Carlos Fernandez <CarlosFdez@users.noreply.github.com>
This commit is contained in:
parent
fe8e98ef35
commit
b9d67e44da
13 changed files with 86 additions and 32 deletions
|
|
@ -178,10 +178,17 @@ export default class DhpDowntime extends HandlebarsApplicationMixin(ApplicationV
|
||||||
}
|
}
|
||||||
|
|
||||||
static async takeDowntime() {
|
static async takeDowntime() {
|
||||||
const moves = Object.values(this.moveData).flatMap(category => {
|
const moves = Object.keys(this.moveData).flatMap(categoryKey => {
|
||||||
return Object.values(category.moves)
|
const category = this.moveData[categoryKey];
|
||||||
.filter(x => x.selected)
|
return Object.keys(category.moves)
|
||||||
.flatMap(move => [...Array(move.selected).keys()].map(_ => move));
|
.filter(x => category.moves[x].selected)
|
||||||
|
.flatMap(key => {
|
||||||
|
const move = category.moves[key];
|
||||||
|
return [...Array(move.selected).keys()].map(_ => ({
|
||||||
|
...move,
|
||||||
|
movePath: `${categoryKey}.moves.${key}`
|
||||||
|
}));
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
const cls = getDocumentClass('ChatMessage');
|
const cls = getDocumentClass('ChatMessage');
|
||||||
|
|
|
||||||
|
|
@ -132,12 +132,21 @@ export default class DhpChatLog extends foundry.applications.sidebar.tabs.ChatLo
|
||||||
}
|
}
|
||||||
|
|
||||||
async actionUseButton(event, message) {
|
async actionUseButton(event, message) {
|
||||||
const { moveIndex, actionIndex } = event.currentTarget.dataset;
|
const { moveIndex, actionIndex, movePath } = event.currentTarget.dataset;
|
||||||
const parent = await foundry.utils.fromUuid(message.system.actor);
|
const parent = await foundry.utils.fromUuid(message.system.actor);
|
||||||
const actionType = message.system.moves[moveIndex].actions[actionIndex];
|
const actionType = message.system.moves[moveIndex].actions[actionIndex];
|
||||||
const cls = game.system.api.models.actions.actionsTypes[actionType.type];
|
const cls = game.system.api.models.actions.actionsTypes[actionType.type];
|
||||||
const action = new cls(
|
const action = new cls(
|
||||||
{ ...actionType, _id: foundry.utils.randomID(), name: game.i18n.localize(actionType.name) },
|
{
|
||||||
|
...actionType,
|
||||||
|
_id: foundry.utils.randomID(),
|
||||||
|
name: game.i18n.localize(actionType.name),
|
||||||
|
originItem: {
|
||||||
|
type: CONFIG.DH.ITEM.originItemType.restMove,
|
||||||
|
itemPath: movePath,
|
||||||
|
actionIndex: actionIndex
|
||||||
|
}
|
||||||
|
},
|
||||||
{ parent: parent.system }
|
{ parent: parent.system }
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1547,3 +1547,8 @@ export const beastformTypes = {
|
||||||
label: 'DAGGERHEART.CONFIG.BeastformType.hybrid'
|
label: 'DAGGERHEART.CONFIG.BeastformType.hybrid'
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const originItemType = {
|
||||||
|
itemCollection: 'itemCollection',
|
||||||
|
restMove: 'restMove'
|
||||||
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
import DhpActor from '../../documents/actor.mjs';
|
import DhpActor from '../../documents/actor.mjs';
|
||||||
import D20RollDialog from '../../applications/dialogs/d20RollDialog.mjs';
|
import D20RollDialog from '../../applications/dialogs/d20RollDialog.mjs';
|
||||||
import { ActionMixin } from '../fields/actionField.mjs';
|
import { ActionMixin } from '../fields/actionField.mjs';
|
||||||
|
import { originItemField } from '../chat-message/actorRoll.mjs';
|
||||||
|
|
||||||
const fields = foundry.data.fields;
|
const fields = foundry.data.fields;
|
||||||
|
|
||||||
|
|
@ -25,6 +26,7 @@ export default class DHBaseAction extends ActionMixin(foundry.abstract.DataModel
|
||||||
description: new fields.HTMLField(),
|
description: new fields.HTMLField(),
|
||||||
img: new fields.FilePathField({ initial: undefined, categories: ['IMAGE'], base64: false }),
|
img: new fields.FilePathField({ initial: undefined, categories: ['IMAGE'], base64: false }),
|
||||||
chatDisplay: new fields.BooleanField({ initial: true, label: 'DAGGERHEART.ACTIONS.Config.displayInChat' }),
|
chatDisplay: new fields.BooleanField({ initial: true, label: 'DAGGERHEART.ACTIONS.Config.displayInChat' }),
|
||||||
|
originItem: originItemField(),
|
||||||
actionType: new fields.StringField({
|
actionType: new fields.StringField({
|
||||||
choices: CONFIG.DH.ITEM.actionTypes,
|
choices: CONFIG.DH.ITEM.actionTypes,
|
||||||
initial: 'action',
|
initial: 'action',
|
||||||
|
|
@ -215,6 +217,7 @@ export default class DHBaseAction extends ActionMixin(foundry.abstract.DataModel
|
||||||
title: `${this.item instanceof CONFIG.Actor.documentClass ? '' : `${this.item.name}: `}${game.i18n.localize(this.name)}`,
|
title: `${this.item instanceof CONFIG.Actor.documentClass ? '' : `${this.item.name}: `}${game.i18n.localize(this.name)}`,
|
||||||
source: {
|
source: {
|
||||||
item: this.item._id,
|
item: this.item._id,
|
||||||
|
originItem: this.originItem,
|
||||||
action: this._id,
|
action: this._id,
|
||||||
actor: this.actor.uuid
|
actor: this.actor.uuid
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,16 @@ const targetsField = () =>
|
||||||
})
|
})
|
||||||
);
|
);
|
||||||
|
|
||||||
|
export const originItemField = () =>
|
||||||
|
new fields.SchemaField({
|
||||||
|
type: new fields.StringField({
|
||||||
|
choices: CONFIG.DH.ITEM.originItemType,
|
||||||
|
initial: CONFIG.DH.ITEM.originItemType.itemCollection
|
||||||
|
}),
|
||||||
|
itemPath: new fields.StringField(),
|
||||||
|
actionIndex: new fields.StringField()
|
||||||
|
});
|
||||||
|
|
||||||
export default class DHActorRoll extends foundry.abstract.TypeDataModel {
|
export default class DHActorRoll extends foundry.abstract.TypeDataModel {
|
||||||
static defineSchema() {
|
static defineSchema() {
|
||||||
return {
|
return {
|
||||||
|
|
@ -35,6 +45,7 @@ export default class DHActorRoll extends foundry.abstract.TypeDataModel {
|
||||||
source: new fields.SchemaField({
|
source: new fields.SchemaField({
|
||||||
actor: new fields.StringField(),
|
actor: new fields.StringField(),
|
||||||
item: new fields.StringField(),
|
item: new fields.StringField(),
|
||||||
|
originItem: originItemField(),
|
||||||
action: new fields.StringField()
|
action: new fields.StringField()
|
||||||
}),
|
}),
|
||||||
damage: new fields.ObjectField(),
|
damage: new fields.ObjectField(),
|
||||||
|
|
@ -51,14 +62,23 @@ export default class DHActorRoll extends foundry.abstract.TypeDataModel {
|
||||||
get actionItem() {
|
get actionItem() {
|
||||||
const actionActor = this.actionActor;
|
const actionActor = this.actionActor;
|
||||||
if (!actionActor || !this.source.item) return null;
|
if (!actionActor || !this.source.item) return null;
|
||||||
return actionActor.items.get(this.source.item);
|
|
||||||
|
switch (this.source.originItem.type) {
|
||||||
|
case CONFIG.DH.ITEM.originItemType.restMove:
|
||||||
|
const restMoves = game.settings.get(CONFIG.DH.id, CONFIG.DH.SETTINGS.gameSettings.Homebrew).restMoves;
|
||||||
|
return Array.from(foundry.utils.getProperty(restMoves, `${this.source.originItem.itemPath}`).actions)[
|
||||||
|
this.source.originItem.actionIndex
|
||||||
|
];
|
||||||
|
default:
|
||||||
|
const item = actionActor.items.get(this.source.item);
|
||||||
|
return item ? item.system.actionsList?.find(a => a.id === this.source.action) : null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
get action() {
|
get action() {
|
||||||
const actionActor = this.actionActor,
|
const { actionActor, actionItem: itemAction } = this;
|
||||||
actionItem = this.actionItem;
|
|
||||||
if (!this.source.action) return null;
|
if (!this.source.action) return null;
|
||||||
if (actionItem) return actionItem.system.actionsList?.find(a => a.id === this.source.action);
|
if (itemAction) return itemAction;
|
||||||
else if (actionActor?.system.attack?._id === this.source.action) return actionActor.system.attack;
|
else if (actionActor?.system.attack?._id === this.source.action) return actionActor.system.attack;
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -98,7 +98,9 @@ export default class DamageField extends fields.SchemaField {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const token = game.scenes.find(x => x.active).tokens.find(x => x.id === target.id);
|
const token = target.id
|
||||||
|
? game.scenes.find(x => x.active).tokens.find(x => x.id === target.id)
|
||||||
|
: actor.prototypeToken;
|
||||||
if (config.hasHealing)
|
if (config.hasHealing)
|
||||||
damagePromises.push(
|
damagePromises.push(
|
||||||
actor.takeHealing(config.damage).then(updates => targetDamage.push({ token, updates }))
|
actor.takeHealing(config.damage).then(updates => targetDamage.push({ token, updates }))
|
||||||
|
|
|
||||||
|
|
@ -24,7 +24,7 @@ export default class TargetField extends fields.SchemaField {
|
||||||
if (!this.target?.type) return (config.targets = []);
|
if (!this.target?.type) return (config.targets = []);
|
||||||
config.hasTarget = true;
|
config.hasTarget = true;
|
||||||
let targets;
|
let targets;
|
||||||
// If the Action is configured as self-targeted, set targets as the owner.
|
// If the Action is configured as self-targeted, set targets as the owner. Probably better way than to fallback to getDependentTokens
|
||||||
if (this.target?.type === CONFIG.DH.GENERAL.targetTypes.self.id)
|
if (this.target?.type === CONFIG.DH.GENERAL.targetTypes.self.id)
|
||||||
targets = [this.actor.token ?? this.actor.prototypeToken];
|
targets = [this.actor.token ?? this.actor.prototypeToken];
|
||||||
else {
|
else {
|
||||||
|
|
@ -72,17 +72,17 @@ export default class TargetField extends fields.SchemaField {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Format actor to useful datas for Action roll workflow.
|
* Format actor to useful datas for Action roll workflow.
|
||||||
* @param {*} actor Actor object to format.
|
* @param {*} token Token object to format.
|
||||||
* @returns {*} Formatted Actor.
|
* @returns {*} Formatted Actor.
|
||||||
*/
|
*/
|
||||||
static formatTarget(actor) {
|
static formatTarget(token) {
|
||||||
return {
|
return {
|
||||||
id: actor.id,
|
id: token.id,
|
||||||
actorId: actor.actor.uuid,
|
actorId: token.actor.uuid,
|
||||||
name: actor.actor.name,
|
name: token.actor.name,
|
||||||
img: actor.actor.img,
|
img: token.actor.img,
|
||||||
difficulty: actor.actor.system.difficulty,
|
difficulty: token.actor.system.difficulty,
|
||||||
evasion: actor.actor.system.evasion,
|
evasion: token.actor.system.evasion,
|
||||||
saved: {
|
saved: {
|
||||||
value: null,
|
value: null,
|
||||||
success: null
|
success: null
|
||||||
|
|
|
||||||
|
|
@ -145,9 +145,11 @@ export default class DhpChatMessage extends foundry.documents.ChatMessage {
|
||||||
});
|
});
|
||||||
|
|
||||||
html.querySelectorAll('.token-target-container').forEach(element => {
|
html.querySelectorAll('.token-target-container').forEach(element => {
|
||||||
|
if (element.dataset.token) {
|
||||||
element.addEventListener('pointerover', this.hoverTarget);
|
element.addEventListener('pointerover', this.hoverTarget);
|
||||||
element.addEventListener('pointerout', this.unhoverTarget);
|
element.addEventListener('pointerout', this.unhoverTarget);
|
||||||
element.addEventListener('click', this.clickTarget);
|
element.addEventListener('click', this.clickTarget);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -28,13 +28,16 @@
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
gap: 2px;
|
gap: 2px;
|
||||||
cursor: pointer;
|
|
||||||
transition: all 0.3s ease;
|
transition: all 0.3s ease;
|
||||||
border-radius: 6px;
|
border-radius: 6px;
|
||||||
|
|
||||||
|
&.clickable {
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
&:hover {
|
&:hover {
|
||||||
background: @golden-10;
|
background: @golden-10;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
header {
|
header {
|
||||||
display: flex;
|
display: flex;
|
||||||
|
|
|
||||||
|
|
@ -90,12 +90,15 @@
|
||||||
background: transparent;
|
background: transparent;
|
||||||
transition: all 0.3s ease;
|
transition: all 0.3s ease;
|
||||||
padding: 5px;
|
padding: 5px;
|
||||||
cursor: pointer;
|
|
||||||
transition: all 0.3s ease;
|
transition: all 0.3s ease;
|
||||||
|
|
||||||
|
&.clickable {
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
&:hover {
|
&:hover {
|
||||||
background: @golden-10;
|
background: @golden-10;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
img {
|
img {
|
||||||
width: 40px;
|
width: 40px;
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
<ul class="daggerheart chat damage-summary">
|
<ul class="daggerheart chat damage-summary">
|
||||||
{{#each targets}}
|
{{#each targets}}
|
||||||
<li class="token-target-container" data-token="{{this.token.id}}">
|
<li class="token-target-container {{#if this.token.id}}clickable{{/if}}" data-token="{{this.token.id}}">
|
||||||
<header>
|
<header>
|
||||||
<img src="{{this.token.texture.src}}" />
|
<img src="{{this.token.texture.src}}" />
|
||||||
<h2 class="actor-name">{{this.token.name}}</h2>
|
<h2 class="actor-name">{{this.token.name}}</h2>
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@
|
||||||
</div>
|
</div>
|
||||||
</details>
|
</details>
|
||||||
{{#each move.actions as | action index |}}
|
{{#each move.actions as | action index |}}
|
||||||
<button class="action-use-button" data-move-index="{{@../key}}" data-action-index="{{index}}">
|
<button class="action-use-button" data-move-index="{{@../key}}" data-action-index="{{index}}" data-move-path="{{../movePath}}" >
|
||||||
<span>{{localize action.name}}</span>
|
<span>{{localize action.name}}</span>
|
||||||
</button>
|
</button>
|
||||||
{{/each}}
|
{{/each}}
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@
|
||||||
</div>
|
</div>
|
||||||
<div class="targets-container">
|
<div class="targets-container">
|
||||||
{{#each targets}}
|
{{#each targets}}
|
||||||
<div class="token-target-container" data-token="{{this.id}}">
|
<div class="token-target-container {{#if this.id}}clickable{{/if}}" data-token="{{this.id}}">
|
||||||
<img src="{{this.texture.src}}" />
|
<img src="{{this.texture.src}}" />
|
||||||
<h2 class="title">{{this.name}}</h2>
|
<h2 class="title">{{this.name}}</h2>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue