Various fixes/update based on first tests feedback
This commit is contained in:
@@ -167,12 +167,9 @@ Hooks.once('tokenActionHudCoreApiReady', async (coreModule) => {
|
||||
const kits = this.actor.itemTypes?.kit ?? []
|
||||
const actions = []
|
||||
for (const kit of kits) {
|
||||
const charges = kit.system.charges
|
||||
const chargesText = `${charges.value}/${charges.max}`
|
||||
actions.push({
|
||||
name: kit.name,
|
||||
id: kit.id,
|
||||
info1: { text: chargesText },
|
||||
encodedValue: ['kit', kit.id].join(this.delimiter)
|
||||
})
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@ export default class AwEAbilitySheet extends AwEItemSheet {
|
||||
/** @override */
|
||||
static DEFAULT_OPTIONS = {
|
||||
classes: ["ability"],
|
||||
position: { width: 620 },
|
||||
position: { width: 620, height: 560 },
|
||||
window: { contentClasses: ["ability-content"] }
|
||||
}
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ export default class AwEItemSheet extends HandlebarsApplicationMixin(foundry.app
|
||||
classes: ["awemmy", "item"],
|
||||
position: {
|
||||
width: 600,
|
||||
height: "auto"
|
||||
height: 480
|
||||
},
|
||||
form: {
|
||||
submitOnChange: true
|
||||
@@ -91,6 +91,22 @@ export default class AwEItemSheet extends HandlebarsApplicationMixin(foundry.app
|
||||
const handler = this.options.actions?.[actionName]
|
||||
if (handler) handler.call(this, event, input)
|
||||
})
|
||||
// Auto-split comma-separated values on paste
|
||||
input.addEventListener("paste", async event => {
|
||||
const pasted = (event.clipboardData ?? window.clipboardData).getData("text")
|
||||
const parts = pasted.split(",").map(s => s.trim().toLowerCase()).filter(Boolean)
|
||||
if (parts.length < 2) return // single value: let default paste handle it
|
||||
event.preventDefault()
|
||||
const fieldName = input.dataset.field ?? "system.traits"
|
||||
const current = foundry.utils.getProperty(this.document, fieldName) ?? []
|
||||
const merged = [...new Set([...current, ...parts])]
|
||||
try {
|
||||
await this.document.update({ [fieldName]: merged })
|
||||
} catch (err) {
|
||||
ui.notifications.error(game.i18n.localize("AWEMMY.Error.TraitPasteFailed"))
|
||||
console.error("AwE | trait paste update failed:", err)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
@@ -293,12 +293,8 @@ export default class AwECharacterSheet extends AwEActorSheet {
|
||||
}
|
||||
|
||||
static async #onDailyReset(event, target) {
|
||||
const actor = this.document
|
||||
const dailyAbilities = actor.itemTypes.ability.filter(i => i.system.usedToday)
|
||||
if (!dailyAbilities.length) return
|
||||
const updates = dailyAbilities.map(i => ({ _id: i.id, "system.usedToday": false }))
|
||||
await actor.updateEmbeddedDocuments("Item", updates)
|
||||
ui.notifications.info(game.i18n.localize("AWEMMY.Ability.DailyResetDone"))
|
||||
const count = await this.document.resetDailyAbilities()
|
||||
if (count > 0) ui.notifications.info(game.i18n.localize("AWEMMY.Ability.DailyResetDone"))
|
||||
}
|
||||
|
||||
static async #onLongRest(event, target) {
|
||||
|
||||
@@ -3,8 +3,8 @@ export const DEV_MODE = false
|
||||
|
||||
export const ATTRIBUTES = {
|
||||
agility: { id: "agility", abbrev: "AGI", label: "AWEMMY.Attribute.Agility" },
|
||||
fitness: { id: "fitness", abbrev: "FIT", label: "AWEMMY.Attribute.Fitness" },
|
||||
awareness: { id: "awareness", abbrev: "AWA", label: "AWEMMY.Attribute.Awareness" },
|
||||
fitness: { id: "fitness", abbrev: "FIT", label: "AWEMMY.Attribute.Fitness" },
|
||||
influence: { id: "influence", abbrev: "INF", label: "AWEMMY.Attribute.Influence" }
|
||||
}
|
||||
|
||||
@@ -26,6 +26,7 @@ export const ABILITY_COST = {
|
||||
"three": { id: "three", label: "ΔΔΔ" },
|
||||
"reaction": { id: "reaction", label: "↩" },
|
||||
"free": { id: "free", label: "AWEMMY.Ability.Cost.Free" },
|
||||
"variable": { id: "variable", label: "AWEMMY.Ability.Cost.Variable" },
|
||||
"none": { id: "none", label: "—" }
|
||||
}
|
||||
|
||||
@@ -33,7 +34,9 @@ export const ABILITY_TYPE = {
|
||||
"field": { id: "field", label: "AWEMMY.Ability.Type.Field" },
|
||||
"archetype": { id: "archetype", label: "AWEMMY.Ability.Type.Archetype" },
|
||||
"general": { id: "general", label: "AWEMMY.Ability.Type.General" },
|
||||
"beginner": { id: "beginner", label: "AWEMMY.Ability.Type.Beginner" }
|
||||
"beginner": { id: "beginner", label: "AWEMMY.Ability.Type.Beginner" },
|
||||
"advanced": { id: "advanced", label: "AWEMMY.Ability.Type.Advanced" },
|
||||
"pinnacle": { id: "pinnacle", label: "AWEMMY.Ability.Type.Pinnacle" }
|
||||
}
|
||||
|
||||
export const OUTCOME_LABELS = {
|
||||
|
||||
+19
-21
@@ -146,21 +146,15 @@ export default class AwEActor extends Actor {
|
||||
}
|
||||
|
||||
/**
|
||||
* Use a kit item: decrement charges and post a chat message.
|
||||
* Use a kit item: post a chat message.
|
||||
* @param {string} kitId - The kit item ID.
|
||||
*/
|
||||
async useKit(kitId) {
|
||||
const item = this.items.get(kitId)
|
||||
if (!item) return
|
||||
const charges = item.system.charges
|
||||
if (charges.value <= 0) {
|
||||
ui.notifications.warn(game.i18n.format("AWEMMY.Kit.Depleted", { name: item.name }))
|
||||
return
|
||||
}
|
||||
await item.update({ "system.charges.value": charges.value - 1 })
|
||||
await ChatMessage.create({
|
||||
speaker: ChatMessage.getSpeaker({ actor: this }),
|
||||
content: `<p>${game.i18n.format("AWEMMY.Kit.Used", { name: item.name, value: charges.value - 1, max: charges.max })}</p>`
|
||||
content: `<p>${game.i18n.format("AWEMMY.Kit.Used", { name: item.name })}</p>`
|
||||
})
|
||||
}
|
||||
|
||||
@@ -173,7 +167,8 @@ export default class AwEActor extends Actor {
|
||||
if (!item) return
|
||||
const sys = item.system
|
||||
|
||||
if (sys.usedToday) {
|
||||
const isDaily = sys.isDaily
|
||||
if (isDaily && sys.usedToday) {
|
||||
ui.notifications.warn(game.i18n.format("AWEMMY.Ability.AlreadyUsed", { name: item.name }))
|
||||
return
|
||||
}
|
||||
@@ -187,7 +182,6 @@ export default class AwEActor extends Actor {
|
||||
await this.update({ "system.flowPoints.value": fp - sys.flowPointCost })
|
||||
}
|
||||
|
||||
const isDaily = sys.frequency?.toLowerCase().includes("day")
|
||||
if (isDaily) await item.update({ "system.usedToday": true })
|
||||
|
||||
const abilityTypeLabel = game.i18n.localize(SYSTEM.ABILITY_TYPE[sys.abilityType]?.label ?? sys.abilityType)
|
||||
@@ -212,7 +206,18 @@ export default class AwEActor extends Actor {
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform a long rest: restore HP, reset daily abilities, refill kits, post chat card.
|
||||
* Reset all once-per-day abilities (usedToday → false).
|
||||
* @returns {Promise<void>}
|
||||
*/
|
||||
async resetDailyAbilities() {
|
||||
const dailyAbilities = this.itemTypes.ability.filter(i => i.system.usedToday)
|
||||
if (!dailyAbilities.length) return 0
|
||||
await this.updateEmbeddedDocuments("Item", dailyAbilities.map(i => ({ _id: i.id, "system.usedToday": false })))
|
||||
return dailyAbilities.length
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform a long rest: restore HP, reset daily abilities, post chat card.
|
||||
* No confirmation dialog — caller is responsible for confirming if needed.
|
||||
*/
|
||||
async longRest() {
|
||||
@@ -227,16 +232,9 @@ export default class AwEActor extends Actor {
|
||||
}
|
||||
if (Object.keys(updates).length > 0) await this.update(updates)
|
||||
|
||||
const dailyAbilities = this.itemTypes.ability.filter(i => i.system.usedToday)
|
||||
if (dailyAbilities.length) {
|
||||
await this.updateEmbeddedDocuments("Item", dailyAbilities.map(i => ({ _id: i.id, "system.usedToday": false })))
|
||||
summary.push(game.i18n.format("AWEMMY.Rest.AbilitiesReset", { count: dailyAbilities.length }))
|
||||
}
|
||||
|
||||
const depleted = this.itemTypes.kit.filter(i => i.system.charges.value < i.system.charges.max)
|
||||
if (depleted.length) {
|
||||
await this.updateEmbeddedDocuments("Item", depleted.map(i => ({ _id: i.id, "system.charges.value": i.system.charges.max })))
|
||||
summary.push(game.i18n.format("AWEMMY.Rest.KitsReplenished", { count: depleted.length }))
|
||||
const resetCount = await this.resetDailyAbilities()
|
||||
if (resetCount > 0) {
|
||||
summary.push(game.i18n.format("AWEMMY.Rest.AbilitiesReset", { count: resetCount }))
|
||||
}
|
||||
|
||||
const bulletList = summary.map(s => `<li>${s}</li>`).join("")
|
||||
|
||||
@@ -21,7 +21,11 @@ export default class AwEAbility extends foundry.abstract.TypeDataModel {
|
||||
schema.frequency = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.requirements = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.trigger = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.range = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.targets = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.duration = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.traits = new fields.ArrayField(new fields.StringField())
|
||||
schema.isDaily = new fields.BooleanField({ required: true, initial: false })
|
||||
schema.flowPointCost = new fields.NumberField({ required: true, nullable: false, initial: 0, min: 0, integer: true })
|
||||
schema.usedToday = new fields.BooleanField({ required: true, initial: false })
|
||||
|
||||
|
||||
@@ -4,7 +4,10 @@ export default class AwEBackground extends foundry.abstract.TypeDataModel {
|
||||
const schema = {}
|
||||
|
||||
schema.description = new fields.HTMLField({ required: true, textSearch: true })
|
||||
schema.bonus = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.boostAgility = new fields.BooleanField({ initial: false })
|
||||
schema.boostAwareness = new fields.BooleanField({ initial: false })
|
||||
schema.boostFitness = new fields.BooleanField({ initial: false })
|
||||
schema.boostInfluence = new fields.BooleanField({ initial: false })
|
||||
|
||||
return schema
|
||||
}
|
||||
|
||||
@@ -1,15 +1,10 @@
|
||||
export default class AwEKit extends foundry.abstract.TypeDataModel {
|
||||
static defineSchema() {
|
||||
const fields = foundry.data.fields
|
||||
const requiredInteger = { required: true, nullable: false, integer: true }
|
||||
const schema = {}
|
||||
|
||||
schema.description = new fields.HTMLField({ required: true, textSearch: true })
|
||||
schema.fieldName = new fields.StringField({ initial: "", required: false, nullable: true })
|
||||
schema.charges = new fields.SchemaField({
|
||||
value: new fields.NumberField({ ...requiredInteger, initial: 0, min: 0 }),
|
||||
max: new fields.NumberField({ ...requiredInteger, initial: 0, min: 0 })
|
||||
})
|
||||
|
||||
return schema
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user